PHP 5.4 – chiusura $questo supporto’

Vedo che le nuove funzionalità previste per PHP 5.4 sono: tratti, matrice di dereferenziazione, un JsonSerializable interfaccia e qualcosa di cui all’come ‘closure $this support

http://en.wikipedia.org/wiki/Php#Release_history

Mentre gli altri sono immediatamente chiaro (JsonSerialiable, matrice di dereferenziazione) o ho guardato le specifiche (tratti), non sono sicuro di quello di chiusura $questo supporto’ è. Ho avuto successo googling per esso o trovando nulla a riguardo sul php.net

Qualcuno sa che cosa deve essere?

Se dovessi indovinare, vorrebbe dire qualcosa di simile a questo:

$a = 10; $b = 'strrrring';
//'old' way, PHP 5.3.x
$myClosure = function($x) use($a,$b)
             {
                 if (strlen($x) <= $a) return $x;
                 else return $b;
             };

//'new' way with closure $this for PHP 5.4
$myNewClosure = function($x) use($a as $lengthCap,$b as $alternative)
                 {
                     if(strlen($x) <=  $this->lengthCap)) return $x;
                     else 
                     {
                         $this->lengthCap++;  //lengthcap is incremented for next time around
                         return $this->alternative;
                     }
                 };

Il significato (anche se questo esempio è banale), che in passato, una volta che il tappo è stato costruito associato ‘usare’ le variabili sono fisse. Con chiusura $questo supporto’ sono più come membri si può pasticciare con.

Fa questo suono corretto e/o chiudere e/o ragionevole? Qualcuno sa cos’è questa “chiusura $questo supporto’ significa?

  • FWIW, 5.4 non è ancora il nome ufficiale di PHP tronco-è ancora internamente chiamato “5.3.99” e vi è una certa polemica se sarà davvero 5.4 o non (vs 6.0, che sarebbe poi essere messa in relazione con la grande Unicode riscrivere “6.0” ramo).
  • ahh bene sapere. grazie per il fissaggio tag
InformationsquelleAutor jon_darkstar | 2011-04-20



