1 Replies - 2116 Views - Last Post: 07 May 2012 - 03:02 PM

#1 cupidvogel  Icon User is offline

  • D.I.C Addict

Reputation: 31
  • View blog
  • Posts: 593
  • Joined: 25-November 10

Using "use" doesn't import variables implicitly

Posted 06 May 2012 - 08:17 AM

Hi, I was under the impression that one difference between use and require is that the former enables one to use unqualified versions of the imported variables, while the latter requires fully qualified names. But look at my situation, I am running a code from C:\Perl\Codes under test.pl which contains this:

BEGIN {unshift @INC, "C:/"};
use Cards::need;
print "$w";



I have added a folder named Cards in C:\\ directory, inside which there is the module called need.pm. It contains this code:

package Cards::need;
our @b;
$w = 5;
@b = (1,2,3);



However when I run the test.pl file, nothing gets printed until I edit the 3rd line to be a fully qualified name like print $Cards::need::w. So why is the implicit import not working?

This post has been edited by cupidvogel: 06 May 2012 - 08:20 AM


Is This A Good Question/Topic? 0
  • +

Replies To: Using "use" doesn't import variables implicitly

#2 dsherohman  Icon User is offline

  • Perl Parson
  • member icon

Reputation: 226
  • View blog
  • Posts: 654
  • Joined: 29-March 09

Re: Using "use" doesn't import variables implicitly

Posted 07 May 2012 - 03:02 PM

View Postcupidvogel, on 06 May 2012 - 04:17 PM, said:

Hi, I was under the impression that one difference between use and require is that the former enables one to use unqualified versions of the imported variables, while the latter requires fully qualified names.


That's correct, to a very rough approximation... More accurately, use Foo; is equivalent to
BEGIN {
  require Foo;
  Foo->import;
}


This means there are two important differences between use and require:

1) use calls the import method of the used module, which will import any symbols which are exported by that module.

2) use is executed at compile time (because it effectively runs inside a BEGIN block), while require is executed at run time.

View Postcupidvogel, on 06 May 2012 - 04:17 PM, said:

BEGIN {unshift @INC, "C:/"};



FYI, you can simplify this a little by changing it to
use lib 'C:/';


View Postcupidvogel, on 06 May 2012 - 04:17 PM, said:

However when I run the test.pl file, nothing gets printed until I edit the 3rd line to be a fully qualified name like print $Cards::need::w. So why is the implicit import not working?


If you were to use strict; in test.pl it would print something... (Namely, it would print a refusal to compile because you're referencing a variable that doesn't exist. :D )

The reason that no implicit import takes place is contained in difference #1 above: need.pm doesn't export anything for test.pl to import. Take a look at the Exporter documentation for all the gory details, but, to make this specific case work, change need.pm to (untested, but should be correct):
package Cards::need;

use base 'Exporter';
BEGIN {
  our @EXPORT = qw( &$w &@b );
}

our $w = 5;
our @b = (1,2,3);



By making Cards::need a subclass of Exporter, you'll inherit its import method. This method will automatically import everything from the @EXPORT array into any package which calls it (and import is called implicitly when you use a module). In real code, you'd probably want to use @EXPORT_OK instead, which only imports symbols which are specifically requested by the calling module, but that would mean you'd need to change line 2 of test.pl to use Cards::need qw( $w ); for it to work.
Was This Post Helpful? 0
  • +
  • -

Page 1 of 1