Spec-Zone.ru › Perl 5.28

постоянная

СОДЕРЖАНИЕ

  • ИМЯ
  • СИНОПСИС
  • ОПИСАНИЕ
  • ПРИМЕЧАНИЯ
    • Список констант
    • Определение нескольких констант сразу
    • Магические константы
  • ТЕХНИЧЕСКИЕ ПРИМЕЧАНИЯ
  • ОСОБЕННОСТИ
  • СМОТРИТЕ ТАКЖЕ
  • ОШИБКИ
  • АВТОРЫ
  • АВТОРСКИЕ ПРАВА И ЛИЦЕНЗИЯ

ИМЯ

constant - Perl-прагма для объявления констант

СИНОПСИС

use constant PI    => 4 * atan2(1, 1);
use constant DEBUG => 0;

print "Pi equals ", PI, "...\n" if DEBUG;

use constant {
    SEC   => 0,
    MIN   => 1,
    HOUR  => 2,
    MDAY  => 3,
    MON   => 4,
    YEAR  => 5,
    WDAY  => 6,
    YDAY  => 7,
    ISDST => 8,
};

use constant WEEKDAYS => qw(
    Sunday Monday Tuesday Wednesday Thursday Friday Saturday
);

print "Today is ", (WEEKDAYS)[ (localtime)[WDAY] ], ".\n";

ОПИСАНИЕ

Эта прагма позволяет объявлять константы во время компиляции.

Когда вы объявляете константу, например PI с помощью описанного выше метода, каждый компьютер, на котором работает ваш скрипт, может иметь столько значащих цифр точности, сколько может использовать. Кроме того, ваша программа будет легче читаться, скорее всего будет поддерживаться (и поддерживаться правильно) и с гораздо меньшей вероятностью отправит космический зонд на неправильную планету, потому что никто не заметил единственное уравнение, в котором вы написали 3.14195.

Когда константа используется в выражении, Perl заменяет её значением во время компиляции и может далее оптимизировать выражение. В частности, любой код в if (CONSTANT) блоке будет оптимизирован, если константа ложна.

ПРИМЕЧАНИЯ

Как и все use директивы, определение константы происходит во время компиляции. Следовательно, вероятно, некорректно размещать объявление константы внутри условного оператора (например, if ($foo) { use constant ... }).

Константы, определённые с помощью этого модуля, не могут быть интерполированы в строки как переменные. Однако конкатенация работает нормально:

print "Pi equals PI...\n";        # WRONG: does not expand "PI"
print "Pi equals ".PI."...\n";    # right

Даже если ссылка объявлена как константа, ссылка может указывать на данные, которые могут быть изменены, как показано в этом коде.

use constant ARRAY => [ 1,2,3,4 ];
print ARRAY->[1];
ARRAY->[1] = " be changed";
print ARRAY->[1];

Константы относятся к пакету, в котором они определены. Чтобы обратиться к константе, определённой в другом пакете, укажите полное имя пакета, как в Some::Package::CONSTANT. Модули могут экспортировать константы, и их также можно вызывать как методы класса или экземпляра, то есть как Some::Package->CONSTANT или как $obj->CONSTANT, где $obj — экземпляр Some::Package. Подклассы могут определять свои собственные константы, чтобы переопределять те, которые находятся в базовом классе.

Начиная с версии 1.32 этого модуля, константы можно определять в пакетах, отличных от вызывающего, включив имя пакета в имя константы:

use constant "OtherPackage::FWIBBLE" => 7865;
constant->import("Other::FWOBBLE",$value); # dynamically at run time

Использование заглавных букв для имён констант является просто соглашением, хотя рекомендуется, чтобы константы выделялись и предотвращались коллизии с другими именами, ключевыми словами и именами подпрограмм. Имена констант должны начинаться с буквы или нижнего подчёркивания. Имена, начинающиеся с двух нижних подчёркиваний, зарезервированы. Некоторые неудачные имена сгенерируют предупреждения, если предупреждения включены во время компиляции.

Список констант

Константы могут быть списками, содержащими более (или менее) одного значения. Константа без значений оценивается как undef в скалярном контексте. Обратите внимание, что константы с более чем одним значением не возвращают последнее значение в скалярном контексте, как можно было бы ожидать. В настоящее время они возвращают количество значений, но это может измениться в будущем. Не используйте константы с несколькими значениями в скалярном контексте.

ПРИМЕЧАНИЕ: Это подразумевает, что выражение, определяющее значение константы, оценивается в списочном контексте. Это может привести к неожиданным результатам:

use constant TIMESTAMP => localtime;                # WRONG!
use constant TIMESTAMP => scalar localtime;         # right

Первая строка выше определяет TIMESTAMP как список из 9 элементов, как возвращается localtime() в списочном контексте. Чтобы установить его в строку, возвращаемую localtime() в скалярном контексте, требуется явное ключевое слово scalar.

Список констант — это списки, а не массивы. Для индексирования или среза их необходимо заключить в скобки.

my @workdays = WEEKDAYS[1 .. 5];            # WRONG!
my @workdays = (WEEKDAYS)[1 .. 5];          # right

Определение нескольких констант сразу

