読者です 読者をやめる 読者になる 読者になる

肉とビールとパンケーキ by @sotarok

少し大人になった「肉とご飯と甘いもの」

Heredoc と Nowdoc

PHP

PHPには,昔ながらの,つまり,シェルスクリプトなどから由来する「ヒアドキュメント」が存在ししています.まあ,他の言語と同じですね.使い方は若干気持ち悪いですが,以下のような感じ.

<?php
$hoge = "変数の展開も可能";
$here = <<<HERE
これが
ヒアドキュメント!

$hoge
HERE;

それは,Here Document なわけですが,PHPの公式マニュアルでは Heredoc と表記されています.
そして,最近,内部で変数が展開されない(静的に評価される),Nowdoc ってやつができました.PHP 5.3 からの機能です.使い方は,ヒアドキュメントの終端識別子(上記のHERE)をシングルクオートで囲うだけです.つまり,シングルクオートで囲われた文字列と同様の動作をしめすヒアドキュメントみたいなものですね.

<?php
$hoge = "変数の展開も可能";
$here = <<<'NOW'
これが
Nowdoc!

$hoge <- これは展開されない
NOW;

これはなにが便利になったかと言うと,クラスのプロパティ定義にヒアドキュメント風に文字列を定義できるようになったということです(式として評価されない文字列リテラルとなるため).

<?php
$hoge = "変数の展開も可能";

class Hoge {
  public $here = <<<EOI
$hoge

これはできなかった.なぜなら変数の展開をしようとしちゃうから.
「Parse error: syntax error, unexpected T_VARIABLE, expecting T_ENCAPSED_AND_WHITESPACE or T_END_HEREDOC」
EOI;
}

class Hoge {
  public $here = <<<'EOI'
$hoge

これができるようになった.
EOI;
}


まあ要するにそれだけなんですけど,クラス定義時に安全に沢山文字列定義ができて嬉しいですね!よかったですね!

そもそもの話

というかそもそも,PHPは複数行にまたがる文字列を通常通り " または ' で定義できます.つまり,最初の例は,次のものと全く同じです(あ,厳密に言うと,直前直後の改行が削除されるのでは一緒にするにはいじらなきゃなんですけど)

<?php
$hoge = "変数の展開も可能";
$here = "
これが
ヒアドキュメント!

$hoge
";

となると,そもそもヒアドキュメントって必要だったのか,という話になりますね.まあ " のエスケープが不要であるといえばそうなのかもしれませんが,それだけですかね・・・・.
つまり,変数を展開したくなくてでも長ったらしい文章をクラス定義時にプロパティに定義したければ,

<?php
class Hoge {
  public $here = '$hoge

これができるようになった.';
}

これでよくね?というわけです.

さらにそもそもの話

いや,それでもヒアドキュメントが欲しいんだ,という人もいるかも知れません.多言語からきて使い慣れてるとか,引用符のエスケープがだるいとか,色いろあるとは思うんですけど,いや,実は,中に変数を含まなければ,ヒアドキュメントでも,クラス定義時にプロパティに定義できます.

PHP 5.3 以降では、変数を含まないヒアドキュメントではこの制約はなくなりました。

PHP: 文字列 - Manual
<?php
$hoge = "変数の展開も可能";

class Hoge {
  public $here = <<<EOI
これはOK.変数が含まれないから.
EOI;
}

いや,あれ?Nowdocって,どうせ変数を展開したくないわけだから,ドルを含む文字列を定義したいか(まあその場合ヒアドキュメントでも,¥$ とすれば良い),変数を含まない文字列で良い場合,別にヒアドキュメントで良い,とか考えると,果たして Nowdoc が必要だったのか徐々に謎になってきます.

本題

まあ,Nowdocの有意性はともかく,ヒアドキュメントはHeredocでヒアドキュメントなので,Nowdocはナウドキュメントでよくないですか,という,それだけの話です.
ナウ!ドキュメント!
ブログ書いたなう!