制御構造(制御構文)

条件分岐

if文の中が1行の場合は中カッコ(波括弧)は省略可能。 複数行ある場合は、Parse error となる。

$x = 10;
if($x === 10) {
	print '変数$xは10です。';
} else {
	print '変数$xは10ではありません。';
}

//中カッコを省略
if($x === 10)
	print '変数$xは10です。';
else
	print '変数$xは10ではありません。';

//ただし、elseブロックは直近のif命令に対応する
//if文が入れ子になってる場合は誤動作の元になる
$x = 10;
$y = 0;
if($x === 10) {
	if($y === 10) {
		print '変数$x、$yは10です。';
	}
} else {
	print '変数$xは10ではありません。';
} // 結果:何も表示されない

//↑これを中カッコ省略すると
if($x === 10)
	if($y === 10)
		print '変数$x、$yは10です。';
else
	print '変数$xは10ではありません。';
// 結果:変数$xは10ではありません。
// if($y === 10) に対応する else とみなされるため

条件式からはできるだけ否定は取り除く

ド・モルガンの法則

!A && !B == !(A || B)
!A || !B == !(A && B)

//下記は同義
if( !$flag1 && !$flag2 ){...}
if( !($flag1 || $flag2) ){...}

break

現在実行中の for, foreach, while, do-while, switch 構造の実行を終了します。
オプションの引数で ネストしたループ構造を抜ける数を指定することができます。 この引数のデフォルトは 1 で、直近のループ構造からだけ抜けます。実在する階層以上の数字を指定するとFatal errorとなる

continue

現在の周回だけをスキップし、ループそのものは継続して実行する。
switchブロック配下のcontinue命令(引数なし)はbreakと同じように動作する。switch文がループ構造とみなされ、引数なしではE_WARNINGとなる。(php7.3以降) continue 2 とすると、外側のループの次回の処理から続行します。

for ($i = 1; $i < 4; $i++) {
  $result = 0;
  switch ($i) {
    case 1 :
    case 3 :
			// $i = 1、3の場合のみ変数$resultを計算
      $result = $i * $i;
      break;
    case 2 :
      continue 2;
    //   continue; //引数なしではbreakと同じ、下のprint文が実行される(ただし警告が表示される)
    //   break;
    //   break 2;  //ループそのものを終了する $i=3は実行されない
  }
  print "{$i}の2乗は{$result}です。". PHP_EOL;
}

match

PHP 8.0.0 以降
型と値の一致チェック(===) に基づいて行われます。 値を返すので変数に代入したり、引数として渡すことができる。 match 式は、必ずセミコロン ; で終わらなければなりません。 最後の式のカンマを省略しても良い。

$food = 'cake';

$return_value = match ($food) {
    'apple' => 'This food is an apple',
    'bar' => 'This food is a bar',
    'cake' => 'This food is a cake',
};

var_dump($return_value);
// output > string(19) "This food is a cake"

match 式は、全ての場合を網羅していなければいけません。 制約式がどの分岐でも処理できなかった場合、 UnhandledMatchError がスローされます。

//defaultパターン、あらゆる場合にマッチする
$expressionResult = match ($condition) {
    1, 2 => foo(),
    3, 4 => bar(),
    default => baz(),
};

意図的なフォールスルーは値をカンマ区切りで列挙する。

$drink = 'ビール';
print match($drink) {
	'日本酒','ビール','ワイン' => '醸造酒です。',
	'ブランデー',' ウィスキー' => '蒸留酒です。',
};/

制約式に true を指定することで、 厳密な一致チェックを行わずに match 式を使うことができます。

整数の範囲に応じてmatch式を分岐させる一般的な使い方
(switch文でもtrueを使った同様の手法あり)

$age = 23;

$result = match (true) {
    $age >= 65 => 'senior',
    $age >= 25 => 'adult',
    $age >= 18 => 'young adult',
    default => 'kid',
};

var_dump($result);
//output > string(11) "young adult"

「⇒」の左辺に任意の式を指定できる(switch文にはない)

$data = 10;
print match($data) {
	hoge() => 'hogeがマッチ',
	foo() => 'fooがマッチ',
	bar() => 'barがマッチ',
};

while / do ~ while 命令

while は前置判定、do ~ while は後置判定
do ~ whileは1回は必ず実行される
do ~ whileの末尾にはセミコロンが必要

while(条件式) {
	// 条件式がtrueである間、繰り返し実行する処理
}

do {
	// 条件式がtrueである間、繰り返し実行する処理
} while (条件式);

foreach で値変数の参照渡し

$data = ['岩手', '埼玉', '岐阜', '広島', '福岡'];
foreach ($data as &$value) {
//foreach ($data as $value) {
  $value = $value . '県';
}
print_r($data);

//結果:$dataが書き換えられた
Array
(
    [0] => 岩手県
    [1] => 埼玉県
    [2] => 岐阜県
    [3] => 広島県
    [4] => 福岡県
)

declare

ディレクティブ の箇所で、セットされた declareブロックの挙動を指定することが出来ます。
現在のところ設定できるディレクティブは、ticks、encoding、strict_types だけです。
値として渡せるのはリテラルだけ、変数や定数は不可。
declare 文はグローバルスコープとしても使用され、 それはそれ以降のコード上の全てにおいて影響します (しかし、declare を含むファイルがインクルードされた場合は、 親ファイルにはその影響は及びません)。

ticks

条件式や引数式などは tick できません。
tickごとに発生させるイベントはregister_tick_function() を使用して指定します。

declare(ticks=1);

// tick イベントごとにコールされる関数
function tick_handler()
{
    echo "tick_handler() called\n";
}

register_tick_function('tick_handler'); // tick イベント発生

$a = 1; // tick イベント発生

if ($a > 0) {
    $a += 2;   // tick イベント発生
    print($a); // tick イベント発生
}

require / require_once

ファイルが見つからなかった場合、Fatal Error(致命的なエラー)処理が中断される。
外部ファイルは絶対パスを利用するのが望ましい。相対パスは起動スクリプトが起点となるため。

//絶対パスの例
require_once __DIR__.'/func.php';

読み込まれるファイルのマジック定数は、読み込みを行う前にパーサが評価します。
php.ini で allow_url_fopen が有効だと、URLを指定して外部サーバーのファイルを読み込むことができる。

include / include_once

ファイルが見つからなかった場合、Warning(警告)
処理は継続される。

<参考>

情報関数:get_included_files(): array
require、require_once、include、include_once によりスクリプトにロードされたすべてのファイルのフルパスを含む名前を配列で返す。