Anonymous Monk has asked for the wisdom of the Perl Monks concerning the following question:

Why is the following script (abc.pl) giving an error message stating that abc() is not accessible ? However the scripts runs perfectly fine when i put 'use B' followed by 'use A' ? Can anybody help ?????
abc.pl #!/usr/bin/perl use lib "."; use A; use B; def(); ######################################## A.pm package A; require Exporter; @ISA = qw(Exporter); @EXPORT = qw( abc ); use B; sub abc{ print "Inside sub abc of package A\n"; } ######################################## B.pm package B; require Exporter; @ISA = qw(Exporter); @EXPORT = qw( def ); use A; sub def{ print "Inside sub def of package B -> calling sub abc from package A\n +"; abc(); }

Replies are listed 'Best First'.
Re: loading modules using sub
by kennethk (Abbot) on Jun 24, 2010 at 18:38 UTC
    You have circular inheritance - A uses B uses A uses B... Perl resolves this by importing a module only once. In your case, this means that depending on the order of processing, abc() may or may not be exported before def() is defined.

    The solution is don't do this. Circular dependence can usually be replaced with simple inheritance with no loss of functionality. In this case, the 'solution' is to simply not have module A use B. More often, the easiest solution is abstracting the shared code into a common module 'C'.

    #!/usr/bin/perl use lib "."; use A; use B; def(); ######################################## A.pm package A; require Exporter; @ISA = qw(Exporter); @EXPORT = qw(abc); use C; ######################################## B.pm package B; require Exporter; @ISA = qw(Exporter); @EXPORT = qw(def); use C; sub def{ print "Inside sub def of package B -> calling sub abc from package + C\n"; abc(); } ######################################## C.pm package C; require Exporter; @ISA = qw(Exporter); @EXPORT = qw(abc); sub abc{ print "Inside sub abc of package A\n"; }
      Thanks kennethk, What i knew was 'use' puts the modules in compile-time, so i assumed how ever circular the 'use' call may be, at the point of execution, both the A.pm and B.pm are well resolved. Can you plese let me know how perl walks through the above script(abc.pl), and may fail in loading some functions. Wanted to have a clear picture of how perl compiles and executes.