К. Арнольд, Д. Гослинг - Язык программирования Java (1160779), страница 22
Текст из файла (страница 22)
В приведенном ниже фрагменте метод sameSignбудет выполняться лишь в том случае, если x и y имеют одинаковый знак (или одновременно равны нулю), в противном случае выполняетсяdifferentSign:differentSign:if (x << 0 == y << 0)sameSign();elsedifferentSign();Значения с плавающей точкой подчиняются стандартному упорядочению (–1.0 меньше 0.0, которое, в свою очередь, меньше положительнойбесконечности), за исключением аномального значения NaN. Все операторы отношения, которые сравнивают NaN с числом, всегда возвращаютfalse, кроме оператора !=, который всегда возвращает true.
Данное утверждение остается истинным, даже если оба операнда равны NaN.Например, значение выражения:Double.NaN == Double.NaNвсегда равно false. Чтобы проверить, является ли некоторое значение NaN, используйте специальные средства, определяемые на уровне типа:статические методы Float.isNaN(float) и Double.isNaN(Double).Две ссылки на объект всегда могут проверяться на равенство.
Выражение ref1==ref2 равно true, если обе ссылки указывают на один и тот жеобъект или обе они равны null, даже если ссылки относятся к различным объявленным типам. В противном случае возвращается false.С объектами String операторы равенства работают не так, как можно было бы ожидать. Для заданных объектов str1 и str2, относящихся к типуString, выражение str1==str2 проверяет, указывают ли эти две ссылки на один и тот же объект String. Оно не проверяет, совпадает ли содержимоеэтих строк.
Равенство содержимого определяется методом String.equals, описанным в главе 8.5.18. Поразрядные операцииСуществуют следующие бинарные поразрядные операции:& поразрядное И| поразрядное включающее ИЛИ^ поразрядное исключающее ИЛИ (XOR)Кроме того, имеется унарный оператор дополнения ~, который изменяет состояние каждого бита операнда на противоположное. Дополнениецелого значения 0x00003333 равняется 0xffffcccc.Другие операторы, работающие с операндами на уровне битов, осуществляют сдвиг битов в целых значениях. Это следующие операторы:<< сдвиг влево с заполнением правых битов нулями>> сдвиг вправо с заполнением левых битов содержимымстаршего (знакового) бита>>>> > сдвиг вправо с заполнением левых битов нулямиВ левой части оператора сдвига указывается сдвигаемое значение, а в правой — количество разрядов. Например, var>>>2 сдвигает битыпеременной var на два разряда вправо и заполняет два старших бита нулями.Правила типов для операторов сдвига несколько отличаются от тех, что применяются к прочим бинарным операторам.
Тип результатаоператора сдвига совпадает с типом левого операнда — то есть сдвигаемого значения. Если в левой части оператора сдвига стоит величина типаint, то результат сдвига также будет иметь тип int, даже если количество сдвигаемых разрядов было представлено в виде значения типа long.Если количество разрядов сдвига превышает количество бит в слове или если оно окажется отрицательным, то фактическое количестворазрядов сдвига будет отличаться от заданного. Оно будет представлять собой заданное количество с применением маски, равной размеру типаза вычетом единицы. Например, для 32-разрядного значения типа int используется маска 0x1f (31), так что выражения n<<35 и n<<-29 будутэквивалентны n<<3.Поразрядные операторы могут также использоваться с логическими значениями.
& и | возвращают те же значения, что и их логические аналоги&& и ||, с одним важным отличием: в поразрядных операторах всегда вычисляются оба операнда, тогда как в логических операторах обаоперанда вычисляются лишь в случае необходимости.Поразрядный оператор ^ возвращает значение true, если операнды различаются — лишь один из них равен true, но не оба сразу. ^предоставляет еще одну возможность для моделирования “логического исключающего ИЛИ”:if ((x << 0) ^ (y << 0))differentSign();elsesameSign();Поразрядные операторы могут применяться только для значений целого и логического типа, но не для значений с плавающей точкой илиссылок.
Операторы сдвига применяются только для целых типов. В тех редких случаях, когда вам понадобится манипулировать с битами впредставлении величины с плавающей точкой, можно воспользоваться методами преобразования для классов Float и Double, рассмотренными вразделе “Float и Double” на стр. .5.19. Условный операторУсловный оператор позволяет всего в одном выражении выбрать одно из двух значений на основании логической переменной. Приводимаяниже запись:value = (userSetIt ? usersValue : defaultValue);равнозначна следующей:if (userSetIt)value = usersValue;elsevalue = defaultValue;Главное отличие между операторами if и ?: заключается в том, что последний обладает собственным значением.
Условный операторобеспечивает более компактную запись, однако не все программисты соглашаются с тем, что он лучше воспринимается читателем программы.Мы пользуемся тем или иным вариантом в зависимости от обстоятельств. Использование скобок, окружающих выражения условного оператора,является вопросом личного вкуса, и на практике встречаются самые различные варианты.
Сам язык не требует присутствия скобок.Выражения-результаты (второе и третье) должны иметь тип, совместимый с операцией присваивания. Каждое из них должно быть таким, чтобыоно присваивалось другому без явного приведения типа. Тип результата условного оператора совпадает с более общим из типов двухвозможных результатов. Например, в оператореdouble scale = (halveit ? 1 : 0.5);результаты относятся к типам int (1) и float (0.5).
Значение типа int может быть присвоено переменной double, поэтому условный оператор такжеимеет тип double. Это правило сохраняется и для ссылок — если значение одного типа может присваиваться другому, то типом операции будетнаиболее общий (наименее расширяемый) из них. Если ни один из этих типов не может быть присвоен другому, то операция являетсянедопустимой.Условный оператор иногда называют или оператором “вопросительный знак/точка” из-за формы его записи, или “тернарным оператором”,поскольку это единственный тернарный (трех-операндный) оператор в языке Java.5.20. Операторы присваиванияПростой знак = является основной формой оператора присваивания. Java поддерживает много других разновидностей присваивания. Любойарифметический или бинарный поразрядный оператор может быть объединен с = для образования оператора присваивания.
Например:arr[where()] += 12;приводит к тому же результату, что иarr[where()] = arr[where()] + 12;за исключением того, что в первой записи выражение в левой части вычисляется всего один раз.Для заданной переменной var типа Type, значения expr и бинарного оператора op записьvar op= exprэквивалентна следующей:var = (Type)((var) op (expr))за исключением того, что значение var вычисляется всего один раз. Это означает, что запись op= допустима лишь в том случае, если оператор opможет быть использован для типов, участвующих в выражении.
Так, вы не сможете применить <<= с переменными типа double, потому чтооператор сдвига << не работает с double.Обратите внимание на использование скобок в приведенной выше записи. Выражениеa *= b + 1эквивалентноa = a * (b + 1)но неa=a*b+1Хотя a += 1 — то же самое, что и ++a, запись с использованием ++ счи- тается более наглядной, и потому ей отдается предпочтение.5.21.
Имена пакетовИмя пакета представляет собой последовательность идентификаторов, разделяемых точками (.). В течение некоторого времени текстовыередакторы с поддержкой Unicode еще будут оставаться редкостью, так что в именах пакетов, предназначенных для широкого распространения,стоит ограничиваться ASCII-символами.Упражнение 5.2На основании того, что вы узнали в этой главе (но без написания программ на Java!), определите, какие из приведенных ниже выраженийявляются неверными, а также укажите тип и значение верных выражений:3 <<<< 2L -1(3L <<<< 2) -110 << 12 == 6 >> 1710 <<<< 12 == 6 >>>> 1713.5e-1 % Float.POSITIVE_INFINITYFloat.POSITIVE_INFINITY + Double.POSITIVE_INFINITYDouble.POSITIVE_INFINITY + Float.POSITIVE_INFINITY0.0 / -0.0 == -0.0 / 0.0Integer.MAX_VALUE + Integer.MIN_VALUELong.MAX_VALUE + 5;(short)5 * (byte)10(i << 15 ? 1.72e3f : 0)i++ + i++ + --i// исходное значение i = 3Содержание | Далее© 1997-2002 Издательский дом "Питер".
Авторские права охраняются.Предназначено только для частного использования!Воспроизведение материалов или частей данной книги в любом виде без письменного разрешения Издательского дома "Питер" запрещено!Приложение АРодные методыИх прозвали “чудо-рабочими”, когда один из них поинтересовался, каким гаечным ключом нужно забивать шуруп в стенуДжордж Браун, конгрессмен, Сан-Бернардино, Калифорния.Иногда возникают ситуации, когда приложение или библиотека не могут быть написаны исключительно на языке Java, и тогда приходитсясоздавать код на другом языке, который, вероятно, более точно учитывает специфику используемой платформы. Обычно потребность в этомвозникает в следующих случаях:Уже имеется большой объем работающего программного кода. Проще написать “прокладку” для этого кода на Java, чем переписыватьего заново.Приложение должно пользоваться системными средствами, отсутствующими в классах Java.Среда Java не обладает достаточным быстродействием для приложений, критичных по времени, и реализация их на другом языке можетоказаться более эффективной.●●●Чтобы помочь программисту в подобных ситуациях, Java позволяет реализовывать родные (native) методы на каком-либо из локальных (родных)языков программирования, обычно C или C++.
Родные методы объявляются следующим образом:public native void unlock() throws IOException;Ключевое слово native представляет собой еще один модификатор для объявляемого метода. Родные методы реализуются на родных языках,поэтому для них не существует программного кода на Java. Тем не менее, они вызываются из Java-программ, как и любые другие методы.Класс, содержащий родной метод, в соответствии с требованиями безопасности, не может загружаться по сети и выполняться. Болееконкретно — классы с родными методами не могут использоваться в аплетах<$Iаплет>. Даже если вопросы безопасности вас не интересуют,родной код не дает тех гарантий переносимости, которые предоставляет Java. Любой код на Java, использующий родные методы, долженотдельно переноситься на каждую целевую платформу.И все же родные методы могут приносить пользу, особенно если вы будете полагаться на общедоступные библиотеки.