4 Replies
  1. 74

    Questo era già in programma per PHP 5.3, ma

    Per PHP 5.3 $questo supporto per le Chiusure è stato rimosso a causa di mancato accordo potrebbe essere raggiunto come implementare in un sano moda. Questo RFC descrive le possibili strade che possono essere intraprese per implementare nella prossima versione di PHP.

    Infatti, significa che è possibile fare riferimento all’istanza dell’oggetto (live demo)

    <?php
    class A {
      private $value = 1;
      public function getClosure() 
      {
        return function() { return $this->value; };
      }
    }
    
    $a = new A;
    $fn = $a->getClosure();
    echo $fn(); //1

    Per una discussione, vedere il PHP Wiki

    e di interesse storico:

    • oooh, stavo andando in toto la direzione sbagliata. significa “$questo’ essere l’istanza di Foo giusto? ho pensato ‘$questa’ come la chiusura stessa. sarebbe use essere ancora necessaria?
    • no, l’utilizzo di use non è ancora possibile. Non è possibile utilizzare $questo come lessicale variabile in qualsiasi versione di PHP per data. Ho aggiornato con l’esempio del Wiki e un link a un codepad che mostra i risultati con la corrente di PHP tronco.
    • grazie questo è grande. btw – il public $closure non fare nulla e distrae dal tuo punto, che si otherwies dimostrare molto bene
    • ho modificato che fuori, spero che tu non mente. i collegamenti sono ottimi btw, non ho mai veramente guardato quelle pagine wiki prima di
    • sì, grazie. felice se posso aiutare.
    • Penso che jon significava use nel caso generale–non è specifico per $this. Per quanto ne so, use saranno ancora necessarie per accedere alle variabili locali. Non vedo l’ora di far cadere il use ($self) trucco. 🙂
    • il problema circa l’uso($self) trucco è che funziona per metodi pubblici solo, quello di cui abbiamo davvero voluto è quello di essere in grado di accedere a tutti i soci, dopo tutto stiamo parlando di $questo… ci vorrà un po ‘ di tempo fino a che tutto inizia con l’utilizzo di php 5.4, alcuni server ancora utilizzare 5.2
    • Per chiarezza, con riferimento del RFC link (wiki.php.net/rfc/closures/object-extension) l’implementazione in PHP 5.4 un+ più simile approccio A, B, C o D? Sto assumendo A, tuttavia se ci sono avvertimenti che forniscono la dinamica di riassociazione comportamento prescritto da D, sarebbe fantastico.
    • Io non sono sicuro al 100% ma le persone più coinvolte con la decisione mi hanno detto di pensare è A.
    • Grazie @Gordon – Che è quello che ho pensato. Speriamo che il PHP docs sarà presto aggiornato per includere qualcosa di definitivo.
    • In realtà, $closure->bindTo($object); sembra svolgere il compito di riassociazione manualmente, e dovrebbe essere una fantastica aggiunta al PHP.

  2. 53

    Una cosa che Gordon perdere è ri-associazione di $this. Mentre quello che ha descritto è il comportamento di default, è possibile ri-legare.

    Esempio

    class A {
        public $foo = 'foo';
        private $bar = 'bar';
    
        public function getClosure() {
            return function ($prop) {
                return $this->$prop;
            };
        }
    }
    
    class B {
        public $foo = 'baz';
        private $bar = 'bazinga';
    }
    
    $a = new A();
    $f = $a->getClosure();
    var_dump($f('foo')); //prints foo
    var_dump($f('bar')); //works! prints bar
    
    $b = new B();
    $f2 = $f->bindTo($b);
    var_dump($f2('foo')); //prints baz
    var_dump($f2('bar')); //error
    
    $f3 = $f->bindTo($b, $b);
    var_dump($f3('bar')); //works! prints bazinga

    Chiusure bindTo metodo di istanza (in alternativa, utilizzare la statica Closure::bind) restituisce un nuovo chiusura con $this re-bound per il valore dato. Il campo è impostato passando al secondo argomento, questo determinerà la visibilità del privato e protetto membri, a cui si accede dall’interno della chiusura.

    • +1 per la descrizione del bindTo() funzionalità, che è una bella caratteristica importante.
  3. 22

    Edificio su @Gordon risposta è la possibilità di simulare alcuni hacky aspetti di chiusura-$questo, PHP 5.3.

    <?php
    class A
    {
        public $value = 12;
        public function getClosure()
        {
            $self = $this;
            return function() use($self)
            {
                return $self->value;
            };
        }
    }
    
    $a = new A;
    $fn = $a->getClosure();
    echo $fn(); //12
    • Sì, ma una differenza notevole è che non è possibile accedere a qualsiasi privato o protetto proprietà o metodi $self dall’interno la chiusura.
    • +1 haha, trovato questa risposta, un anno più tardi e ha risolto il mio problema. 😉
    • non si intende, non è possibile accedere private o protected variabile in PHP 5.3?
    • sì. Questa soluzione per la 5.3 funziona solo con le proprietà pubbliche.
    • Che cosa è una buona soluzione per aggirare il problema, allora?
    • Io non sono a conoscenza di qualsiasi soluzione per l’accesso ai non-pubblica di proprietà all’interno di chiusure in PHP 5.3. Miglior consiglio è quello di aggiornare alla versione 5.4 o successiva.

  4. 2

    Solo basandosi su altre risposte qui, credo che questo esempio mostrerà ciò che è possibile PHP 5.4+:

    <?php
    
    class Mailer {
        public    $publicVar    = 'Goodbye ';
        protected $protectedVar = 'Josie ';
        private   $privateVar   = 'I love CORNFLAKES';
    
        public function mail($t, $closure) {
            var_dump($t, $closure());
        }
    }
    
    class SendsMail {
        public    $publicVar    = 'Hello ';
        protected $protectedVar = 'Martin ';
        private   $privateVar   = 'I love EGGS';
    
        public function aMailingMethod() {
            $mailer = new Mailer();
            $mailer->mail(
                $this->publicVar . $this->protectedVar . $this->privateVar,
                function() {
                     return $this->publicVar . $this->protectedVar . $this->privateVar;
                }
            );
        }
    }
    
    $sendsMail = new SendsMail();
    $sendsMail->aMailingMethod();
    
    //prints:
    //string(24) "Hello Martin I love EGGS"
    //string(24) "Hello Martin I love EGGS"

    vedere: https://eval.in/private/3183e0949dd2db

Lascia un commento