Chinaunix首页 | 论坛 | 博客
  • 博客访问: 829576
  • 博文数量: 253
  • 博客积分: 6891
  • 博客等级: 准将
  • 技术积分: 2502
  • 用 户 组: 普通用户
  • 注册时间: 2010-11-03 11:01
文章分类

全部博文(253)

文章存档

2016年(4)

2013年(3)

2012年(32)

2011年(184)

2010年(30)

分类: Python/Ruby

2011-10-19 14:51:14

Perl finds modules by looking through the directories in the special Perl array, @INC. The use statement executes at compile time, so it looks at the module search path, @INC, at compile time.

For example, suppose we have our own directory under /home/gilligan/lib, and we place our own Navigation::SeatOfPants module in /home/gilligan/lib/Navigation/SeatOfPants.pm. When we load our module, Perl won't find it.

use Navigation::SeatOfPants;

You might think that we should just add our module directory to @INC before we call the use. However, even adding:

unshift @INC, '/home/gilligan/lib'; # broken use Navigation::SeatOfPants;

doesn't work. Why? Because the unshift happens at runtime, long after the use was attempted at compile time. The two statements are lexically adjacent but not temporally adjacent. Just because we wrote them next to each other doesn't mean they execute in that order. We want to change @INC before the use executes. One way to fix this is to add a BEGIN block around the push:

BEGIN { unshift @INC, '/home/gilligan/lib'; } use Navigation::SeatOfPants;

Now the BEGIN block compiles and executes at compile time, setting up the proper path for the following use.

the most common way to use is :

  1. use lib '/home/gilligan/lib';
  2. use Navigation::SeatOfPants;

Think of use lib as not "use this library" but rather "use this path to find my libraries (and modules)." Too often, we see code written like:

use lib '/home/gilligan/lib/Navigation/SeatOfPants.pm'; # WRONG

and then the programmer wonders why it didn't pull in the definitions. Be aware that use lib indeed runs at compile time, so this also doesn't work:

my $LIB_DIR = '/home/gilligan/lib'; ... use lib $LIB_DIR; # BROKEN use Navigation::SeatOfPants;

Certainly, Perl establishes the declaration of the $LIB_DIR variable at compile time (so we won't get an error with use strict, although the actual use lib should complain), but the actual assignment of the /home/gilligan/lib/ value doesn't happen until runtime. Oops, too late again!

At this point, we need to put something inside a BEGIN block or perhaps rely on yet another compile-time operation: setting a constant with use constant:

  1. use constant LIB_DIR => '/home/gilligan/lib';
  2. ...
  3. use lib LIB_DIR;
  4. use Navigation::SeatOfPants;

There. Fixed again. That is, until we need the library to depend on the result of a calculation. (Where will it all end? Somebody stop the madness!) This should handle about 99 percent of our needs.


阅读(923) | 评论(0) | 转发(0) |
0

上一篇:Slice: array and hash

下一篇:use Cwd use File::Spec

给主人留下些什么吧!~~