特定の時点で配列に挿入しようとしています:
$hi = "test";
$var2 = "next";
$arr = array(&$hi);
$arr[] = &$var2; // this works
array_splice($arr, 1, 0, &$var2); // this doesn't
splice を使用して配列に挿入しようとすると失敗し、最初の方法を使用しても失敗しないのはなぜですか?
簡単な答えですが、参照を使用してこの関数を呼び出すことは推奨されておらず、(php 構成によっては) 警告が生成される可能性があることに注意してください。
array_splice($arr, 1, 0, array(&$var2));
方法と理由の答え: 何が起こっているかは非常に微妙です。スプライスを行うと、その位置に参照を挿入したため、実際には $var2 が再割り当てされます。次のコードで確認できます。
<?php
$hi = "test";
$var2 = "next";
$arr = array(&$hi);
$arr[] = &$var2; // this works
printf("=== var2 before splice:\n%s\n", var_export($var2, TRUE));
array_splice($arr, 1, 0, &$var2); // this doesn't
printf("=== var2 after splice:\n%s\n", var_export($var2, TRUE));
?>
次の結果が得られます。
=== var2 before splice:
'next'
=== var2 after splice:
array (
0 => 'next',
)
接合前の $var2 は、予想どおり ('next') の文字列であったことに注意してください。ただし、結合後、$var2 は文字列 'next' という 1 つの要素を含む配列に置き換えられています。
原因はドキュメントにあると思います:「置換が配列でない場合、1つに型キャストされます(つまり(配列)$パラメータ)。だから何が起こっているのですか?
内部で何が起こっているのか、すべて正確にはわかりませんが、スプライス中に $var が確実に再割り当てされています。3 番目の変数を使用すると、参照として既に存在するものに何かを代入していないため、期待どおりに機能することに注意してください。
<?php
$hi = "test";
$var2 = "next";
$var3 = "last";
$arr = array(&$hi);
$arr[] = &$var2; // this works
array_splice($arr, 1, 0, &$var3);
printf("=== arr is now\n%s\n", var_export($arr, TRUE));
?>
結果を生成します。
=== arr is now
array (
0 => 'test',
1 => 'last',
2 => 'next',
)
最後の引数を配列にする必要があるかもしれません。そうしないと、マニュアルに従って型キャストされます。
array_splice( $arr, 1, 0, array( &$var2 ) );
あなたのような例を試してみると、「呼び出し時の参照渡しは推奨されていません」という警告が表示されます。この答えによると:
php.ini ファイルで allow_call_time_pass_reference を true に設定できます。しかし、それはハックです。