Ich bin anderer Meinung. Es stimmt, dass es oft nicht wichtig ist. Aber manchmal ist es sehr wichtig.
Die Schließung, die eine Referenz auf $this
hält, könnte das Garbage Collection dieses Objekts verhindern, was wiederum die Leistung signifikant beeinträchtigen könnte. Hier ist ein Beispiel, wo es wirklich einen großen Unterschied macht:
class LargeObject {
protected $array;
public function __construct() {
$this->array = array_fill(0, 2000, 17);
}
public function getItemProcessor(): Closure {
// Versuchen Sie es hier mit und ohne 'static'
return static function () {
// führen Sie eine Verarbeitung durch, die nichts mit $this zu tun hat
};
}
}
$start = microtime(true);
$processors = [];
for ($i = 0; $i < 2000; $i++) {
$lo = new LargeObject();
$processors[] = $lo->getItemProcessor();
}
$memory = memory_get_usage() >> 20;
$time = (microtime(true) - $start) * 1000;
printf("Das hat %dms gedauert und %dMB Speicher verbraucht\n", $time, $memory);
Hier ist die Ausgabe mit einer normalen Schließung:
Das hat 55ms gedauert und 134MB Speicher verbraucht
Hier ist die Ausgabe mit einer statischen Schließung:
Das hat 22ms gedauert und 1MB Speicher verbraucht
Ich habe dies mit PHP 7.3.19 auf Debian Buster getestet, also kann Ihre Erfahrung variieren. Offensichtlich ist dies ein speziell konstruiertes Beispiel, um den Unterschied zu demonstrieren. Aber solche Dinge können auch in echten Anwendungen passieren. Ich habe angefangen, Slevomats SlevomatCodingStandard.Functions.StaticClosure Sniff zu verwenden, um mich daran zu erinnern, immer statische Schließungen zu verwenden.