Search     or:     and:
 LINUX 
 Language 
 Kernel 
 Package 
 Book 
 Test 
 OS 
 Forum 
 iakovlev.org 
 Languages
 С
 GNU С Library 
 Qt 
 STL 
 Threads 
 C++ 
 Samples 
 stanford.edu 
 ANSI C
 Libs
 LD
 Socket
 Pusher
 Pipes
 Encryption
 Plugin
 Inter-Process
 Errors
 Deep C Secrets
 C + UNIX
 Linked Lists / Trees
 Asm
 Perl
 Python
 Shell
 Erlang
 Go
 Rust
 Алгоритмы
NEWS
Последние статьи :
  Тренажёр 16.01   
  Эльбрус 05.12   
  Алгоритмы 12.04   
  Rust 07.11   
  Go 25.12   
  EXT4 10.11   
  FS benchmark 15.09   
  Сетунь 23.07   
  Trees 25.06   
  Apache 03.02   
 
TOP 20
 Secure Programming for Li...6507 
 Linux Kernel 2.6...5279 
 Trees...1119 
 Максвелл 3...1051 
 William Gropp...990 
 Go Web ...963 
 Ethreal 3...930 
 Ethreal 4...917 
 Gary V.Vaughan-> Libtool...914 
 Ext4 FS...905 
 Rodriguez 6...900 
 Clickhouse...900 
 Ethreal 1...897 
 Steve Pate 1...886 
 C++ Patterns 3...864 
 Assembler...854 
 Ulrich Drepper...844 
 DevFS...788 
 MySQL & PosgreSQL...774 
 Стивенс 9...758 
 
  01.01.2024 : 3621733 посещений 

iakovlev.org
 

Пакеты и модули

Область имен - namespace - часть памяти программы со своей собственной областью видимости. Видимость переменных ограничена данным модулем .Модуль - пакет , который можно загружать и интегрировать с данной программой . В пакет может входить как один , так и несколько файлов-исходников . В следующем примере создается пакет, сохраняемый как файл package1.pl: package package1; BEGIN { } sub subroutine1 {print "Hello!\n";} return 1; END { } Чтобы использовать в программе код пакета, надо поместить в сценарий команду require: require 'package1.pl'; Теперь можно ссылаться на идентификаторы пакета package1, отделив его имя от идентификатора символами ::. require 'package1.pl'; package1::subroutine1(); print $package1::variable1; Hello! 1 Для того , чтобы не использовать префикс package1:: , нужно использовать модули . Модуль - пакет , оформленный в виде отдельного файла с расширением .pm. Модуль может содержать глобальные переменные . Создадим модуль Module1 package Module1; BEGIN { use Exporter (); @ISA = 'Exporter'; @EXPORT = '&subroutine1'; } sub subroutine1 {print "Hello!\n";} return 1; END { } Вызвать модуль можно так : use Module1; subroutine1(); Hello! Использование команды require отличается тем , что подключение модуля происходит в момент вызова , в то время как команда use подключает модуль на этапе компиляции . Имя текущего пакета можно определить с помощью встроенного идентификатора __PACKAGE__. В следует примере имя текущего пакета выводится из подпрограммы subroutine1, входящей в пакет package1: package package1; BEGIN {} sub subroutine1 { print __PACKAGE__; } return 1; END {} Если код пакета расположен в 2-х разных файлах , можно использовать команду require несколько раз : require 'file1.pl'; require 'file2.pl'; А можно и не вызывать 2 раза , а сделать например так : package package1; BEGIN {require 'package2.pl';} sub hello {print "Hello!\n";} return 1; END {} В код модуля можно встроить документацию с помощью операторов =pod и =cut : =pod (Начало встроенной документации) =item myTest1 Тут пошел 1-й комментарий ... =item myTest2 Тут пошел 2-й комментарий ... =cut (Конец встроенной документации) Чтобы из модуля разрешить экспорт подпрограммы , но по молчанию ее не загружать , нужно использовать @EXPORT_OK : package Module1; BEGIN { use Exporter(); @ISA = qw(Exporter); @EXPORT_OK = qw(&subroutine1); } sub subroutine1 {print "Hello!\n";} return 1; END { } Для вызова этой подпрограммы можно экспортировать ее явно : # use Module1 qw{&subroutine1); Если вы не хотите, чтобы модуль экспортировал в область глобальных имен свои имена, описанные как экспортируемые по умолчанию, надо добавить пару круглых скобок после имени модуля, указанного в команде use: use Module1 (); Если вы не хотите, чтобы модуль экспортировал определенные имена, их надо перечислить во время работы с модулем Exporter в массиве @EXPORT_FAIL : package Uptime; BEGIN { use Exporter; @ISA = qw/Exporter/; if ($^O ne 'MSWin32') { @EXPORT = qw/&uptime/; } else { print "Sorry, no uptime available in Win32.\n"; @EXPORT_FAIL = qw/&uptime/; } } sub uptime {print `uptime`;} return 1; END { } Задать номер версии в коде модуля можно так : $VERSION = 1.00; Проверить версию модуля можно так : use Module1(); Module1->require_version(2.00); Если в программе вызывается несуществующая процедура из какого-то модуля , это можно обработать с помощью AUTOLOAD : package Autoload; BEGIN { use Exporter (); @ISA = qw(Exporter); @EXPORT = qw(&AUTOLOAD); } sub AUTOLOAD () { my $subroutine = $AUTOLOAD; $subroutine =~ s/.*:://; print "You called $subroutine with these arguments: ", join(", ", @_); } return 1; END { } Следующий фрагмент показывает , что произойдет , если вызвать несуществующую подпрограмму : use Autoload; printem (1, 2, 3); Вывод будет такой : You called printem with these arguments: 1, 2, 3 Для каждого модуля можно определить свою собственную AUTOLOAD . Для выборочной загрузки отдельных частей модуля существует стандартный модуль AutoLoader : Для этого в модуле перед подпрограммами нужно поместить ключевое слово __END__ , а затем из командной строки обработать исходный файл модуля командой perl -w -e 'use AutoSplit; autosplit("%1", "%2")' где первый параметр - имя модуля , второй - каталог , где будет записан результат . Исходный код будет разбит на отдельные файлы с расширением .al . Чтобы модуль мог использовать механизм автозагрузки файлов, созданных с помощью autosplit, его главая часть должна быть организована специальным образом. Примером может служить модуль POSIX, который разбивает свои многочисленные подпрограммы на отдельные файлы и загружает их только тогда, когда они действительно требуются пользователю: package POSIX; use AutoLoader; ...... sub AUTOLOAD { $AutoLoader::AUTOLOAD = $AUTOLOAD; goto &Autoloader::AUTOLOAD; }
Оставьте свой комментарий !

Ваше имя:
Комментарий:
Оба поля являются обязательными

 Автор  Комментарий к данной статье