1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

【PHP/継承】クラス内のpublic変数宣言はコンストラクタより先に行われているのだった

Posted at

PHPのライブラリの継承ラッパーを作っていて認識違いでハマったのでメモ。

状況

例えばこんなライブラリがあり。
基本的にはライブラリ内のコードには手を出したくないので、ここには調整は入れませんが、
デフォルトで $hensuu という変数が存在(ここでは宣言のみ)しています。

Library.php
 class Library_sample {

  var $hensuu;

  public function test(){
   //なんやかんや
  }

}

で、それを継承するラッパークラスを作りました。

Hoge.php

class Hoge extends Library_sample{
	public $hensuu = true;
    public $hensuu2 = true;

	public function __construct()
	{
		parent::__construct();

	}

このラッパークラス「Hoge」で変数、$hensuuにtrueをセットしています。
ついでに$hensuu2も作り、こちらにもtrueをセットしています。

で、このラッパークラスのインスタンスを作り、そのインスタンスからhensuuを表示しようとすると、、、なぜかfalseとなっておりました。
でも、同じ場所でtrueを入れているhensuu2の方はtrueが出力されています。。

index.php

$hoge = new Hoge;
echo $hoge->hensuu;  // false
echo $hoge->hensuu2; // true

※各ファイルのincludeなどは省略しております。

これは一体。。?!

あれ?コンストラクタってインスタンス作る時に最初に実行されるから、ほんで継承してるから
「Hoge.php」のparent::__construct(); のところでまずは変数宣言→
その後に
hensuu = true;
hensuu2 = true;が行われたのでは。。。?としばらくはてながっていました。

結論:単純に順序逆だった

「Hoge.php」の中のpublic変数として先に宣言された後に、コンストラクタが実行されてたみたいです。
hennsuu1はtrueになり、コンストラクタの中で親クラスで改めて宣言されたことでただの変数=falseになった。
hennsuu2はtrueになり、コンストラクタの中で親クラスで、、、は特に宣言されていないのでそのまま変数=trueだった。
ということです。

ここ、勘違いしていました。

では

どうすべきかというと、子供のHoge.php側の「コンストラクタの中でtrueにするべき」でした。
という学びでした。
この辺の順序、思い込みをしていたのでどこでこの挙動になっているんだ?と少しコードを細かくおったりしてました。。w

1
0
5

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?