请教一下use MY::MODULE的问题

请教一下use MY::MODULE的问题

先写一个模块
# Uninstallable.pm
package Uninstallable;
use Symbol qw(delete_package);
#use SelfLoader;
$message = "I'm here\n";

sub unimport {
delete_package(__PACKAGE__);
}
1;

脚本:

#!/usr/bin/perl
# uninstall.pl
use strict;
print "Now you see me: ";
use Uninstallable;
print $Uninstallable::message;
print "Now you don't!\n";

no Uninstallable;
print $Uninstallable::message;

为什么结果是
Now you see me: Now you don't!
而不是:
Now you see me: I'm here
Now you don't!



参考另一个脚本:

use integer;
$result = 4.2+2.3;
print $result,"\n";

no integer;

$result = 4.2+2.3;
print $result,"\n";

结果是:
6
6.5

一时弄不明白,请指教
因为 use/no 都是在 BEGIN BLOCK 里面执行的,而你的 print 是在 run-time 执行的。

另外参考 Symbol 对 delete_package 的描述。



QUOTE:
原帖由 MMMIX 于 2009-1-5 23:53 发表
因为 use/no 都是在 BEGIN BLOCK 里面执行的,而你的 print 是在 run-time 执行的。

另外参考 Symbol 对 delete_package 的描述。

但为什么
use integer;
$result = 4.2+2.3;
print $result,"\n";

no integer;

$result = 4.2+2.3;
print $result,"\n";

照理说这个use/no也是在BEGIN块里面执行的...那么no integer 应该会覆盖调use integer

另外,假设我的unimport函数不是delete_package,比如说是undef $message

结果也是一样的..





请指教


QUOTE:
原帖由 oi533 于 2009-1-6 11:12 发表



但为什么
use integer;
$result = 4.2+2.3;
print $result,"\n";

no integer;

$result = 4.2+2.3;
print $result,"\n";

照理说这个use/no也是在BEGIN块里面执行的...那么no integer 应该会覆 ...

显然是因为 integer 和 Symbol 起作用的机制不同,integer 是修改 Perl 一些 operator 的语意,而且这种修改的 scope 还是 limited to the enclosing block;而 Symbol 则是操作 symbol table,尤其是是 delete_package,则干脆是将整个 package 的 namespace 都给删除了,而一旦删除就真的没有了,自然也就没法用了。当然,Perl 实现的一些缓存机制估计也有影响,详见 Symbol 文档。
我的输出是

Now you see me: I am here.
Now you don't!
I am here.

跟你的输出不一样啊。