2009-11-01 14 views
5

Mam klasę Logger, która między innymi ma metodę Log.
Jak Log jest najczęstszą użycie instancji Logger, mam przewodowy __invoke zadzwonić LogPHP Callable Object jako obiekt Członek

Inna klasa „Site” zawiera człon „log”, wystąpienie Logger.

dlaczego to praca:

$Log = $this->Log; 
$Log("Message"); 

Ale nie to:

$this->Log("Message"); 

Były powiedzie się z "PHP Fatal error: Zadzwoń do niezdefiniowanej metody Site :: log()"
Czy to ograniczenie realizacji obiektu wywoływalnego, czy też coś nie rozumiem?

Odpowiedz

1

samych powodów nie można to zrobić:

$value = $this->getArray()["key"];

lub nawet ten

$value = getArray()["key"];

Ponieważ składnia PHP nie zrobić krótką rękę bardzo dobrze.

+0

Głównie z powodu luźnego pisania. Nie można w żaden sposób zasugerować, co masz zamiar zrobić, więc domyślnie błędne jest wcześniej. –

+0

Napisałem dziwny preparser, który pozwala pisać takie wyrażenia: http://code.google.com/p/php-preparser/ :) (czy mogę "reklamować" tutaj moje rozwiązania open source?) –

+5

Ten przykład nie jest już istotny, ta składnia działa teraz. –

1

to może działać:

${this->Log}("Message"); 

Ale może to jest po prostu łatwiej i lepiej używać pełnego połączenia? Wydaje się, że nie ma sposobu, aby uzyskać to, co chcesz pracować w jednej linii.

Błąd w pytaniu wskazuje, że szuka funkcji zdefiniowanej w klasie, która nie istnieje. Obiekt, który można zarezerwować, nie jest funkcją i wygląda na to, że nie może być w tym przypadku traktowany jako jeden.

+0

nie będzie działał (przynajmniej nie dla mnie z php 5.3) »nieoczekiwany T_OBJECT_OPERATOR ...« – knittl

7

Niestety, jest to (nadal) ograniczenie PHP, ale ma sens, gdy się nad tym zastanowić, ponieważ klasa może zawierać właściwości i metody, które mają wspólne nazwy. Na przykład:

<?php 
class Test { 
    public $log; 

    public function __construct() { 
     $this->log = function() { 
      echo 'In Test::log property'; 
     }; 
    } 

    public function log() { 
     echo 'In Test::log() method'; 
    } 
} 

$test = new Test; 
$test->log(); // In Test::log() method 
call_user_func($test->log); // In Test::log property 
?> 

Jeśli PHP ma pozwolić na składnię, której pragniesz, która funkcja zostanie wywołana? Niestety, pozostawia nam tylko call_user_func[_array]() (lub kopiowanie $this->log do innej zmiennej i wywoływanie tego).

Jednakże, byłoby miło, gdyby była do przyjęcia następującej składni:

<?php 
{$test->log}(); 
?> 

Ale niestety, tak nie jest.

+0

To naprawdę dziwne dziwactwo. Coś w rodzaju ($ test-> log)() wydaje się głównie ograniczeniem parsera, a nie samego języka. –

Powiązane problemy