Вместо написания нескольких use constant операторов, вы можете определить несколько констант в одном операторе, указав вместо имени константы ссылку на хеш, где ключи — имена констант, которые нужно определить. Очевидно, что все константы, определённые с помощью этого метода, должны иметь одно значение.

use constant {
    FOO => "A single value",
    BAR => "This", "won't", "work!",        # Error!
};

Это фундаментальное ограничение способа построения хешей в Perl. Сообщения об ошибках, возникающие в таких случаях, часто бывают довольно загадочными — в худшем случае их может вообще не быть, и вы обнаружите ошибку только позже.

При определении нескольких констант вы не можете использовать значения других констант, определённых в том же объявлении. Это связано с тем, что вызывающий пакет не знает о какой-либо константе внутри этой группы до после завершения use оператора.

use constant {
    BITMASK => 0xAFBAEBA8,
    NEGMASK => ~BITMASK,                    # Error!
};

Магические константы

Магические значения и ссылки могут быть преобразованы в константы во время компиляции, что позволяет создавать потрясающие вещи, такие как это. (Эти номера ошибок не полностью переносимы, к сожалению.)

use constant E2BIG => ($! = 7);
print   E2BIG, "\n";        # something like "Arg list too long"
print 0+E2BIG, "\n";        # "7"

Вы не можете получить связанную константу, передавая связанный скаляр в качестве значения. Однако ссылки на связанные переменные могут использоваться в качестве констант без каких-либо проблем.

ТЕХНИЧЕСКИЕ ПРИМЕЧАНИЯ

В текущей реализации скалярные константы фактически являются встраиваемыми подпрограммами. Начиная с версии 5.004 Perl, соответствующая скалярная константа вставляется непосредственно вместо некоторых вызовов подпрограмм, тем самым сохраняя накладные расходы на вызов подпрограммы. См. "Константные функции" в perlsub для получения подробной информации о том, как и когда это происходит.

В редких случаях, когда вам нужно определить во время выполнения, была ли определена конкретная константа с помощью этого модуля, вы можете использовать эту функцию для проверки хеша %constant::declared. Если имя заданной константы не содержит имени пакета, используется текущий пакет.

sub declared ($) {
    use constant 1.01;              # don't omit this!
    my $name = shift;
    $name =~ s/^::/main::/;
    my $pkg = caller;
    my $full_name = $name =~ /::/ ? $name : "${pkg}::$name";
    $constant::declared{$full_name};
}

ОСОБЕННОСТИ

Список констант не встраивается, если вы не используете Perl v5.20 или более поздние версии. В версиях 5.20 и выше они все еще не являются неизменяемыми, но это может измениться в будущих версиях.

В одном пакете не может быть подпрограммы или ключевого слова с тем же именем, что и константа. Вероятно, это хорошо.

Константа с именем в списке STDIN STDOUT STDERR ARGV ARGVOUT ENV INC SIG разрешена только в пакете main::, по техническим причинам.

В отличие от констант в некоторых языках, их нельзя переопределять в командной строке или через переменные окружения.

Вы можете столкнуться с проблемами, если используете константы в контексте, который автоматически приводит имена без квалификаторов к строкам (как это верно для любого вызова подпрограммы). Например, вы не можете сказать $hash{CONSTANT}, потому что CONSTANT будет интерпретироваться как строка. Используйте $hash{CONSTANT()} или $hash{+CONSTANT}, чтобы предотвратить включение механизма цитирования имён без квалификаторов. Аналогично, поскольку оператор => приводит имя без квалификаторов к строке, вы должны сказать CONSTANT() => 'value' (или просто использовать запятую вместо большого знака стрелки) вместо CONSTANT => 'value'.

СМОТРИТЕ ТАКЖЕ

Readonly - Средство создания неизменяемых скаляров, массивов, хешей.

Attribute::Constant - Делайте переменные только для чтения с помощью атрибута

Scalar::Readonly - Расширение Perl для SvREADONLY флага скаляров

Hash::Util - Подбор общих утилит для хешей (в основном для блокировки/разблокировки ключей и значений)

ОШИБКИ

Пожалуйста, сообщите об ошибках или запросах на новые функции через утилиту perlbug(1).

АВТОРЫ

Том Финикс, <rootbeer@redcat.com>, с помощью многих других людей.

Множественные объявления констант сразу добавлены Кэсси Уэстом, <casey@geeknest.com>.

Документация в основном переписана Ильмари Каронен, <perl@itz.pp.sci.fi>.

Эта программа поддерживается разработчиками Perl 5. Распространение CPAN поддерживается Себастьяном Апергисом-Трамони <sebastien@aperghis.net>.

АВТОРСКИЕ ПРАВА И ЛИЦЕНЗИЯ

Copyright (C) 1997, 1999 Том Финикс

Этот модуль является свободным программным обеспечением; вы можете перераспределять его или изменять его в соответствии с теми же условиями, что и Perl сам.

© 1993–2020 Larry Wall and others
Licensed under the GNU General Public License version 1 or later, or the Artistic License.
The Perl logo is a trademark of the Perl Foundation.
https://perldoc.perl.org/5.28.3/constant

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API