Программирование на Objective-C 2.0
Шрифт:
Objective-C позволяет помещать отдельный символ «точка с запятой» в любом месте, где можно ставить обычный программный оператор. Такой оператор (его называют пустым (null) оператором) ничего не выполняем Это может показаться бесполезным, но программисты часто используют его в операторах while, for и do. Например, следующий оператор используется для сохранения всех символов, прочитанных со стандартного устройства ввода (по умолчанию это терминал), в массив символов, на который указывает text. Ввод продолжается, пока не встретится символ новой строки (перевода строки). В этом операторе ис-пользуется библиотечная процедура getchar, которая читает и возвращает по од-ному символу со стандартного устройства ввода. while ((*text++ = getchar )!='') ;
Все операции выполняются
На самом нижнем уровне приоритетов находится оператор «запятая». В главе 5 мы указывали, что внутри оператора for можно включать в любое из полей не-сколько выражений, отделяя их запятыми. Например, в операторе for (i = 0, j = 100; i != 10; ++i, j -= 10) ...
до начала цикла инициализируется значение i, равное 0, и j, равное 100. После выполнения тела цикла значение i увеличивается на 1 ,а из значения) вычитается 10.
Поскольку все операторы в Objective-C дают какое-то значение, значением оператора «запятая» является результат правого выражения. Оператор sizeof
В программах никогда не следует делать какие-либо предположения о размере определенного типа данных, но иногда нужно знать эту информацию — например, при выделении динамической памяти, использовании библиотечных процедур, при записи или архивации данных в файл. В Objective-C имеется оператор с именем sizeof, который можно использовать для определения размера типа данных или объекта. Оператор sizeof возвращает размер указанного элемента в байтах. Аргументом для оператора sizeof может быть переменная, имя массива, имя базового типа данных, объект, имя производного типа данных или выражение. Например, написав sizeof (int)
мы получим число байтов для сохранения целого значения. На моем Mac Book Air получается значение 4 (то есть 32 бита). Если объявить х как массив из 100 значений типа int, то выражение sizeof (х)
даст количество памяти, необходимой для сохранения 100 целых элементов массива х.
Если myFract является объектом класса Fraction, содержащим две переменных экземпляра типа int (numerator и denominator — числитель и знаменатель), то выражение sizeof (myFract)
даст значение 4 на любом компьютере, где для представления указателей ис-пользуются 4 байта. На самом деле sizeof дает это значение для любого объекта, потому что мы запрашиваем размер указателя на данные объекта. Чтобы получить размер реальной структуры данных для хранения экземпляра объекта класса Fraction, нужно написать sizeof (myFract)
На моем MacBook Air это дает значение 12. Эту сумма складывается из 4 байтов для numerator, 4 байтов для denominator, плюс еще 4 байта для наследуемого компонента isa, о котором говорится в разделе «Как это действует» в конце главы. Выражение sizeof (struct data_entry)
дает количество памяти, необходимой для хранения одной структуры data_entry. Если data определен как массив элементов struct data_entry, то выражение sizeof (data) / sizeof (struct dataentry)
дает число элементов, содержащихся в data (data должен быть заранее опреде-ленным массивом, а не формальным параметром или массивом по внешней ссылке). Выражение sizeof (data) / sizeof (data[0])
дает тот же результат.
Используйте оператор sizeof, чтобы избежать вычислений или задания фик-сированных размеров в программах. Аргументы командной строки
Довольно часто программы запрашивают на терминале пользователя ввод не-большого количества информации.
Вместо запроса такую информацию можно вводить при запуске программы. Это осуществляется с помощью аргументов командной строки (commandline arguments).
Мы уже указывали, что единственным отличительным свойством функции main является специальное имя; она указывает, где должно начинаться выполнение программы. На самом деле функцию main в начале выполнения программы вызывает
система выполнения (runtime) так же, как мы вызываем функцию из своей собственной программы. Когда main заканчивает выполнение, управление передается системе runtime, которая знает, что ваша программа завершена.Когда система runtime вызывает main, этой функции передаются два аргумен-та. Первый аргумент, который называется arge (сокращение от argument count — число аргументов), является целым значением, которое указывает число аргу-ментов, вводимых в командной строке. Второй аргумент для main — это массив указателей на символьные значения с именем argv (сокращение от argument vector). В этом массиве содержатся aigc + I символьных указателей. Первым элементом этого массива является указатель на имя выполняемой программы или указатель на нуль-строку, если имя программы недоступно. Последующие записи этого массива указывают значения, заданные в той же строке, что и команда, инициировавшая выполнение данной программы. Последний указатель массива argv, argvfargc], определен как пустой указатель.
Для доступа к аргументам командной строки функция main должна быть объявлена с двумя аргументами. Во всех программах этой книги мы использовали объявление int main (int arge, char *argv[]) { ... }
Напомним, что объявление argv определяет массив, который содержит эле-менты типа «указатель на тип char». Для практического использования аргументов командной строки предположим, что мы разрабатываем программу, которая ищет нужное слово в словаре и выводит его смысл. С помощью следующей команды можно использовать аргументы командной строки, чтобы слово, смысл которого нужно определить, было указано одновременно с запуском программы. lookup aerie
Это позволяет обойтись без запроса ввода пользователя, поскольку слово вво-дится из командной строки.
При запуске этой команды система автоматически передает функции main ука-затель на символьную строку "aerie" вагду[1]. Напомним, что argv[0] содержит указатель на имя программы (в данном случае это "lookup").
Процедура main может иметь следующий вид. #include <Foundation/Foundation.h> int main (int argc, char *argv[]) { struct entry dictionary[100] = { {"aardvark", "a burrowing African mammal"}, {"abyss", "a bottomless pit"}, {"acumen", "mentally sharp; keen"}, {"addle", "to become confused"}, {"aerie", "a high nest"}, {"affix", "to append; attach"}, {"agar", "a jelly made from seaweed"}, {"ahoy", "a nautical call of greeting"}, {"aigrette", "an ornamental cluster of feathers"}, {"ajar", "partially opened"} }; int entries = 10; int entryNumber; int lookup (struct entry dictionary [], char search]], int entries); if ( argc != ? ) { NSLog (@"No word typed on the command line."); return (1); } entryNumber = lookup (dictionary, argv[1], entries); if (entryNumber != -1 ) NSLog (@"%s", dictionaryfentryNumber].definition); else NSLog (@"Sorry, %s is not in my dictionary.", argv[1]); return (0); }
Процедура main при запуске программы проверяет, было ли введено слово после имени профаммы. Если не было или было введено больше одного слова, то значение arge не равно 2, программа выводит сообщение об ошибке и завершает работу, возвращая при выходе значение состояния 1.
Если значение arge равно 2, то вызывается функция lookup для поиска в сло-варе слова, на которое указывает argv[1]. Сели это слово найдено, выводится его смысл (определение).
Аргументы командной строки всегда сохраняются как символьные строки. Например, при запуске профаммы power (возведение в степень) с аргументами командной строки 2 и 16 power 2 16
в argv[1] сохраняется указатель на символьную строку "2" и в argv[2] сохраняется указатель на символьную строку "16". Если программа должна интерпретировать аргументы как числа (например, в случае программы power), их должна преобразовывать сама эта программа. Для таких преобразований в библиотеке профамм содержится несколько процедур: sscanf, atof, atoi, strtod и strotol. В части 11 вы узнаете, как использовать класс NSProcessInfo для доступа к аргументам ко-мандной строки как к строковым объектам, а не С-строкам. 13.8. Как это действует