2017-12-29 45 views
0

Sagen wir, ich habe ein statisches Array und ich möchte hinzufügen, einige weitere Werte in einer untergeordneten Klasse. Da PHP keinen statischen Konstruktor hat, weiß ich wirklich nicht, wie ich das sauber erreichen kann (ich möchte definitiv nichts unter der Klassendefinition hinzufügen und kann den Autoloader nicht ändern)So erweitern statisch vererbte Array in PHP-Klasse

Dies ist Was ich erreichen möchte (funktioniert offensichtlich nicht)

class Parent{ 
    public static $meta = [1,2,3]; 
} 

class Child extends Parent{ 
    public static $meta = array_merge(parent::$meta,[4,5]); 

} 
+0

Ich würde Ihnen empfehlen, Singleton-Klasse zu erstellen, die statische Informationen zwischen den gewünschten Klassen teilen würde. – Andy

Antwort

1

Sie definieren ein Attribut in Ihrer untergeordneten Klasse neu, das nicht empfohlen wird. Sie können überprüfen here Alternativen

Darüber hinaus ist Parent kein zulässiger Name für eine Klasse. Eine Lösung wäre, eine statische Methode zu implementieren, die die Eigenschaft zurückgibt. Wie dies

class ParentClass{ 
    public static $meta = [1,2,3]; 

    public static function getMeta() { 
     return self::$meta; 
    } 
} 

class Child extends ParentClass{ 
    public static function getMeta() { 
     return array_merge(parent::getMeta(),[4,5]); 
    } 
} 

var_dump(Child::getMeta()); 

Ergebnis

array(5) { 
    [0]=> 
    int(1) 
    [1]=> 
    int(2) 
    [2]=> 
    int(3) 
    [3]=> 
    int(4) 
    [4]=> 
    int(5) 
} 

ist können Sie diese hier leben überprüfen: https://3v4l.org/v8Mtm

Hope this Hilfe.

1

Was Sie wollen, ist nicht möglich mit Vars innerhalb Klassen. Stattdessen würde ich vorschlagen, den Zugriff auf die Variable über eine Getter-Methode bereitzustellen. Darüber hinaus würde ich vorschlagen, die statische var zu schützen, um unerwünschten Zugriff von außen zu verhindern.

Mit der späten statischen Bindung können Sie eine statische Funktion in der übergeordneten Klasse bereitstellen, die die eigene Variable mit den Variablen der geerbten Klasse zusammenführt.

class A { 
    protected static $meta = [1,2,3]; 

    public static function getMeta() { 
     if (__CLASS__ == static::class) { 
      return self::$meta; 
     } 
     return array_merge(self::$meta, static::$meta); 
    } 
} 

class B extends A { 
    protected static $meta = [4,5]; 
} 

var_dump(B::getMeta()); 

Der Vergleich von __CLASS__ == static::class ist nur für dieses Beispiel benötigt - wenn Sie mit assiciative Arrays gehen und wollen einfach nur neue Optionen anhängen, können Sie dies einfach ignorieren könnte und eine einfache return self::$meta + static::$meta;

Beachten Sie verwenden, Dies funktioniert nur für eine Vererbung auf einer Ebene. Wenn Sie eine Kaskade von neuen $ meta vars in den untergeordneten Klassen benötigen, haben Sie die getMeta-Methode auch in den untergeordneten Klassen überschrieben.

+0

Aber das Aufrufen von A :: getMeta() würde [1,2,3,1,2,3] zurückgeben, was ein merkwürdiges Verhalten ist. – Unex

+1

@Unex Ihr Recht ... hat es behoben – Philipp

0

Die einzige Möglichkeit, die ich mir vorstellen kann, dies zu tun (ohne einen Konstruktor zu verwenden oder der Klassendefinition hinzuzufügen), ist, define costs so zu verwenden;

/* FOO CLASS FILE */ 
define('FOO_META', [1, 2, 3]); 

class Foo{ 
    public static $meta = FOO_META; 
} 

/* BAR CLASS FILE */ 
define('BAR_META', array_merge(FOO_META, [4, 5, 6])); 

class Bar extends Foo{ 
    public static $meta = BAR_META; 
} 

echo 'Foo-Meta = ' . implode(', ', Foo::$meta) . '<br>'; 
echo 'Bar-Meta = ' . implode(', ', Bar::$meta) . '<br>'; 

Klasse Eigenschaften können nur const Werte innerhalb der Klassendefinition zugeordnet werden. Sie müssen einen Konstruktor (oder eine andere Methode) verwenden, um dies dynamisch auszuführen. Wenn Sie die obige Methode verwenden, würde ich mit Namespaces wie so empfehlen:

define('foo\META', [1, 2, 3]); 
define('bar\META', array_merge(foo\META, [4, 5, 6])); 

EDIT: wenn diese Klassen nur dieses eine Eigenschaft bestehen, warum nicht nur die definiert für sich nutzen? Sie sind im Wesentlichen das Gleiche ohne den zusätzlichen Aufwand.