<?php
// 仅取值
foreach ($array as $value) { ... }
// 取键值
foreach ($array as $key => $value) { ... }
<?php
$colors = [
'white' => '白色',
'black' => '黑色',
'red' => '红色',
];
foreach ($colors as $key => $value) {
echo "{$key} => {$value}<br>";
}
// 输出:
// white => 白色
// black => 黑色
// red => 红色
<?php
$nums = [1, 2, 3];
foreach ($nums as &$v) {
$v *= 2;
}
unset($v); // 重要:解除引用,防止后续污染
print_r($nums); // [2, 4, 6]
默认按值拷贝:foreach ($arr as $v) 中 $v 是副本,修改 $v 不影响原数组;$arr 也是副本(PHP 7+ 写时复制优化)。
<?php
$arr = [1,2,3];
foreach ($arr as $v) {
$arr = []; // 修改外部变量
echo $v; // 输出 123 —— 遍历的是拷贝
}
| 代码 | 输出 | 原因 |
|---|---|---|
foreach ($arr as &$v) { $arr=[]; echo $v; } | 1 | $arr 是引用,循环内修改影响迭代器 |
global $arr; foreach($arr as $v){ $arr=[]; echo $v; } | 1 | 全局变量在 foreach 中按引用处理 |
<?php
$arr = [1,2,3];
foreach ($arr as &$v) { /* ... */ }
foreach ($arr as $v) { /* ... */ } // 危险!$v 仍是引用,最后元素会被覆盖
// 正确做法三选一:
// 1. unset($v); foreach ($arr as $v) ...
// 2. 两次都用引用:foreach ($arr as &$v) ...
// 3. 复制数组:$arr2 = $arr; foreach ($arr2 as $v) ...
foreach ((array)$arr as $v) —— 防止 null/非数组报错。unset($v) 释放对最后元素的引用。foreach:最快,专用内部迭代器,C 层实现。for:需手动索引,适合数值索引数组或需控制步长。each/list/while:已废弃(PHP 7.2+),慢且易错。array_walk/array_map:函数调用开销大,适合函数式转换。<?php
$users = [
['id'=>1, 'name'=>'Alice', 'tags'=>['php','go']],
['id'=>2, 'name'=>'Bob', 'tags'=>['js','ts']],
];
// 递归打印
function printArray(array $arr, int $indent = 0) {
foreach ($arr as $k => $v) {
echo str_repeat(' ', $indent) . "{$k} => ";
if (is_array($v)) {
echo "\n";
printArray($v, $indent+1);
} else {
echo "{$v}\n";
}
}
}
printArray($users);
foreach 是 PHP 遍历数组的首选:语法简洁、性能最优、功能完备。掌握值拷贝与引用的区别、连续引用遍历的陷阱、防御性写法,即可避开 90% 的坑,写出健壮高效的代码。