Date: Mon, 16 Dec 2002 13:17:52 +0500
From: Andrey Sapozhnikov <sapa@icb.chel.su>
Newsgroups: ftn.ru.perl
Subject: Экспорт глобальных переменных в Perl модулях
>>И у Вас и у предыдущего автора происходит экспорт _всего_ глоба, что
>>некорректно ибо никто этого не просил и могут быть побочные эффекты.
>>Представьте, что Вы подключаете два модуля, в одном есть sub xx, а
>>в другом $xx...
> Дело в том, что это не меняет ситуации. Рекомендую, тесту для,
> подключить POSIX (он много экспортит по-дефлоту), и добавить в Вашем
> примере печать @EXPORT. С интересом обнаружите, что туда попали все
> setuid'ы и прочее.
>
> Глоб на package - он и есть глоб. Выяснить, откуда в него попал символ
> - из собственного пространства имен или запихнуто из другого package -
> невозможно.
Еще как меняет. Вот пример экспорта отдельных символов
из A1 и A2 в main. А про экспорт импортированых символов я
уже писал. Hе любой импортированый символ можно отличить
от "родного" (хотя некоторые можно). Поэтом единственное
решение - импортировать сторонние символы _после_ того,
как построите список "своих".
==> A1.pm <==
package A1;
use base 'Exporter';
our @EXPORT=qw(&tt);
sub tt { print "tt calledn"; }
1;
==> A2.pm <==
package A2;
use base 'Exporter';
our @EXPORT=qw($tt);
our $tt=30;
1;
==> a.pl <==
#!/usr/bin/perl -w
use strict;
use A1;
use A2;
tt();
print "$ttn";
=== EOF ===
Результат выполнения:
$ ./a.pl
tt called
30
То же самое в обратной последовательности:
==> a.pl <==
#!/usr/bin/perl -w
use strict;
use A2;
use A1;
tt();
print "$ttn";
=== EOF ===
Тот же результат:
$ ./a.pl
tt called
30
А вот что будет если мы экспортируем глобы целиком:
==> A1.pm <==
package A1;
use base 'Exporter';
our @EXPORT=qw(*tt);
sub tt { print "tt calledn"; }
1;
==> A2.pm <==
package A2;
use base 'Exporter';
our @EXPORT=qw(*tt);
our $tt=30;
1;
==> a.pl <==
#!/usr/bin/perl -w
use strict;
use A1;
use A2;
tt();
print "$ttn";
=== EOF ===
Экспорт глоба *A2::tt из перетер уже экспортированый *A1::tt :
$ ./a.pl
Undefined subroutine &A2::tt called at ./a.pl line 5.
В обратной последовательности:
==> a.pl <==
#!/usr/bin/perl -w
use strict;
use A2;
use A1;
tt();
print "$ttn";
=== EOF ===
Здесь *A1::tt перетер уже экспортированый *A2::tt :
$ ./a.pl
tt called
Use of uninitialized value in concatenation (.) or string at ./a.pl line 6.