Achtergrond:
In Perl kan de reikwijdte van variabelen worden beperkt via de operators my (lexicale zichtbaarheid) en local (dynamische tijdelijke toewijzing). local wordt veel gebruikt voor het overschrijven van globale variabelen en speciale descriptors (zoals $_, $/, $@, %ENV).
Probleem:
Het voornaamste probleem is de verwarring tussen dynamische en lexicale scope. local creëert geen nieuwe variabele, maar vervangt tijdelijk de waarde in een globale (of package) variabele binnen de uitvoering van een blok. Dit is bijzonder kritisch bij het herschrijven van variabelen zoals $/ (regelscheiding), $_ (standaardvariabele), $^W (waarschuwingsvlag), %ENV, STDIN/STDOUT.
Oplossing:
Voorbeeld code:
our $Global = "Hello!"; sub change1 { my $Global = "Bye!"; print "$Global "; } sub change2 { local $Global = "Bye!"; print "$Global "; } print "$Global "; # Hello! change1(); # Bye! print "$Global "; # Hello! change2(); # Bye! print "$Global "; # Hello!
Belangrijkste kenmerken:
Kan local worden toegepast op lexicale variabelen, gedeclareerd met my?
Nee, local werkt alleen met package-g globale variabelen. Het heeft geen invloed op my-objecten.
Wat gebeurt er als local wordt toegepast op speciale descriptors, zoals STDIN?
Je kunt tijdelijk STDIN/STDOUT/stdin toewijzen via local, bijvoorbeeld om de invoer-/uitvoerstream in een subroutine te vervormen zonder globaal effect. Na het verlaten van het blok zal de handle worden hersteld.
Wat is het kritieke verschil tussen local en my bij recursieve functieaanroepen?
local zorgt voor een "push/pop" stack van waarden — elke aanroep vervangt tijdelijk de waarde van het pakket, en geneste aanroepen ontvangen deze vervangende waarde. my biedt een enkele lexicale waarde binnen het blok zonder overerving naar binnen.
In een test wordt local gebruikt om %ENV te vervormen, na het verlaten van het blok onverwachte neveneffecten in andere threads, omdat de code multi-threaded is en local niet op de juiste manier wordt toegepast.
Voordelen:
Nadelen:
Ze vervangen speciale variabelen ($/, $@, $SIG) alleen voor de duur van het aanroepen van het benodigde blok, waarna de wijzigingen correct worden teruggedraaid.
Voordelen:
Nadelen: