Domanda

Ho del codice generato automaticamente che scrive in modo efficace quanto segue in diversi punti di un certo codice:

no warnings 'uninitialized';
local %ENV = %ENV;
local $/   = $/;
local @INC = @INC;
local %INC = %INC;
local 

Ho del codice generato automaticamente che scrive in modo efficace quanto segue in diversi punti di un certo codice:

<*>

Quando si genera automaticamente il codice, alcuni sostengono che non è strettamente necessario che il codice sia "bello", ma vorrei estrarlo in un sottoprogramma. Tuttavia, ciò localizzerebbe quelle variabili in quella subroutine. C'è un modo per localizzare quelle variabili nel frame dello stack chiamante?

Aggiorna : in modo simile, sarebbe bello poter eseguire eval in un frame stack superiore. Penso che Python abbia già questo. Sarebbe bello se lo facesse anche Perl.

=

Ho del codice generato automaticamente che scrive in modo efficace quanto segue in diversi punti di un certo codice:

<*>

Quando si genera automaticamente il codice, alcuni sostengono che non è strettamente necessario che il codice sia "bello", ma vorrei estrarlo in un sottoprogramma. Tuttavia, ciò localizzerebbe quelle variabili in quella subroutine. C'è un modo per localizzare quelle variabili nel frame dello stack chiamante?

Aggiorna : in modo simile, sarebbe bello poter eseguire eval in un frame stack superiore. Penso che Python abbia già questo. Sarebbe bello se lo facesse anche Perl.

; local $| = $|; local %SIG = %SIG; use warnings 'uninitialized';

Quando si genera automaticamente il codice, alcuni sostengono che non è strettamente necessario che il codice sia "bello", ma vorrei estrarlo in un sottoprogramma. Tuttavia, ciò localizzerebbe quelle variabili in quella subroutine. C'è un modo per localizzare quelle variabili nel frame dello stack chiamante?

Aggiorna : in modo simile, sarebbe bello poter eseguire eval in un frame stack superiore. Penso che Python abbia già questo. Sarebbe bello se lo facesse anche Perl.

È stato utile?

Soluzione

Forse puoi organizzare che il codice che utilizza quei locali sia generato come chiusura? Quindi potresti

sub run_with_env {
    my ($sub, @args) = @_;
    no warnings 'uninitialized';
    local %ENV = %ENV;
    local $/   = $/;
    local @INC = @INC;
    local %INC = %INC;
    local 

Forse puoi organizzare che il codice che utilizza quei locali sia generato come chiusura? Quindi potresti

<*> =

Forse puoi organizzare che il codice che utilizza quei locali sia generato come chiusura? Quindi potresti

<*>; local $| = $|; local %SIG = %SIG; use warnings 'uninitialized'; $sub->(@args); } run_with_env(sub { # do stuff here }); run_with_env(sub { # do different stuff here });

Altri suggerimenti

Non sono sicuro del motivo per cui QuantumPete è sottovalutato, sembra che abbia ragione su questo. Non puoi dire a local di inizializzare le variabili nel blocco chiamante. La sua funzionalità è speciale e l'inizializzazione / smontaggio funziona solo sul blocco in cui è stato eseguito.

Esistono alcuni moduli sperimentali come Sub :: Uplevel e Devel :: RunBlock che ti consente di provare a " ingannare " caller () per le subroutine o effettua un "salto in lungo" dei valori nei frame stack superiori (rispettivamente), ma nessuno di questi fa nulla per influenzare il modo in cui local tratta le variabili ( Ho provato. :)

Quindi per ora sembra davvero che dovrete convivere con le dichiarazioni locali nell'ambito in cui ne avete bisogno.

Non ho una grande familiarità con Perl, quindi perdonami se è possibile. Ma normalmente, le variabili locali a un frame dello stack sono disponibili solo all'interno di quel frame dello stack. Non è possibile accedervi da uno più alto o più basso (a meno che non si faccia qualche aritmetica puntatore confuso ma che non è mai garantito per avere successo). Purtroppo, grandi blocchi di dichiarazioni variabili sono qualcosa con cui dovrai convivere.

QuantumPete

perldoc perlguts dice:

   The "Alias" module implements localization of the basic types within
   the caller's scope.  People who are interested in how to localize
   things in the containing scope should take a look there too.

FWIW. Non ho guardato Alias.pm abbastanza da vicino per vedere quanto potrebbe essere facile.

In TCL puoi utilizzare uplevel . Per quanto riguarda Perl, non lo so.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top