ASPN ActiveState Programmer Network
ActiveState
/ Home / Perl / PHP / Python / Tcl / XSLT /
/ Safari / My ASPN /
Cookbooks | Documentation | Mailing Lists | Modules | News Feeds | Products | User Groups


Recent Messages
List Archives
About the List
List Leaders
Subscription Options

View Subscriptions
Help

View by Topic
ActiveState
.NET Framework
Open Source
Perl
PHP
Python
Tcl
Web Services
XML & XSLT

View by Category
Database
General
SOAP
System Administration
Tools
User Interfaces
Web Programming
XML Programming


MyASPN >> Mail Archive >> perl5-porters
perl5-porters
[patch pod/perlref.pod] (was Re: Ignorant wumpus? Or scoping problem?)
by Stas Bekman other posts by this author
Nov 28 2003 9:10AM messages near this date
Re: Ignorant wumpus? Or scoping problem? | Re: [patch pod/perlref.pod] (was Re: Ignorant wumpus? Or scoping problem?)
Dave, I took the liberty to add your explanation almost verbatim to perlref. 
You may want to polish it later, but I think it's pretty important to put that 
info in. And your explanation and the example were pretty clear to me. I 
mainly stressed that it's the string form of eval (it doesn't apply to eval {} )

Also I hope that I put it in the right place in perlref, as it explains 
closures in two places.

Here is the patch:

--- pod/perlref.pod.orig	2003-11-28 00:58:48.000000000 -0800
+++ pod/perlref.pod	2003-11-28 01:06:17.000000000 -0800
@@ -195,6 +195,51 @@
  continue to work as they have always worked.  Closure is not something
  that most Perl programmers need trouble themselves about to begin with.

+Note that lexical variables used inside the string form of C<eval()> 
+might not create a closure if not references elsewhere in the
+subroutine. This is because only when the string is eval'ed at
+run-time, can perl see that a variable is references from within the
+the eval'ed string. At compile time it's not known whether there is a
+lexical variable inside the string or not. For example:
+
+    {
+	my $x = 1;
+	sub f1 { print "f1: x=$x\n" }
+	sub f2 { eval 'print "f2: x=$x\n"' }
+    }
+
+    f1;
+    f2;
+
+produces the following output:
+
+  f1: x=1
+  Use of uninitialized value in concatenation (.) or string at (eval 1) line 1.
+  f2: x=
+
+What happens here is that when f1 is compiled, the compiler notices
+that the sub f1 makes mention of the outer lexical $x, so f1 gets its
+own private reference to that variable. When f2 is compiled, it has no
+such mention of $x, so it doesn't also capture $x.
+
+After the { } block is exited, the interpreter discards the current
+(and only) instance of $x. When f1 is later called, it still has its
+private copy of $x, and so can print out its value. When the eval is
+compiled via f2, f2 hasn't got a private copy of $x, so the eval tries
+to grab the value of the 'real' $x, which is now undef.
+
+In the current development version of perl, you get a warning when
+this happens:
+
+  f1: x=1
+  Variable "$x" is not available at (eval 1) line 1.
+  Use of uninitialized value in concatenation (.) or string at (eval 1) line 1.
+  f2: x=
+
+Therefore be careful when wanting to create a closure and using the
+string form of eval.
+
+
  =item 5.

  References are often returned by special subroutines called constructors.




__________________________________________________________________
Stas Bekman            JAm_pH ------>  Just Another mod_perl Hacker
http://stason.org/     mod_perl Guide --->  http://perl.apache.org
mailto:stas@[...].org http://use.perl.org http://apacheweek.com
http://modperlbook.org http://apache.org   http://ticketmaster.com
Thread:
Glenn Linderman
Dave Mitchell
Stas Bekman
Brad Baxter
Stas Bekman
Dave Mitchell
Stas Bekman
Glenn Linderman
Dave Mitchell
Glenn Linderman
Dave Mitchell
Glenn Linderman
Brad Baxter
Brad Baxter
Glenn Linderman
Dave Mitchell
Rafael Garcia-Suarez
Glenn Linderman
Stas Bekman
Glenn Linderman
Alan Burlison

Privacy Policy | Email Opt-out | Feedback | Syndication
© 2004 ActiveState, a division of Sophos All rights reserved