Анимация
JavaScript
|
Главная Библионтека Обратите внимание: если любая из пяти гласных не обнаруживается, остальная часть выражения пропускается, потому что операция && не вычисляет свой правый аргумент, если значение левого аргумента - "ложь". б) Еще один способ: while (<STDIN>) { if (/a.*e.*i.*o.*u/i) ( print; Этот ответ, как оказывается, проще. Здесь у нас в операторе if используется более простое регулярное выражение, которое ищет пять гласных в указанной последовательности, разделенных любым количеством символов. в) Вот один из способов решения этой задачи: while (<STDIN>) { if (/"[eiou]*а["lou]*е["aou]*i["aeu]*о["aei]*u["aeio]*S/i) { print; Выглядит уродливо, но работает. Чтобы написать такое, просто подумайте: "Что может стоять между началом строки и первой буквой а?", а затем "Что может стоять между первой буквой а и первой буквой е?". В конце концов все решится само, от вас потребуется минимум усилий. 3. Вот один из способов решения этой задачи: while (<STDIN>) { chomp; ($user, $gcos) = (split /:/)[0,4]; (Sreal) = split (/,/, $gcos); print "$user is $real\n"; Bo внешнем цикле while производится считывание по одной строке из файла паролей в переменную $ . По достижении последней строки цикл завершается. Вторая строка тела цикла while означает разбиение строки на отдельные переменные с использованием в качестве разделителя двоеточия. Два из этих семи значений заносятся в отдельные скалярные переменные с имеющими смысл (мы надеемся) именами. Поле GCOS (пятое поле) затем разбивается на части с использованием в качестве разделителя символа запятой, и список-результат присваивается одной скалярной переменной, заключенной в круглые скобки. Эти скобки играют важную роль - они указывают, что операция присваивания должна быть не скалярной, а для массива. Скалярная переменная $геа1 получает первый элемент списка-результата, а остальные элементы отбрасываются. Оператор print затем выводит результаты на экран. 4. Вот один из способов решения этой задачи: while (<STDIN>) ( chomp; ($gcos) = (split /:/) [4]; ($real) = split (/,/, Sgcos); ($first) = split(/\s+/, $real); $seen($first}++; foreach (keys %seen) { if ($seen($ ) > 1) ( print "$ was seen Sseen{$ } times\n"; Цикл while работает во многом так же, как цикл while из предыдущего упражнения. Помимо разбивки строки на поля и поля GCOS на реальное имя (и другие компоненты), в этом цикле осуществляется также разбиение реального имени на собственно имя и остальную часть. После определения имени элемент хеша в %seen инкрементируется, отмечая тот факт, что мы нашли конкретное имя. Обратите внимание: оператор print в этом цикле не используется. В цикле foreach осуществляется проход по всем ключам хеша %seen (именам из файла паролей) с присваиванием каждого из них по очереди переменной $ . Если значение, записанное в %seen по данному ключу, больше 1, значит, это имя уже встречалось. Оператор if проверяет, так ли это, и при необходимости выводит соответствующее сообщение. 5. Вот один из способов решения этой задачи: while (<STDIN>) ( chomp; ($user, $gcos) = (split /:/)[0,4]; ($real) = split /,/, $gcos; ($first) = split(/\s+/, $real) ; $seen($first} .= " $user"; foreach (keys %names) ( $this = $names($ ); If ($this =~ /. /) { print "$ IS used by:$this\n"; Эта программа похожа на ответ к предыдущему упражнению, но вместо того чтобы просто подсчитывать, сколько раз у нас встречалось определенное имя, мы присоединяем регистрационное имя пользователя к элементу хеша % names, указывая имя в качестве ключа. Так, для Фреда Роджерса (регистрационное имятггодегз) $names{ "Fred" ) становится равным " mrrogers", а когда появляется Фред Флинтстоун (регистрационное имя fred), $names{"Fred") становится равным " mrrogers fred". После завершения цикла у нас имеется список имен и список регистрационных имен всех имеющих данное имя пользователей. В цикле foreach, как и в ответе к предыдущему упражнению, осуществляется проход по полученному в результате хешу, но вместо того, чтобы проверять, больше ли единицы значение элемента хеша, мы должны проверить, есть ли в этом значении более одного регистрационного имени. Для этого нужно занести значение в скалярную переменную $this и посмотреть, есть ли в нем после какого-нибудь символа пробел. Если есть, то одному реальному имени соответствуют несколько регистрационных имен, которые и указываются в выдаваемом в результате сообщении. Глава 8 "Функции" 1. Вот один из способов решения этой задачи: sub card I my %card map; @card map{1..9} = qw( one two three four five six seven eight nine my($num) = @ ; if ($card map{$num)) { return $card map{$num}; ) else { return $num; # driver routine: while (<>) I chomp; print "card of $ is ", Scard($ ), "\n"; Подпрограмма scard (названная так потому, что она возвращает название на английском языке для данного числа) начинается с инициализации хеша-константы, который называется %card map. Значения ему присваиваются так, что, например, $card map{ 6} равно six; это делает преобразование достаточно простым. 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 [ 86 ] 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 |