The following creates anonymous subroutines, then (in same statement) gives them a name by stuffing them in the symbol table. But once created, the method short-circuits any further AUTOLOAD invocation; the method is already built.
what I really need is enough optree-optimization fu to change the method-name in the caller code so that it can point to a name-munged method.
what I want to do is partly satisfied by $meth .= $line; but then the munged method, ex: auto_25(), wont be invoked by A::auto() called in main, and Im back to using AUTOLOAD as a dispatcher.
I have tried some lesser ways to achieve this, but no joy; code below attempts to put some context in arg-0, but is defeated by lack of CONSTANT-ness, a new {} is constructed each time, defeating a hash with munged method-names and a-sub refs.
if you run this, youll find the line# reported is same for each call (due to closure on $line). I could get new $line for each invocation, but that defeats a main goal of using the a-sub (efficiency; avoiding unneeded caller()s).#!/usr/local/bin/perl -w use strict; no strict 'refs'; package A; use Data::Dumper; use vars qw($AUTOLOAD); my %cache; sub AUTOLOAD { (my $meth = $AUTOLOAD) =~ s/.*:://; return if $meth eq 'DESTROY'; my ($package, $filename, $line, $subroutine) = caller(0); print "$meth called by: $package, $filename, $line, $subroutine\n" +; $cache{"$package, $filename, $line, $subroutine"} = $_[0]; $_[0]->{line} = $line; *{'A::'.$meth} = sub { print "invoking $meth from: $package, $filename, $line, $subroutin +e\n"; print "\twith ", Dumper (\@_); }; goto &{'A::'.$meth}; } package main; foreach (1..2) { # if hashref were CONSTANT, and not rebuilt for each invocation, # it could preserve the A::fancy({arb=>1},1); A::fancy({ok=>2},2); A::auto({}); A::auto({}); } use Data::Dumper; print Dumper (\%A::);
In reply to munging function names with AUTOLOAD by jimc
For: | Use: | ||
& | & | ||
< | < | ||
> | > | ||
[ | [ | ||
] | ] |