RE: [OT] Dynamically changing current package
Probably just never assumed to be used this way. Do not see to much documentation on using the Symbol table directly. Here is something strange as well. Try copying a package and then creating an object from it . . . Really funky Think I might post this to the p5p list - #!/usr/bin/perl -w # ## ASSIGN TEST TO TEST2 *{ 'Test2::' } = *{ 'Test::' }; ## LETS CREATE SOME OBJECTS my $obj = Test->new; print 'TEST PACKAGE OBJECT : ', ref($obj), "\n\n"; my $obj2 = Test2->new; print 'TEST2 PACKAGE OBJECT : ', ref($obj2), "\n\n"; ## FYI print '- ' x 10, 'TEST', ' -' x 10, "\n"; print map { "$_ - $Test::{$_}\n" } keys %Test:: ; print '- ' x 10, 'TEST2', ' -' x 10, "\n"; print map { "$_ - $Test2::{$_}\n" } keys %Test:: ; BEGIN { package Test; sub new { my $class =shift; print "SETTING OBJECT TO CLASS : $class\n"; bless my $obj = {}, $class; } } --- > > > NewPackage will then contain all things in TestPackage > >> > >> Then you can redefined everything in TestPackage without affecting > >> anything in NewPackage. > > > >Actually it will, if you were to delete NewPackage, TestPackage would not > >contain anything. Modifying 'thingys' in TestPackage would modify > >NewPackage. > > Actually I investigated this a little more and discovered some > strange things... > > If you check out the results, copying the package at the package > level cause scalars to be redefined and subroutines to created as > references. Where as copying the the package at the glob level > caused the the subroutines to be redefined and the scalars to be > references... > > I wonder if this is a problem with perl? > > Robert Landrum > --- results --- > > # perl n.pl 1 > NewPackage::x was defined > NewPackage::june was defined > > $NewPackage::x was set to 100 > $Test::x now contains 100 > > Now Deleting Test package > Test::x was deleted from the STASH > Test::june was deleted from the STASH > > $NewPackage::x was set to 100 > $Test::x now contains 100 > > Now Listing NewPackage > NewPackage::x > NewPackage::june > > Now Listing Test > > # perl n.pl > NewPackage:: was defined as *{Test::} > > $NewPackage::x was set to 100 > $Test::x now contains 1 > > Now Deleting Test package > Test::x was deleted from the STASH > Test::june was deleted from the STASH > > $NewPackage::x was set to 100 > $Test::x now contains 1 > > Now Listing NewPackage > > Now Listing Test > > > > --- Contents of n.pl --- > #!/usr/bin/perl > package Test; > > our $x = 1; > sub june { > > } > > package main; > > if($ARGV[0]) { > for my $name (keys %{Test::}) { > *{"NewPackage::".$name} = *{"Test::".$name}; > print "NewPackage::".$name." was defined\n"; > } > print "\n"; > } else { > *{NewPackage::} = *{Test::}; > print "NewPackage:: was defined as \*{Test::}\n"; > print "\n"; > } > $NewPackage::x = 100; > > print "\$NewPackage::x was set to $NewPackage::x\n"; > print "\$Test::x now contains $Test::x\n"; > print "\n"; > print "Now Deleting Test package\n"; > for my $name (keys %{Test::}) { > delete $Test::{$name}; > print "Test::".$name." was deleted from the STASH\n"; > } > print "\n"; > > print "\$NewPackage::x was set to $NewPackage::x\n"; > print "\$Test::x now contains $Test::x\n"; > print "\n"; > print "Now Listing NewPackage\n"; > for my $name (keys %{NewPackage::}) { > print "NewPackage::".$name."\n"; > } > print "\n"; > print "Now Listing Test\n"; > for my $name (keys %{Test::}) { > print "Test::".$name."\n"; > } > print "\n"; >
RE: [OT] Dynamically changing current package
> > NewPackage will then contain all things in TestPackage >> >> Then you can redefined everything in TestPackage without affecting >> anything in NewPackage. > >Actually it will, if you were to delete NewPackage, TestPackage would not >contain anything. Modifying 'thingys' in TestPackage would modify >NewPackage. Actually I investigated this a little more and discovered some strange things... If you check out the results, copying the package at the package level cause scalars to be redefined and subroutines to created as references. Where as copying the the package at the glob level caused the the subroutines to be redefined and the scalars to be references... I wonder if this is a problem with perl? Robert Landrum --- results --- # perl n.pl 1 NewPackage::x was defined NewPackage::june was defined $NewPackage::x was set to 100 $Test::x now contains 100 Now Deleting Test package Test::x was deleted from the STASH Test::june was deleted from the STASH $NewPackage::x was set to 100 $Test::x now contains 100 Now Listing NewPackage NewPackage::x NewPackage::june Now Listing Test # perl n.pl NewPackage:: was defined as *{Test::} $NewPackage::x was set to 100 $Test::x now contains 1 Now Deleting Test package Test::x was deleted from the STASH Test::june was deleted from the STASH $NewPackage::x was set to 100 $Test::x now contains 1 Now Listing NewPackage Now Listing Test --- Contents of n.pl --- #!/usr/bin/perl package Test; our $x = 1; sub june { } package main; if($ARGV[0]) { for my $name (keys %{Test::}) { *{"NewPackage::".$name} = *{"Test::".$name}; print "NewPackage::".$name." was defined\n"; } print "\n"; } else { *{NewPackage::} = *{Test::}; print "NewPackage:: was defined as \*{Test::}\n"; print "\n"; } $NewPackage::x = 100; print "\$NewPackage::x was set to $NewPackage::x\n"; print "\$Test::x now contains $Test::x\n"; print "\n"; print "Now Deleting Test package\n"; for my $name (keys %{Test::}) { delete $Test::{$name}; print "Test::".$name." was deleted from the STASH\n"; } print "\n"; print "\$NewPackage::x was set to $NewPackage::x\n"; print "\$Test::x now contains $Test::x\n"; print "\n"; print "Now Listing NewPackage\n"; for my $name (keys %{NewPackage::}) { print "NewPackage::".$name."\n"; } print "\n"; print "Now Listing Test\n"; for my $name (keys %{Test::}) { print "Test::".$name."\n"; } print "\n";
RE: [OT] Dynamically changing current package
> NewPackage will then contain all things in TestPackage > > Then you can redefined everything in TestPackage without affecting > anything in NewPackage. Actually it will, if you were to delete NewPackage, TestPackage would not contain anything. Modifying 'thingys' in TestPackage would modify NewPackage.
RE: [OT] Dynamically changing current package
You can also change the package using globs. *{NewPackage::} = *{TestPackage::}; NewPackage will then contain all things in TestPackage Then you can redefined everything in TestPackage without affecting anything in NewPackage. You can also do something like for my $name (keys %{Test::}) { *{"NewPackage::".$name} = *{"Test::".$name} if($name =~ /somefunc/); } That's a poor mans export You can also load different modules based on developer if you force them to log in and create packages preceeded by their usernames $user = $r->connection->user; # right? $usrpkg = $user."::Foo::"; *{original::Foo::} = *{Foo::} unless(defined *{original::Foo::}); *{Foo::} = (defined *{$usrpkg}) ? *{$usrpkg} : *{original::Foo::}; # in case another user has already loader their stuff over top of Foo. That should make life interesting... I've never actually tried any of this, I'm just spitting out some ideas... Robert Landrum At 12:34 PM -0500 2/1/01, [EMAIL PROTECTED] wrote: > > Andrew Ho <[EMAIL PROTECTED]> wrote: >> I know how to use "package" in the normal case, where it's static. >> However, you can't say "package $foo" or even "eval 'package >> foo'" or even "BEGIN { eval 'package foo' }." I'm wondering >> if there's any way short of hacking the Perl source itself >> to make the compiler dynamically choose a namespace. > >The reason your eval examples don't work is because the scope of the package >declaration only extends to the end of the current block, the end of the >current file, or the end of the current 'eval', whichever comes first. > >If you want to put code into a particular package at runtime, you have to >recompile that code along with the package declaration: > >eval " >package $foo; >$scalar_containing_some_code >"; > >Or you can pull in the code from an external file: > >eval " >package $foo; >do '$script'; >"; > >The package declaration is scoped the way it is is because it is a >compile-time directive, not a run-time directive. Code is placed into a >particular package at compile-time; to change the package of a particular >piece of code at run-time really means to destroy that compiled code and to >recompile it in a new package. This is essentially what happens when you >use the string form of eval, above. > > >Michael
RE: [OT] Dynamically changing current package
> Andrew Ho <[EMAIL PROTECTED]> wrote: > I know how to use "package" in the normal case, where it's static. > However, you can't say "package $foo" or even "eval 'package > foo'" or even "BEGIN { eval 'package foo' }." I'm wondering > if there's any way short of hacking the Perl source itself > to make the compiler dynamically choose a namespace. The reason your eval examples don't work is because the scope of the package declaration only extends to the end of the current block, the end of the current file, or the end of the current 'eval', whichever comes first. If you want to put code into a particular package at runtime, you have to recompile that code along with the package declaration: eval " package $foo; $scalar_containing_some_code "; Or you can pull in the code from an external file: eval " package $foo; do '$script'; "; The package declaration is scoped the way it is is because it is a compile-time directive, not a run-time directive. Code is placed into a particular package at compile-time; to change the package of a particular piece of code at run-time really means to destroy that compiled code and to recompile it in a new package. This is essentially what happens when you use the string form of eval, above. Michael
Re: [OT] Dynamically changing current package
At 23:20 31/01/2001 -0800, Andrew Ho wrote: >AH>This isn't strictly a mod_perl question, but is there a good way in >AH>general Perl to dynamically change the current package name? > >GED>perldoc -f package > >I know how to use "package" in the normal case, where it's static. >However, you can't say "package $foo" or even "eval 'package foo'" or even >"BEGIN { eval 'package foo' }." I'm wondering if there's any way short of >hacking the Perl source itself to make the compiler dynamically choose a >namespace. I guess you could copy everything you have that you need in that package there (using aliases probably) and then goto &sub there (making the sub in that package think it was called by your caller) but I don't really see the point of that. Perhaps if you told us what is the problem that you think you can solve by switching your package we'd be able to suggest more appropriate solutions. -- robin b. "Chance is irrelevant. We will succeed." -- 7o9
Re: [OT] Dynamically changing current package
Hi Andrew, On Wed, 31 Jan 2001, Andrew Ho wrote: > This isn't strictly a mod_perl question, but is there a good way in > general Perl to dynamically change the current package name? perldoc -f package 73, Ged.
Re: [OT] Dynamically changing current package
Hello, AH>This isn't strictly a mod_perl question, but is there a good way in AH>general Perl to dynamically change the current package name? GED>perldoc -f package I know how to use "package" in the normal case, where it's static. However, you can't say "package $foo" or even "eval 'package foo'" or even "BEGIN { eval 'package foo' }." I'm wondering if there's any way short of hacking the Perl source itself to make the compiler dynamically choose a namespace. Humbly, Andrew -- Andrew Ho http://www.tellme.com/ [EMAIL PROTECTED] Engineer [EMAIL PROTECTED] Voice 650-930-9062 Tellme Networks, Inc. 1-800-555-TELLFax 650-930-9101 --