Closed p5pRT closed 20 years ago
our $a = "Outer"; { our $a = "Inner"; print "$a\n"; } print "$a\n";
$a is "Inner" in both places. If I understand how our() works\, its supposed to have the same scoping rules as my(). I would expect "Inner" and then "Outer"\, same as my().
Next\, our() doesn't appear to localize in a loop conditional:
our $a = "Outer"; for (our $a = 1; $a \< 2; $a++) { print "$a\n"; } print "$a\n";
$a is 3\, not "Outer" after the for loop. I presume the two bugs are related.
However\, this -does- work as expected.
our $a = "Outer"; for our $a (1\, 2) { print "$a\n"; } print "$a\n";
$a is 'Outer' after the for loop.
Summary of my perl5 (revision 5.0 version 5 subversion 63) configuration: Platform: osname=linux\, osvers=2.2.10\, archname=i686-linux uname='linux athens 2.2.10 #3 smp mon aug 2 16:48:09 edt 1999 i686 unknown ' config_args='' hint=previous\, useposix=true\, d_sigaction=define usethreads=undef useperlio=undef d_sfio=undef use64bits=undef usemultiplicity=undef Compiler: cc='cc'\, optimize='-g'\, gccversion=2.95.2 19991109 (Debian GNU/Linux) cppflags='-Dbool=char -DHAS_BOOL -DDEBUGGING -fno-strict-aliasing -I/usr/local/include -DDEBUGGING_OPS -DDEBUGGING_MSTATS' ccflags ='-Dbool=char -DHAS_BOOL -DDEBUGGING -fno-strict-aliasing -I/usr/local/include -DDEBUGGING_OPS -DDEBUGGING_MSTATS' stdchar='char'\, d_stdstdio=define\, usevfork=false intsize=4\, longsize=4\, ptrsize=4\, doublesize=8 d_longlong=define\, longlongsize=8\, d_longdbl=define\, longdblsize=12 alignbytes=4\, usemymalloc=y\, prototype=define Linker and Libraries: ld='cc'\, ldflags =' -L/usr/local/lib' libpth=/usr/local/lib /lib /usr/lib libs=-lnsl -lndbm -lgdbm -ldbm -ldb -ldl -lm -lc -lposix -lcrypt libc=/lib/libc-2.1.2.so\, so=so\, useshrplib=false\, libperl=libperl.a Dynamic Linking: dlsrc=dl_dlopen.xs\, dlext=so\, d_dlsymun=undef\, ccdlflags='-rdynamic' cccdlflags='-fpic'\, lddlflags='-shared -L/usr/local/lib'
Characteristics of this binary (from libperl): Compile-time options: DEBUGGING Built under linux Compiled at Jan 3 2000 05:17:35 @INC: /usr/local/perl5.005_63/lib/i686-linux /usr/local/perl5.005_63/lib /usr/local/perl5.005_63/lib/site_perl/i686-linux /usr/local/perl5.005_63/lib/site_perl .
--
Michael G Schwern schwern@pobox.com http://www.pobox.com/~schwern /(?:(?:(1)[.-]?)?\(?(\d{3})\)?[.-]?)?(\d{3})[.-]?(\d{4})(x\d+)?/i
On Mon\, 24 Jan 2000 00:01:21 EST\, Michael G Schwern wrote:
I've bumped into a few basic scoping problems with our():
our $a = "Outer"; { our $a = "Inner"; print "$a\n"; } print "$a\n";
$a is "Inner" in both places.
Of course it is; both $a's are aliases to the same global. our doesn't automatically local()ize. You need to explicitly spell that C\<local our $a = "Inner"> if that's what you want.
I think the "our" variable masks ... warning had better be extended to warn on this case.
Sarathy gsar@ActiveState.com
On Sun\, Jan 23\, 2000 at 09:38:42PM -0800\, Gurusamy Sarathy wrote:
Of course it is; both $a's are aliases to the same global. our doesn't automatically local()ize. You need to explicitly spell that C\<local our $a = "Inner"> if that's what you want.
Oh\, then the docs in perlfunc are a little confusing. I read:
An our declares the listed variables to be valid globals within the enclosing block\, file\, or eval. That is\, it has the same scoping rules as a "my" declaration\, but does not create a local variable.
as basically\, "it scopes just like a my() variable except you can refer to it as a fully qualified variable"
Okay\, so color me stupid\, but why is our()'s lexical scoping capabilities useful? Just for 'strict vars' reasons?
PS I just realized I've been using $a in my examples and tests\, I probably should be using something else.
--
Michael G Schwern schwern@pobox.com http://www.pobox.com/~schwern /(?:(?:(1)[.-]?)?\(?(\d{3})\)?[.-]?)?(\d{3})[.-]?(\d{4})(x\d+)?/i
Michael G Schwern wrote:
as basically\, "it scopes just like a my() variable except you can refer to it as a fully qualified variable"
Okay\, so color me stupid\, but why is our()'s lexical scoping capabilities useful? Just for 'strict vars' reasons?
I can't see any situation where this is actually /necessary/\, but as an advocate of minimal scoping of variables\, I have to approve :)
Consider a pair of functions that access the same data:
sub shove($) { our @stack; push @stack\, shift; }
sub prolapse() { our @stack; pop @stack }
A contrived example\, of course\, but until now this could only have been achieved either with a global (that would be visible throughout the module from its declaration) or a closure\, which is fine unless your code is running under mod_perl or a similar re-packaging mechanism...
Pete -- use Disclaimer::Standard; my $phone='+44 1793 564450'; # "THIS IS THE COMPATIBILITY my $fax='+44 1793 566918'; # POLICE. RESTORE YOUR ORIGINAL my $mobile='+44 7973 725120'; # TOKE.C AND BACK AWAY SLOWLY."
our() doesn't have any "local" component in it.
Consider:
# CASE 0: grant access to global during scope\, # but assign to it forever our $var = "fred";
is really like
# CASE 1: (same as previous) our $var; $var = "fred";
rather than like
# CASE 2: grant access to global during scope\, # and also assign it a new\, run-time value # for this block only our $var; local $var = "fred";
In other words\, the duration of a run-time assignment in a compiler-noted our() declaration on a global is itself permanent in effect and wholly unconcerned with blocks\, even though the "use-strict-legal" visibility conferred by the our() modifier is restricted to that lexical block.
You'd be wanting
local our $var = "fred";
if you're expecting both. (And yes\, it should be "our local" in English.)
--tom
An our declares the listed variables to be valid globals within the enclosing block\, file\, or eval\. That is\, it has the same scoping rules as a "my" declaration\, but does not create a local variable\.
as basically\, "it scopes just like a my() variable except you can refer to it as a fully qualified variable"
Okay\, so color me stupid\, but why is our()'s lexical scoping capabilities useful? Just for 'strict vars' reasons?
Because you're providing explicit access to a global variable.
if ($x \< 0) { our $count; $count++; }
if ($x > 0) { print "got $count\n"; # ERROR; $count not seen }
If it this aspect of my() which our() mimics--it's restricting access to the enclosing scope. You might also be wrongthinking by expecting our() to nest. They don't. There's only ever one our() variable. our() just says "ok to access global in this block". If another block says the same thing\, they're talking about the same global variable.
my() is completely different. It can nest. You can have more than one my() variable of the same name due to nesting\, and these are different variables\, with different addresses\, and with potentially different values. If another block says the same thing\, they're *not* talking about the same variable\, but two separate private variables of the same name.
my() variables "belong" to private and unique lexical scopes\, whereas our() variables "belong" to packages\, the home of global variables and universally accessible.
Perl => Meaning ----- ------- my => local our => global local => save
--tom
Pete Jordan writes: : Consider a pair of functions that access the same data: : : sub shove($) { : our @stack; : push @stack\, shift; : } : : sub prolapse() { : our @stack; : pop @stack : }
Or even:
sub shove($) { push our @stack\, shift } sub prolapse() { pop our @stack }
Of course\, that's not so different from
sub shove($) { push @MyPackage::stack\, shift } sub prolapse() { pop @MyPackage::stack }
but with C\
Larry
On Sun\, 23 Jan 2000 21:38:42 PST\, I wrote:
On Mon\, 24 Jan 2000 00:01:21 EST\, Michael G Schwern wrote:
I've bumped into a few basic scoping problems with our():
our $a = "Outer"; { our $a = "Inner"; print "$a\n"; } print "$a\n";
$a is "Inner" in both places.
Of course it is; both $a's are aliases to the same global. our doesn't automatically local()ize. You need to explicitly spell that C\<local our $a = "Inner"> if that's what you want.
I think the "our" variable masks ... warning had better be extended to warn on this case.
% ./perl -Ilib -Mdiagnostics -we 'our $foo; { our $foo; }'
"our" variable $foo redeclared at -e line 1 (#1)
(W) You seem to have already declared the same global once before in the
current lexical scope.
(Did you mean "local" instead of "our"?) (#2)
(W) Remember that "our" does not localize the declared global variable.
You have declared it again in the same lexical scope\, which seems superfluous.
Sarathy gsar@ActiveState.com
Migrated from rt.perl.org#2023 (status was 'resolved')
Searchable as RT2023$