46019 (665326), страница 15
Текст из файла (страница 15)
В выражении E1 < E2 операнды должны удовлетворять одному из следующего набора условий:
1. Оба значения Е1 и Е2 - арифметического типа.
2. Оба значения Е1 и Е2 являются указателями квалифицированных или неквалифицированных версий совместимых типов объектов.
Определение квалифицированных имен дается на стр.108 оригинала.
3. Оба значения Е1 и Е2 являются указателями квалифицированных или неквалифицированных версий совместимых неполных типов.
В случае 1 выполняются обычные арифметические преобразования. Результат E1 < E2 имеет тип int. Если значение E1 меньше значения E2, то результат равен 1 (истина); в противном случае результат равен 0 (ложь).
В случаях 2 и 3, где Е1 и Е2 являются указателями совместимых типов, результат операции E1 Обычно сравнение указателей разных структур, массивов или объединений , либо сравнение указателей вне диапазона объекта типа массив дает неопределенные результаты; однако исключение делается для указателя "за последним элементом", как указывается в разделе "Арифметические действия с указателями" на стр.57 оригинала. Если Р указывает на элемент массива, а Q указывает на его последний элемент, то выражение H Операция больше чем > Выражение E1 > E2 дает 1 (истина), если значение Е1 больше значения Е2;в противном случае результат равен 0 (ложь), причем используются те же способы интерпретации арифметических сравнений и сравнений указателей, что определены для операции "больше чем". К операндам применимы те же правила и ограничения. Операция меньше или равно <= Аналогичным образом, выражение E1 <= E2 дает 1 (истина), если значение Е1 меньше или равно значению Е2. В противномслучаерезультат равен 0 (ложь), причем используются те же способы интерпретации арифметических сравнений и сравнений указателей, что определены для операции "меньше чем". К операндам применимы те же правила и ограничения. Операция больше или равно >= И наконец, выражение E1 >= E2 дает 1 (истина), если значение Е1 больше или равно значению Е2. В противном случае результат равен 0 (ложь), причем используются те же способы интерпретации арифметических сравнений и сравнений указателей, что определены для операции "меньше чем". К операндам применимы те же правила и ограничения. Операции типа равенства Существует две операции типа равенства: == и !=. Они проверяют условие равенства операндов арифметического типа и типа указателей, следуя при этом правилам, аналогичным тем, что действуют для операцийотношения. Отметим, однако, что == и != имеют более низкий приоритет выполнения, чем операции отношения , =. Кроме того, операции == и != позволяют выполнять проверку равенства указателей в таких случаях, где операции отношения неприменимы. Синтаксис этих операций следующий: выражение-типа-равенства: выражение-отношения выражение-типа-равенства == выражение-отношения выражение-типа-равенства != выражение-отношения Операция проверки равенства == В выражении E1 == E2 операнды должны удовлетворять одному из следующего набора условий: 1. Оба значения Е1 и Е2 - арифметического типа. 2. Оба значения Е1 и Е2 являются указателями квалифицированных или неквалифицированных версий совместимых типов. 3. Одно из значений, Е1 или Е2, является указателем объекта неполного типа, а второй - указателем на квалифицированную или неквалифицированную версию void. 4. Одно из значений, Е1 или Е2, является указателем, а второе - константой типа пустого указателя. Если Е1 и Е2 имеют тип, являющийся допустимым типом для операций отношения, то применимы правила, подробно описанные для операций отношения типа Е1 < E2, E1 <= T2, и т.д. В случае 1, например, выполняются обычные арифметические преобразования, а результат операции Е1 == Е2 имеет тип int. Если значение Е1 равно значению Е2, то результат равен 1 (истина); в противном случае результат равен нулю (ложь). В случае 2 Е1 == Е2 дает 1 (истина), если Е1 и Е2 указывают на один и тот же объект, либо оба указывают на "следующий после последнеего" элемент одного и того же объекта типа массив, либо оба являются пустыми указателями. Если Е1 и Е2 являются указателями на объекты типа функции, то Е1 == Е2 дает значение 1 (истина), если оба они пустые, либо оба указывают на одну и ту же функцию. И наоборот, если Е1 == Е2 дает 1 (истина), то и Е1, и Е2 указывают на одну и ту же функцию или являются пустыми. В случае 4 указатель объекта или неполного типа преобразуется к типу другого операнда (указателю квалифицированной или неквалифицированной версии void). Оператор проверки неравенства != Выражение Е1 != Е2 подчиняется тем же правилам, что и ля Е1 == Е2, за исключением того, что результат равен 1 (истина), если операнды неравны, и 0 (ложь) в случае равенства операндов. Операция поразрядного И & Синтаксис данной операции следующий: выражение-И: выражение-типа-равенства выражение-И & выражение-равенства В выражении E1& E2 оба операнда должны быть интегрального типа. Выполняются обычные арифметические преобразования Е1 и Е2, а результатом является поразрядное И для Е1 и Е2. Каждый бит результата определяется в соответствии с таблицей 1.21. Таблица истинности для поразрядных операций Таблица 1.21 Битовое значение в Е1 в Е2 Битовое значение Е1 & E2 E1 ^ E2 E1 \! E2 0 0 0 0 1 0 0 1 0 1 0 1 1 1 1 0 0 1 1 1 Операция поразрядного исключающего ИЛИ^ Синтаксис этой операции следующий: выражение-исключающее-ИЛИ: выражение-И выражение-исключающее-ИЛИ ^ выражение-И В выражении E1 ^ E2 оба операндадолжныбыть интегрального типа,причем выполняются обычные арифметические преобразования Е1 и Е2, а результатом операции является поразрядное исключающееИЛИ для Е1 и Е2. Каждый бит результата определяется таблицей 1.21. Операция поразрядного включающего ИЛИ \! Синтаксис этой операции следующий: выражение-включающее-ИЛИ: выражение-исключающее-ИЛИ выражение-включающее-ИЛИ \! выражение-исключающее-ИЛИ В выражении E1\! E2 оба операнда должны быть интегрального типа, причем выполняются обычные арифметические преобразования Е1 и Е2, а результатом операции является поразрядное включающее ИЛИ для Е1 и Е2. Каждый бит результата определяется таблицей 1.21. Операция логического И&& Синтаксис этой операции следующий: выражение-логическое-И: выражение-включающее-ИЛИ выражение-логическое-И && выражение-включающее-ИЛИ В выражении E1 && E2 оба операнда должны быть скалярноготипа. Результат операции имеет тип int и равен 1 (истина), если оба значения, Е1 и Е2 ненулевые; в противном случае результат равен 0 (ложь). В отличие от поразрядной операции &, операция && гарантирует расчет выражения в последовательности слева-направо: первым вычисляется Е1; если Е1 равен 0, то Е1 && E2 дает 0 (ложь), и Е2 не вычисляется вообще. Операция логического ИЛИ \!\! Синтаксис этой операции следующий: выражение-логическое-ИЛИ: выражение-логическое-И выражение-логическое-ИЛИ \!\! выражение-логическое-И В выражении E1 \!\! E2 оба операнда должны быть скалярноготипа. Результат операции имеет тип int и равен 1 (истина), если одно из значений, Е1 или Е2 ненулевое; в противном случае результат равен 0 (ложь). В отличие от поразрядной операции \!, операция \!\! гарантирует расчет выражения в последовательности слева-направо: первым вычисляется Е1; если Е1 не равен 0, то Е1 \!\! E2 дает 1 (истина), и Е2 не вычисляется вообще. Условная операция ?: Синтаксис этой операции следующий: условное-выражение выражение-логическое-ИЛИ выражение-логическое-ИЛИ ? выражение : условное-выражение В выражении Е1? Е2 : Е3 операнд Е1 должен быть скалярного типа. Операнды Е2 и Е3 должны удовлетворять одному из приводимых ниже правил: 1. Оба операнда - арифметического типа. 2. Оба операнда имеют совместимые типы структуры или объединения. 3. Оба операнда - типа void. 4. Оба операнда имеют тип указателя на квалифицированные или неквалифицированные версии совместимых типов. 5. Один операнд имеет тип указателя, а второй является константой типа пустого указателя. 6. Один операнд имеет тип указателя на объект или неполный тип, а второй - тип указателя на квалифицированную или неквалифицированную версию типа void. Прежде всего вычисляется Е1; если он имеет ненулевое значение (истина), то Е2 вычисляется, а Е3 игнорируется. Если Е1 дает ноль (ложь), то Е3 вычисляется, а Е2 игнорируется.Результат операции Е1 ? Е2 : Е3 зависит от того, который из операндов, Е2 или Е3, будет вычисляться. В случае 1 оба операнда, Е2 и Е3, подвергаются обычным арифметическим преобразованиям, а типом результата будетобщий тип, получаемый в результате преобразований. В случае 2 типом результата будет являться общий тип структуры или объединения Е2 или Е3. В случае 3 результат будет иметь тип void. В случаях 4 и5 типом результата является указатель типа, квалифицированного всеми квалификаторами типов, на которые указывают оба операнда. В случае 6 типом результата будет тип операнда, не являющегося указателем на void. Операции присвоения Существует одиннадцать операций присвоения. самым простым из них является операция =; остальные называются составными операциями присвоения. Синтаксис операций присвоения следующий: выражение-присвоения: условное-выражение унарное-выражение операция присвоения выражение-присвоения операция-присвоения: одно из = *= /= %= += -= <>= &= ^= \!= Простая операция присвоения = В выражении Е1 = Е2 Е1 должен быть модифицируемым именующим выражением. Значение Е2 после преобразования к типу Е1 помещается в объект, задаваемый Е1 (замещая предыдущее значение Е1). Значение выражнения присвоения это значение Е1 после присвоения. Само по себе выражение присвоения не является именующим значением. ОперандыЕ1 и Е2 должны удовлетворять одному из следующего набора правил: 1. Е1 имеет квалифицированный или неквалифицированный арифметический тип, а Е2 имеет арифметический тип. 2. Е1 имеет квалифицированную или неквалифицированную версию типа структуры или объединения, совместимого с типом Е2. 3. Е1 и Е2 это указатели на квалифицированную или неквалифицированную версии совместимых типов , а тип, на который указывает левый операнд, имеет все квалификаторы типа, на который указывает правый операнд. 4. Один из операндов, Е1 или Е2, является указателем объектаили неполного типа, а другой - указвтелем на квалифицированную или неквалифицированную версию void. Тип, на который указываетлевый операнд, имеет все квалификаторы типа, на который указывает правый операнд. 5. Е1 является указателем, а Е2 - константой типа пустого указателя. Составные операции присвоения Составные операции вида операция=, где "операция" - это один из десяти символов операции * / % + - <> & ^ \!, интерпретируются следующим образом: Е1 операция= Е2 имеет тот же эффект, что и Е1 = Е1 операция Е2 за исключением того, что именующее значение Е1 вычисляется только один раз. Например, Е1 += Е2 это то же самое, что Е1 = Е1 + Е2. Правила для составных операций присвоения, следовательно, такие же, как и описанные в предыдущем разделе (для простой операции присвоения =). Операция с запятой Синтаксис этой операции следующий: выражение: выражение-присвоения выражение , выражение-присвоения В выражении с запятой Е1,Е2 левый операнд Е1 вычисляется как выражение void, затем Е2 вычисляется таким образом, что дает результат и тип выражения с запятой. Рекурсивно, выражение Е1,Е2,...,Уn дает в результате вычисляемые слева-направо Ei, а значение итип En определяет результат всего выражения в целом. Для того, чтобы избежать неоднозначности интерпретации запятых с учетом существования запятых при задании аргументов функции и в списках инициализации, следует использовать круглые скобки. Например, func(i, (j = 1, j +4), k); вызывает func с тремя аргументами, а не с четырьмя. Эти аргументы: i, 5 и k. Операторы Операцииопределяют поток управления выполнением программы. При отсутствии заданных операторов перехода и выбора операторы выполняются последовательно, в порядке их следования в исходном коде программы. В следующей таблице показан синтаксис операторов: Операторы Turbo C++ Таблица 1.22 оператор: оператор-с-меткой составной-оператор оператор-выражение оператор-выбора оператор-итерации оператор-перехода asm-оператор объявление (только С++) asm-оператор: asm лексемы новая-строка asm лексемы; asm (*лексемы; = *) оператор-с-меткой идентификатор : операция case выражение-типа-константы : оператор default : оператор составной-оператор: (* *) список-объявления: объявление список-объявления объявление список-операторов: ; оператор-выбора: if (выражение) оператор if (выражение) оператор else оператор switch (выражение) выражение выражение-итерации: while (выражение) оператор do оператор while (выражение); for (оператор-нач-условия ; <выраже- ние>)оператор оператор-нач-условия: оператор-выражение объявление (только С++) оператор-перехода: goto идентификатор; continue ; break ; return ; Блоки Составной оператор, или блок, представляет собой список (возможно, пустой) операторов, заключенных в фигурные скобки ((**)). Синтаксически блок можно рассматривать в качестве единого оператора, но он играет также роль в определении контекста идентификаторов. Идентификатор, объявленный в пределах блока, имеет контекст, начиная с точки объявления и кончая заключающей скобкой. Блоки могут иметь любую глубину вложенности. Операторы-с-метками Оператору можно присвоить метку следующим образом: 1. идентификатор-метки : оператор Идентификатор метки служит мишенью для оператора безусловного перехода. Идентификаторы меток имеют свое собственное пространство имен в контексте функции. Отметим, что С++ позволяетдавать метки как операторам объявления, так и прочим операторам. 2. case выражение-типа-константы : оператор default : оператор Операторы с метками case и default используются только в сочетании с операторами выбора. Операторы-выражения Любое выражение, за которым следует двоеточие, образует оператор-выражение: Turbo C++ выполняет операторы-выражения, вычисляя выражения. Все побочные эффекты от этого вычисления завершаются до начала выполнения следующего оператора. Большинство операторов-выражений представляют собой операторы присвоения или вызовы функций. Специальным случаем является пустой оператор, состоящий из одного двоеточия (:). Пустой оператор не выполняет никаких действий. Тем неменее,он полезен в тех случаях, когда синтаксис С ожидает наличия некоторого оператора, но по программе он не требуется. Операторы выбора Операторы выбора, или операторы управления потоком выполнения программы, выполняют выбор одной из альтернативных ветвей программы, проверяя для этого определенные значения. Сущесвует два типа операторов выбора: if...else и switch. Операторы if Базовый оператор if имеет следующий шаблон: if(условное-выражение) оператор-если-"истина" оператор-если-"ложь" Заключение условного-выражения в круглые скобки является важным моментом синтаксиса этого оператора. Условное-выражение должно быть скалярного типа. Это выражение вычисляется. Если оно является нулевым (или пустым в случае типа указателя), мы говорим, что условное-выражение ложно; в противном случае оно истинно. Если предложение else отсутствует, а условное-выражение дает значение "истина", то выполняется оператор-если-"истина"; в противном случае он игнорируется. Если задано опциональное предложениеelse оператор-если-"ложь", а условное-выражение дает значение "истина", то выполняется оператор-если-"истина"; в противном случае выполняется оператор-если"ложь". Примечание В отличие от, например, Паскаля, Turbo C++ не имеет специального булевого типа данных. В условных проверках роль такого типа может играть целочисленная переменная или указатель. Выражение отношения (a > b) (если оно допустимо) дает int 1 (истина), если (a > b), и int 0 (ложь), если (a < b). Преобразования указателейвыполняются таким образом, что значение указателя всегда может быть корректно сравнено с выражением типа константы, дающим 0. Таким образом, сравнение для пустых указателей может быть сделано в виде if (lptr)... или if (ptr == 0).... Оператор-если-"ложь" и оператор-если-"истина" сами могут являться операторами if, что позволяет организовывать любую глубину вложенности условных проверок. При использовании вложенных конструкций if...else следует быть внимательным и обеспечивать правильный выбор выполняемых операторов. Оператор endif здесь отсутствует; любая неоднозначность конструкции "else" разрешается сопоставлением else с последним найденным на уровне данного блока if без else. Например, if (x == 1) if (y == 1) puts("x=1 и y=1"); else puts("x != 1"); дает неверное решение! else, независимо от ваших намерений, сопоставляется второму оператору if. Правильное решение это: x=1 и y!=1. Отметим действие фигурных скобок: if (x == 1) (* if (y == 1) puts("x = и y=1"); *) else puts("x != 1"); // правильное решение Операторы switch Оператор switch использует следующий базовый формат: switch (переключающее-выражение) оператор-варианта Операторswitchпозволяет передавать управление одному из нескольких операторов с меткой варианта в зависимости от значения переключающего выражения. Последнее должно быть интегрального типа (в С++ оно может быть типа класса, при условии, что возможно его однозначное преобразование к интегральному типу.) Любой оператор в операторе-варианта (включая пустой оператор) может быть помечен одной или более меткой варианта: case выражение-типа-константы-i : оператор-варианта-i где каждое выражение-типа-константы-i должно иметь уникальное целочисленное значение (преобразуемое к типу управляющего выражения) в пределах объемлющего оператора switch. Допускается иметь в одном операторе switch повторяющиеся константы варианта. Оператор может иметь также не более одной метки default: default : оператор-умолчания После вычисления переключающего-выражения выполняется сопоставление результата с одним из выражений-типа-константы -i. Если найдено соответствие, то управление передается оператору-варианта-i с меткой, для которой найдено соответствие. Если соответствия не найдено и имеется метка default, то управление передается оператору-умолчания. Если соответствия не найдено и метка default отсутствует, то никакие операторы не выполняются. Когда программа встречает метки case и default, это не производит на нее никакого действия. Управление просто передается дальше через метки следующему оператору или переключателю. Для того, чтобы остановить выполнение группы операторов дляконкретного варианта, следует использовать оператор break. Операторы итерации Операторы итерации позволяют организовывать циклическое выполнение набора операторов программы. Turbo C++ имеет три формы операторов итерации : циклы while, do и for. Операторы while Общий формат данного оператора следующий: while (условное-выражение) оператор-пока-"истина" Оператор тела цикла, оператор-пока-"истина", будет циклически повторяться до тех пор, пока вычисление условного выражения не даст значения ноль (ложь). Условное выражение вычисляется и проверяется первым (как описано на стр.93 оригинала). Если это значение ненулевое (истина), то выполняется оператор-пока-"истина"; если не встречен оператор перехода, выполняющий выход из цикла, то условное-выражение вычисляется снова. цикл повторяется до тех пор, пока условное-выражение не даст значения 0. Как и в случае оператора if, выражения типа указателя могут сравниваться с пустым указателем, так что while (ptr) ... эквивалентно while (ptr != NULL)... Цикл while представляет собой удобный способ сканирования строк и других заканчивающихся пустым символом структур данных: char str[10]="Borland"; char *ptr=&str[0]; int count=0; //... while (*ptr++) // цикл до конца строки count++; При отсутствии операторов перехода оператор-пока-"истина" должен некоторым способом воздействовать на значение условного-выражения, либо последнее должно изменяться во время его вычисления, с тем, чтобы предотвратить зацикливание. Операторы do while Общий формат этих операторов следующий: do выполняемый-оператор while (условное-выражение) Выполняемый-оператор циклически повторяется до тех пор, пока вычисление условного-выражения не даст 0 (ложь). Главное отличие этого оператора от оператора while состоит в том, что условное-выражение здесь проверяется не до, а после первого выполнения тела цикла. Гарантированокак минимум одно его выполнение. На тип условного-выражения накладывается то же самое ограничение (оно должно быть скалярным). Операторы for Формат оператора for в С следующий: for(;; ) оператор В С++ может быть как выражением, так и объявлением. Последовательность действий при выполнении данного оператора следующая: 1. Выполняется вычисление выражения-инициализации, если таковое задано. Как следует из его названия, это выражение обычно инициализирует один или несколько счетчиков цикла, но его синтаксис в действительности позволяет любую степень сложности (включая в случае С++ объявления). Отсюда следует вывод, что любая программа в С может быть записана в виде единственного цикла for. (Однако не пытайтесь писать в таком стиле без должной подготовки. Такое доступно лишь высоким профессионалам). 2. Выражение-проверки вычисляется по правилам, приводимым для циклов while. Если выражение-проверки ненулевое (истина), то оператор тела цикла выполняется. Пустое выражение трактуется в данном случае как while(1), то есть как если бы условие проверкивыполнялось всегда.Если выражение-проверки дает значение ноль (ложь), то цикл for прекращается.