[PHP] テンプレートエンジンやヒアドキュメントにおける改行文字の扱い
PHPは言語構造としてテンプレートエンジン(文書の出力機能)があり、一方でヒアドキュメントの機能もあるが、基本的に見た目のまま出力される。
ただし改行については、いずれもやや癖があるので注意。
テンプレートエンジン
PHPタグ <?php の閉じタグ ?> の直後の改行は無視される。
PHP:
first-line <?php echo 'php'; ?> second-line
出力:
first-line phpsecond-line
このため、以下のような書き方をするとコードの見た目上はきれいだが、出力されたテキストは意図したものにならない。
例1
PHP:
<div> <?php echo 'sample'; ?> </div>
出力:
<div> sample</div>
例2
PHP:
<div> <?php if (b) : ?> sample <?php endif; ?> </div>
出力:
<div> sample </div>
これらを防ぐには、PHPタグの直後にはかならず改行をひとつ余計に入れ、できるだけPHPタグの前にはタブやスペースを入れないようにする。
例1
<div> <?php echo 'sample'; ?> </div>
例2
<div> <?php if (b) : ?> sample <?php endif; ?> </div>
出力:
<div> sample </div>
ヒアドキュメント
最後の行(終端 IDの直前)の改行は無視される。
PHP:
echo <<< EOD first EOD; echo 'second'
出力:
firstsecond
この場合も、対応としては改行をひとつ余計に記述しておく。
PHP:
echo <<< EOD first EOD; echo 'second'
出力:
first second
PHPファイル
上記とは異なり、PHPファイルそのものは最後の改行が省略されるということはない。
ただし、見た目上とは異なり、ファイルの終端が改行とみなされることはないので注意が必要(一部のワープロソフトなどとは異なるということ)。
sample1.php
<?php echo 'first'; ?> second
この場合、以下のように出力される。
first second
このあたりをきちんと理解しておかないと、複数のファイルをインクルードした際に、意図しない形での出力になってしまう。
sample2.php
<?php echo 'third'; ?> fourth
link.php
require 'sample1.php'; require 'sample2.php';
出力
first secondthird fourth
コーディングの際によくやるように、常に最後は改行で終わるようにしたほうがいいかもしれない。
<?php echo 'first'; ?> second # EOF
補足:PHPの閉じタグを省略しよう
上記のとおり、PHPタグ直後の改行は無視されるため、以下のようにPHPのコードのみを記述した場合は、最後に改行がひとつあってもコード側でechoなどによって何かを出力しないかぎり、何も表示されない。
<?php function doSample() { //... } ?> # \n # EOF
裏を返せば、最後に複数の改行があった場合、テキストとして改行文字が出力されることになる。
sample.php
<?php function doSample() { //... } ?> # \n # \n # EOF
ほとんどの場合これでも問題はないが、ヘッダ情報などを出力する際にエラーになってしまうことがある。
<?php require 'sample.php'; header('Location: http://www.example.com/'); ?>
header()では、それを実行する前に他の出力があることを認めていないため。
関数やクラスのインクルードの際に問題になりやすいので、昔から閉じタグ「?>」を省略することが推奨されている(PHPの公式リファレンスの例では、相変わらず閉じタグを書いているが)。
<?php function doSample() { //... }
これでファイルの末尾にいくら改行があっても、何も出力されない。
言語仕様として許されている方法なので、PHPコードのみのファイルでは基本的にこういう書き方をするようにしよう。