Czy PHP może utworzyć instancję obiektu z nazwy klasy w postaci ciągu?

83

Czy w PHP można utworzyć instancję obiektu na podstawie nazwy klasy, jeśli nazwa klasy jest przechowywana w ciągu?

user135295
źródło

Odpowiedzi:

139

Tak, zdecydowanie.

$className = 'MyClass';
$object = new $className; 
brianreavis
źródło
7
Super, powinienem to przetestować, zanim zapytam hehe. Dzięki!
user135295
2
@user - też dobrze. Zastanawiam się, dlaczego trafiłem do SO bezpośrednio, zamiast robić absolutne minimum? lol
Ben
2
W rzeczywistości nie jest to takie oczywiste. Wiem, że w Javie jest to coś, co nazywa się odbiciem, ale w porównaniu z tym jest to bardzo proste.
Bartis Áron
4
Jeśli clsss znajduje się w przestrzeni nazw, użyj $ class = 'PrintData \\'. $ class; return new $ class ();
Dariux
2
Ponadto, jak stwierdza dokument PHP, jeśli klasa, której chcesz utworzyć instancję, znajduje się w przestrzeni nazw, musisz określić FQN (w pełni kwalifikowaną nazwę). Na przykład ja sam byłem w przestrzeni nazw „App \ Http \ Controllers” i miałem ciąg $ string = 'App \ Models \ Task'; Pomyślałem, że jeśli spróbuję utworzyć instancję łańcucha, zepsuje się, ale w rzeczywistości nie musisz dodawać znaku \ na początku.
Matt Kieran,
6

Tak to jest :

<?php

$type = 'cc';
$obj = new $type; // outputs "hi!"

class cc {
    function __construct() {
        echo 'hi!';
    }
}

?>
Pan Smith
źródło
5

jeśli twoja klasa potrzebuje argumentów , powinieneś to zrobić:

class Foo 
{
   public function __construct($bar)
   {
      echo $bar; 
   }
}

$name = 'Foo';
$args = 'bar';
$ref = new ReflectionClass($name);
$obj = $ref->newInstanceArgs(array($args));
josef
źródło
3

Statyczne też:

$class = 'foo';
return $class::getId();
Andrew Atkinson
źródło
To nie daje odpowiedzi na pytanie. Aby skrytykować lub poprosić autora o wyjaśnienie, zostaw komentarz pod jego postem. - Z recenzji
Blackbam,
@Blackbam odpowiednia powiązana dodatkowa odpowiedź. Prosimy o komentarz tylko wtedy, gdy jest to przydatne.
Andrew Atkinson
To prawda, że ​​w zasadzie działa i tak małe wyjaśnienie Twojej odpowiedzi byłoby miłe. Pytanie brzmiało „czy PHP może utworzyć instancję obiektu”, ale dostęp do statycznej funkcji składowej nie jest dostępem do obiektu.
Blackbam,
0

Możesz wykonać dynamiczne wywołanie, przechowując nazwy / metody klas w magazynie, takim jak baza danych. Zakładając, że klasa jest odporna na błędy.

sample table my_table
    classNameCol |  methodNameCol | dynamic_sql
    class1 | method1 |  'select * tablex where .... '
    class1 | method2  |  'select * complex_query where .... '
    class2 | method1  |  empty use default implementation

etc .. Następnie w kodzie używając ciągów zwracanych przez bazę danych dla nazw klas i metod. możesz nawet przechowywać zapytania sql dla swoich klas, poziom automatyzacji zależy od twojej wyobraźni.

$myRecordSet  = $wpdb->get_results('select * from my my_table')

if ($myRecordSet) {
 foreach ($myRecordSet   as $currentRecord) {
   $obj =  new $currentRecord->classNameCol;
   $obj->sql_txt = $currentRecord->dynamic_sql;
   $obj->{currentRecord->methodNameCol}();
}
}

Używam tej metody do tworzenia usług internetowych REST.

Hugo R.
źródło
1
A jeśli uda mi się wstrzyknąć do Twojej bazy danych dowolną liczbę klas i metod, to mam całe Twoje pozostałe API… Brawo! NIE używaj tego kodu, jest to bardzo niebezpieczne!
James Kipling,