Eines der ersten Dinge, die ich versuche, in einer unbekannten Programmiersprache zu lernen, ist, wie es Verschlüsse handhabt. Ihre Semantik ist oft damit verwoben, wie die Sprache Bereiche und verschiedene andere knifflige Bits behandelt, so dass sie mehrere andere Aspekte der Sprache erkennen lassen. Plus, Schließungen sind ein sehr mächtiges Konstrukt und oft auf die Menge an Boilerplate, die ich tippen muss. So war ich mit Perl Schließungen rumgespielt und ich stolperte über eine kleine Gotcha:
my @closures;
foreach (1..3) {
# create some closures
push @closures, sub { say "I will remember $_"; };
}
foreach (@closures) {
# call the closures to see what they remember
# the result is not obvious
&{$_}();
}
Wenn ich den obigen Code schrieb ich erwartete
I will remember 1
I will remember 2
I will remember 3
zu sehen, aber stattdessen habe ich I will remember CODE(0x986c1f0)
.
Das obige Experiment ergab, dass $_
sehr kontextabhängig ist und wenn es in einer Schließung erscheint, dann ist sein Wert nicht an dem Punkt der Erstellung der Schließung festgelegt. Es verhält sich eher wie eine Referenz. Welche anderen Probleme sollte ich beim Erstellen von Schließungen in Perl beachten?
Aber das ist so ziemlich das gleiche wie die Verwendung von 'foreach my $ num ...'. – davidk01
Also, wenn sie nur über lexikalische Variablen schließen, was passiert mit anderen Arten von Variablen? Verwendet der Abschluss den Wert, der während der Aufrufseite verfügbar ist, wie für '$ _'? – davidk01
@ davidk01: Wie in jeder anderen Programmiersprache, die globale Variablen erlaubt, schließen sich Schließungen über diese Variable wie normal. Sie haben nur vergessen, dass es global ist und sich daher ändern kann, wenn anderer Code seinen Wert auf etwas anderes setzt (wie beim anonymen Sub selbst, wenn es aufgerufen wird). – slebetman