PHP

PHP5.6の新機能紹介

More than 1 year has passed since last update.

PHP7.1.0α1 / PHP7.1の新機能 / PHP7.0.0α1 / PHP5.6

いつのまにかPHP5.6への移行ガイドができていたので、新機能を斜め読みしてみます。


新機能


Constant scalar expressions

オブジェクト定数に表現が使えるようになりました。

<?php

const A = 1;

class HOGE{
const B = A + 100; // 101
const C = self::B + 10; // 111
const D = intval(1); // Parse error: syntax error
}

ただし変数/メソッド呼び出しはできない模様。

どうせならそこまで対応してほしかったところ。


Variadic functions via ...

関数の引数に可変長引数が使えるようになりました。

これまでも可変長引数はfunc_get_args()で使えましたが、こいつは引数に明記されないからわかりにくいし、IDEにも捉えてもらえませんでした。

<?php

function hoge($arg1, $arg2, ...$args){}

hoge(1, 2); // $args = []
hoge(1, 2, 3, 4, 5); // $args = [3, 4, 5]

固定の引数に入りきらない部分が、可変長引数に配列で入ってきます。

これは便利。


Argument unpacking via ...

関数の呼び出しにも...が使えるようになりました。

<?php

function fuga(...$args){}

fuga(1, [2, 3]); // $args = [1, [2, 3]]
fuga(1, ...[2, 3]); // $args = [1, 2, 3]
fuga(...[1], ...[2, 3]); // $args = [1, 2, 3]

配列を...付きで渡すと、引数を展開してから渡してくれます。

こちらはいったいどういうメリットがあるのかよくわかりません。


Exponentiation via **

累乗演算子です。


use function and use const

関数や定数を use 文でインポートできるようになりました。

<?php

namespace HOGE{
const FUGA = 1;
function foo(){return __FUNCTION__;}
}

namespace{
use const HOGE\FUGA;
use function HOGE\foo;

echo FUGA; // 1
echo foo(); // HOGE\foo
}

http://www.php.net/manual/ja/language.namespaces.faq.php#language.namespaces.faq.nofuncconstantuse


関数や定数は use 文でインポートできない


お、おう。


phpdbg

デバッガとしてphpdbgが同梱されます。

ブレークポイントやステップ実行などの強力なデバッグ機能が使用可能です。

が、今のところコマンドラインツールしかないみたいなので、Eclipseのデバッグウィンドウみたいに扱えるIDEの出現が望まれるところ。

ひとつ見つけたのですが日本語ではないのでよくわかりません。


Default character encoding

デフォルトの文字コードがようやくUTF-8になりました。


php://input is reusable

いまいち意味がよくわかりませんが、php://inputを何度呼び出してもメモリを食いつぶさなくなったってこと?


Large file uploads

2ギガバイト以上のファイルをアップロードできるようになりました。

まあ普通はそんなのupload_max_filesizeで止めますが。


GMP supports operator overloading

GMPの演算子オーバーロードです。


hash_equals() for timing attack safe string comparison

hash_equals()関数のマニュアルはまだ無いようです。

ソースを見ると、どうもふたつの文字列が同じものかを調べてる、つまり===にしか見えないのですが、いったい何の機能があるのでしょう。

どうやらタイミング攻撃を防ぐもののようです。

100文字のパスワードをチェックする機構があったとして、

===は「文字列の長さが違うからfalseを返す」ときと「1文字目が違うからfalseを返す」ときと「100文字目が違うからfalseを返す」ときで処理にかかる時間がほんのわずかに違います。

その時間の違いからパスワードが何文字か推定できて、何文字目が違うか推定できて、結果として全探索より遙かに少ない回数で正解パスワードまで辿り着けてしまうということらしいです。

正直そんなの可能なのか?と思えるのですが、実際やってみた人が現れ、情報セキュリティスペシャリストの問題にも出てくるくらいになっています。

そこでhash_equals()は、途中の文字が違っても最後まで比較を行うことで、実行にかかる時間を一定にするようにしています。

でも文字列長が違ったら即座にFALSEを返してるように見えるんだがどうだろう。


gost-crypto hash algorithm

RFC4357で定義されているGOSTというアルゴリズムに対応したということですが、GOSTが何なのかよくわかりません。


SSL/TLS improvements

SSLの機能が色々追加になりました。

よくわかりませんが。


非推奨

ついでに非推奨となった機能


Calls from incompatible context

インスタンス内でstaticでないメソッドをstatic呼び出しするとE_DEPRECATEDが発生します。

<?php

class A {
public function foo() {}
}
class B {
public function bar() { A::foo(); }
}
(new B)->bar(); // Deprecated: Non-static method A::foo() should not be called statically
A::foo(); // Strict Standards: Non-static method A::foo() should not be called statically

どうして違うエラーになってるのかさっぱりだ。


$HTTP_RAW_POST_DATA and always_populate_raw_post_data

always_populate_raw_post_dataを有効にするとE_DEPRECATEDが発生します。

かわりに php://input を使えということらしいです。

正直、これは是非とも5.6に上げなければ、というような機能はあまりないように思えます。

一番魅力的なのはphpdbgだと思いますが、これはPHP5.4以降個別に入れられたりします。

まあChangeLogにはFixedがたくさん並んでいて、完成度を高める方向に向かっていると考えるといいことなのではないでしょうか。