PHP 数组
本章将详细介绍 PHP 数组的创建、操作和常用函数。
数组概述
PHP 数组是一种有序映射,可以存储多个值。PHP 数组非常灵活,支持索引数组和关联数组。
索引数组
索引数组使用数字作为键:
<?php
// 创建索引数组
$colors = ["红", "绿", "蓝"];
$numbers = [1, 2, 3, 4, 5];
// 使用 array() 函数
$fruits = array("苹果", "香蕉", "橙子");
// 访问元素
echo $colors[0]; // 输出:红
echo $colors[1]; // 输出:绿
// 修改元素
$colors[0] = "红色";
// 添加元素
$colors[] = "黄"; // 添加到末尾
$colors[10] = "紫"; // 指定索引添加
?>
关联数组
关联数组使用字符串作为键:
<?php
// 创建关联数组
$person = [
"name" => "张三",
"age" => 25,
"city" => "北京"
];
// 使用 array() 函数
$user = array(
"username" => "admin",
"email" => "[email protected]"
);
// 访问元素
echo $person["name"]; // 输出:张三
echo $person["age"]; // 输出:25
// 修改元素
$person["age"] = 26;
// 添加元素
$person["job"] = "工程师";
?>
多维数组
数组中的元素可以是另一个数组:
<?php
// 二维数组
$users = [
["name" => "张三", "age" => 25],
["name" => "李四", "age" => 30],
["name" => "王五", "age" => 28]
];
// 访问元素
echo $users[0]["name"]; // 输出:张三
echo $users[1]["age"]; // 输出:30
// 三维数组
$data = [
"users" => [
["name" => "张三", "posts" => ["文章1", "文章2"]],
["name" => "李四", "posts" => ["文章3"]]
]
];
echo $data["users"][0]["posts"][0]; // 输出:文章1
?>
数组操作
添加元素
<?php
$arr = [1, 2, 3];
// 末尾添加
$arr[] = 4; // [1, 2, 3, 4]
array_push($arr, 5, 6); // [1, 2, 3, 4, 5, 6]
// 开头添加
array_unshift($arr, 0); // [0, 1, 2, 3, 4, 5, 6]
// 指定位置添加
array_splice($arr, 2, 0, "新元素");
?>
删除元素
<?php
$arr = [1, 2, 3, 4, 5];
// 删除末尾元素
$last = array_pop($arr); // $last = 5, $arr = [1, 2, 3, 4]
// 删除开头元素
$first = array_shift($arr); // $first = 1, $arr = [2, 3, 4]
// 删除指定元素
unset($arr[1]); // $arr = [0 => 2, 2 => 4](索引不连续)
// 删除指定位置元素
array_splice($arr, 1, 1); // 删除索引 1 开始的 1 个元素
?>
修改元素
<?php
$arr = [1, 2, 3, 4, 5];
// 直接修改
$arr[0] = 10;
// 批量修改
$arr = array_replace($arr, [0 => 100, 1 => 200]);
// 使用 array_splice 替换
array_splice($arr, 1, 2, [20, 30]); // 从索引 1 开始,替换 2 个元素
?>
查找元素
<?php
$arr = ["name" => "张三", "age" => 25, "city" => "北京"];
// 检查键是否存在
var_dump(array_key_exists("name", $arr)); // bool(true)
var_dump(isset($arr["name"])); // bool(true)
var_dump(isset($arr["job"])); // bool(false)
// 检查值是否存在
var_dump(in_array("张三", $arr)); // bool(true)
var_dump(in_array(25, $arr)); // bool(true)
var_dump(in_array("25", $arr)); // bool(true)(松散比较)
var_dump(in_array("25", $arr, true)); // bool(false)(严格比较)
// 查找值的键
$key = array_search(25, $arr); // "age"
$key = array_search("张三", $arr); // "name"
// 查找所有匹配的键
$arr = [1, 2, 3, 2, 4, 2];
$keys = array_keys($arr, 2); // [1, 3, 5]
?>
获取数组信息
<?php
$arr = [1, 2, 3, 4, 5];
// 数组长度
echo count($arr); // 5
echo sizeof($arr); // 5(count 的别名)
// 最大值、最小值、求和
echo max($arr); // 5
echo min($arr); // 1
echo array_sum($arr); // 15
// 获取所有键
$keys = array_keys($arr); // [0, 1, 2, 3, 4]
// 获取所有值
$values = array_values($arr); // [1, 2, 3, 4, 5]
// 检查是否为数组
var_dump(is_array($arr)); // bool(true)
?>
数组遍历
foreach 循环
<?php
$arr = ["name" => "张三", "age" => 25, "city" => "北京"];
// 遍历值
foreach ($arr as $value) {
echo "$value\n";
}
// 遍历键值对
foreach ($arr as $key => $value) {
echo "$key: $value\n";
}
// 修改原数组
$numbers = [1, 2, 3, 4, 5];
foreach ($numbers as &$num) {
$num *= 2;
}
unset($num); // 解除引用
print_r($numbers); // [2, 4, 6, 8, 10]
?>
for 循环
<?php
$arr = [1, 2, 3, 4, 5];
for ($i = 0; $i < count($arr); $i++) {
echo $arr[$i] . "\n";
}
?>
while 循环与 each()(已弃用)
<?php
// PHP 7.2 之前的方式(已弃用)
// while (list($key, $value) = each($arr)) {
// echo "$key: $value\n";
// }
// 推荐使用 foreach
?>
数组指针
<?php
$arr = [1, 2, 3, 4, 5];
// 获取当前元素
echo current($arr); // 1
// 移动指针并获取下一个元素
echo next($arr); // 2
echo next($arr); // 3
// 获取当前键
echo key($arr); // 2
// 移动指针到上一个元素
echo prev($arr); // 2
// 移动指针到开头
reset($arr);
echo current($arr); // 1
// 移动指针到末尾
end($arr);
echo current($arr); // 5
?>
数组排序
按值排序
<?php
$arr = [3, 1, 4, 1, 5, 9, 2, 6];
// 升序排序(重新索引)
sort($arr);
print_r($arr); // [1, 1, 2, 3, 4, 5, 6, 9]
// 降序排序(重新索引)
rsort($arr);
print_r($arr); // [9, 6, 5, 4, 3, 2, 1, 1]
?>
按值排序(保持键)
<?php
$arr = ["b" => 2, "a" => 1, "c" => 3];
// 升序排序(保持键)
asort($arr);
print_r($arr); // ["a" => 1, "b" => 2, "c" => 3]
// 降序排序(保持键)
arsort($arr);
print_r($arr); // ["c" => 3, "b" => 2, "a" => 1]
?>
按键排序
<?php
$arr = ["b" => 2, "a" => 1, "c" => 3];
// 按键升序排序
ksort($arr);
print_r($arr); // ["a" => 1, "b" => 2, "c" => 3]
// 按键降序排序
krsort($arr);
print_r($arr); // ["c" => 3, "b" => 2, "a" => 1]
?>
自定义排序
<?php
$users = [
["name" => "张三", "age" => 25],
["name" => "李四", "age" => 20],
["name" => "王五", "age" => 30]
];
// 按年龄升序排序
usort($users, function($a, $b) {
return $a["age"] <=> $b["age"];
});
// PHP 7.4+ 箭头函数
usort($users, fn($a, $b) => $a["age"] <=> $b["age"]);
// 按名字排序
usort($users, fn($a, $b) => strcmp($a["name"], $b["name"]));
?>
自然排序
<?php
$files = ["img1.png", "img10.png", "img2.png", "img20.png"];
// 普通排序
sort($files);
// ["img1.png", "img10.png", "img2.png", "img20.png"]
// 自然排序
natsort($files);
// ["img1.png", "img2.png", "img10.png", "img20.png"]
// 自然排序(不区分大小写)
natcasesort($files);
?>
数组函数
数组合并
<?php
$a = [1, 2, 3];
$b = [4, 5, 6];
// 合并数组
$merged = array_merge($a, $b); // [1, 2, 3, 4, 5, 6]
// 使用 + 运算符(后者不覆盖前者)
$c = $a + $b; // [1, 2, 3]($b 的键已存在,不覆盖)
// 关联数组合并
$x = ["a" => 1, "b" => 2];
$y = ["b" => 3, "c" => 4];
$z = array_merge($x, $y); // ["a" => 1, "b" => 3, "c" => 4]
?>
数组切片
<?php
$arr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
// 切片(起始位置,长度)
$slice = array_slice($arr, 2, 3); // [3, 4, 5]
// 负数表示从末尾开始
$slice = array_slice($arr, -3); // [8, 9, 10]
// 保留键
$slice = array_slice($arr, 2, 3, true); // [2 => 3, 3 => 4, 4 => 5]
?>
数组分割
<?php
$arr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
// 分割成多个数组
$chunks = array_chunk($arr, 3);
// [[1, 2, 3], [4, 5, 6], [7, 8, 9], [10]]
// 保留键
$chunks = array_chunk($arr, 3, true);
?>
数组填充
<?php
// 填充数组
$arr = array_fill(0, 5, "hello");
// ["hello", "hello", "hello", "hello", "hello"]
// 填充键值对
$arr = array_fill_keys(["a", "b", "c"], 0);
// ["a" => 0, "b" => 0, "c" => 0]
?>
数组去重
<?php
$arr = [1, 2, 2, 3, 3, 3, 4];
// 去重
$unique = array_unique($arr); // [1, 2, 3, 4]
// 严格模式
$arr = [1, "1", 2, 2.0];
$unique = array_unique($arr, SORT_REGULAR); // [1, 2]
?>
数组交集与差集
<?php
$a = [1, 2, 3, 4, 5];
$b = [3, 4, 5, 6, 7];
// 交集
$intersect = array_intersect($a, $b); // [2 => 3, 3 => 4, 4 => 5]
// 差集(在 $a 但不在 $b)
$diff = array_diff($a, $b); // [0 => 1, 1 => 2]
// 关联数组交集
$x = ["a" => 1, "b" => 2, "c" => 3];
$y = ["a" => 1, "b" => 3, "d" => 4];
$intersect = array_intersect_assoc($x, $y); // ["a" => 1]
?>
数组映射与过滤
<?php
$arr = [1, 2, 3, 4, 5];
// 映射
$squares = array_map(fn($n) => $n * $n, $arr);
// [1, 4, 9, 16, 25]
// 过滤
$evens = array_filter($arr, fn($n) => $n % 2 == 0);
// [1 => 2, 3 => 4]
// 归约
$sum = array_reduce($arr, fn($carry, $n) => $carry + $n, 0);
// 15
// 多数组映射
$a = [1, 2, 3];
$b = [4, 5, 6];
$sums = array_map(fn($x, $y) => $x + $y, $a, $b);
// [5, 7, 9]
?>
数组翻转
<?php
$arr = ["a" => 1, "b" => 2, "c" => 3];
// 键值互换
$flipped = array_flip($arr); // [1 => "a", 2 => "b", 3 => "c"]
?>
数组反转
<?php
$arr = [1, 2, 3, 4, 5];
// 反转(保持键)
$reversed = array_reverse($arr); // [5, 4, 3, 2, 1]
// 反转(重新索引)
$reversed = array_reverse($arr, false); // [5, 4, 3, 2, 1]
?>
数组随机
<?php
$arr = [1, 2, 3, 4, 5];
// 随机获取键
$key = array_rand($arr); // 随机键
// 随机获取多个键
$keys = array_rand($arr, 2); // 随机 2 个键
// 随机打乱
shuffle($arr); // 原地打乱
?>
数组判断
<?php
$arr = [1, 2, 3, 4, 5];
// 判断是否所有元素满足条件
$allPositive = array_every($arr, fn($n) => $n > 0); // PHP 8.4+
// 判断是否有元素满足条件
$hasEven = array_any($arr, fn($n) => $n % 2 == 0); // PHP 8.4+
// PHP 8.4 之前的替代方案
$allPositive = !in_array(false, array_map(fn($n) => $n > 0, $arr));
$hasEven = in_array(true, array_map(fn($n) => $n % 2 == 0, $arr));
?>
数组解构(PHP 7.1+)
<?php
// 索引数组解构
[$a, $b, $c] = [1, 2, 3];
echo $a; // 1
echo $b; // 2
echo $c; // 3
// 跳过元素
[, , $third] = [1, 2, 3];
echo $third; // 3
// 关联数组解构
["name" => $name, "age" => $age] = ["name" => "张三", "age" => 25];
echo $name; // 张三
echo $age; // 25
?>
小结
本章我们学习了:
- 数组的创建:索引数组、关联数组、多维数组
- 数组操作:添加、删除、修改、查找元素
- 数组遍历:foreach、for、数组指针
- 数组排序:sort、asort、ksort、usort
- 常用数组函数:合并、切片、过滤、映射等
下一章我们将学习字符串处理。