一、数组概述
1、数组的基本概念
数组是对大量数据进行有效组织和管理的手段之一,通过数组的强大功能,可以对大量性质相同的数据进行存储、排序、插入及删除等操作,从而可以有效地提高程序开发效率及改善程序的编写方式。
2、数组分类
在PHP中,数组既是一种数据类型,也是一种数据的组织与处理手段。数组有一维数组、二维数组、多维数组。但不管是一维数组还是多维数组都可以分为 数字索引数组 和 关联数组。
- 索引数组
数组的元素也可不定义键名,由PHP默认用索引号作为键名。
例:$A=array(5,8,4,6,9,7);
对于采用默认键名的数组,每个元素在数组中的索引号,也称为该元素的下标,数组的下标默认从0开始。 - 关联数组
数组中的每一个数据称为数组的一个元素,每一个元素都由两部分组成:元素名与元素值。其中,元素名称为“键名”,元素值称为“键值”。数组元素的键名由程序员自定义。
例如:$A = array("A" => 3, "B" => 5, "C" => 7, "D" => 9);
二、数组的处理
1、数组的创建与初始化
- 使用
array()
函数创建数组
① $数组变量名 = array(key1 => value1, key2 => value2, …, keyN => valueN);
② $数组变量名 = array(value1, value2, …, valueN);
③ $数组变量名 = array();
④ $数组变量名[下标] = 值;
⑤ $数组变量名[] = 值;
例子
echo '<pre>';
//1
$array = array("name" => "张同学", "xuehao" =>20201111111 , "gender" => "男");
var_dump($array);
//2
$array = array("张同学", 20201111111 , "男");
var_dump($array);
//3
$array = array();
var_dump($array);
//4
$array[0] = "张同学";
$array[1] = 20201111111;
$array[2] = "男";
var_dump($array);
//5
$array[] = "张同学";
$array[] = 20201111111;
$array[] = "男";
var_dump($array);
//注意键名
$array = array( 1 => "张同学", 3 => 20201111111, "男");
var_dump($array);
//注意键名和值
$array = array(1, 1, 1, 1, 8 => 1, 10, 4 => 2, 3 => 13);
var_dump($array);
//使用值 $array["键名"]
echo "<br>";
echo $array[3];
注意:如果定义了两个完全一样的键名,则后面的值会覆盖前面的值
- 使用
range()
定义数组
若一个数组的所有元素的值,都明确在某一范围内,可以使用range()函数来定义一个指定范围的数组。
其语法格式如下:
$数组名=range($min,$max,[$step])
<?php
echo '<pre>';
$array = range(1, 5);
var_dump($array);
$array = range(2, 10, 2);
var_dump($array);
$array = range("a", "e");
var_dump($array);
?>
- 二维数组和多维数组
二维数组和一维数组的声明方式一样,只是将数组中的一个或多个元素也声明成一个数组,同时也有直接为数组元素赋值和使用 array() 函数两种声明二维数组的方法。
<?php
echo '<pre>';
$array0 = array("name" => "张同学", "xuehao" =>20201111111 , "gender" => "男");
$array1 = array("name" => "李同学", "xuehao" =>2020222222 , "gender" => "男");
$array2 = array("name" => "赵同学", "xuehao" =>2020333333 , "gender" => "女");
$array = array(
array("name" => "张同学", "xuehao" =>20201111111 , "gender" => "男"),
array("name" => "李同学", "xuehao" =>2020222222 , "gender" => "男"),
array("name" => "赵同学", "xuehao" =>2020333333 , "gender" => "女")
);
var_dump($array);
//获取二维数组中的元素也和一维数组类似,只需要注明每个维度的下标即可,示例代码如下:
echo $array[0]['name'].'同学的学号是'.$array[0]['xuehao'].',性别是'.$array[0]['gender'];
?>
参考二维数组,举一反三,可以很容易地创建三维数组、四维数组或者其他更高维数的数组。
定义一个三维数组的示例如下:
<?php
echo '<pre>';
$array = array(
array(
"name" => "张同学",
"xuehao" =>20201111111 ,
"gender" => "男",
"score" => array(
"yuwen" => 100,
"shuxue" => 90,
"yingyu" => 80,
)
),
array(
"name" => "李同学",
"xuehao" =>2020222222 ,
"gender" => "男",
"score" => array(
"yuwen" => 95,
"shuxue" => 85,
"yingyu" => 75,
)
),
array(
"name" => "赵同学",
"xuehao" =>2020333333 ,
"gender" => "女",
"score" => array(
"yuwen" => 80,
"shuxue" => 90,
"yingyu" => 100,
)
)
);
var_dump($array);
echo $array[1]["score"]["shuxue"]; //输出李同学的数学分数
//打印数组长度
echo count($array);
echo count($array, 1);
?>
- 数组的长度
数组元素的个数,称为数组的长度。可以通过count()或sizeof()两个函数来获取数组的元素个数。- count() 函数其语法格式如下:
count($array [, $mode = COUNT_NORMAL])
参数说明如下:- $array:为待统计的数组或对象;
- $mode:为可选参数,可以省略。
- 如果省略 $mode 参数,或者将其设置为 COUNT_NORMAL 或者 0,count() 函数将不检测多维数组;
- 如果 $mode 设置为 COUNT_RECURSIVE 或者 1,count() 函数将递归计算数组中元素的个数,对于计算多维数组的元素个数尤为有用。
- sizeof() 函数
sizeof() 函数是 count() 函数的别名,也就是所 sizeof() 函数的功能及使用方法与 count() 函数完全相同。
- count() 函数其语法格式如下:
2、键名和值的操作
- 存在性检查
- 检查键名或索引是否存在:
array_key_exists()
语法格式如下:
array_key_exists(mixed $key, array $array): bool
数组里有键 key 时,array_key_exists() 返回 true。 key 可以是任何能作为数组索引的值。注意:<?php $array = array( "name" => "张同学", "xuehao" =>20201111111 , "gender" => "男", "score" => array( "yuwen" => 100, "shuxue" => 90, "yingyu" => 80, ) ); if(array_key_exists('name', $array)){ echo '键名“name”存在<br>'; }else{ echo '键名“name”不存在<br>'; } //array_key_exists() 函数仅能判断数组第一维的键名,不能判断多维数组里嵌套的键名。 if(array_key_exists('shuxue', $array)){ echo '键名“shuxue”存在<br>'; }else{ echo '键名“shuxue”不存在<br>'; } if(array_key_exists('shuxue', $array['score'])){ echo '键名“shuxue”存在<br>'; }else{ echo '键名“shuxue”不存在<br>'; } //注意 isset()函数也可以用来检查数组中的键名是否存在 if(isset($array['score']['shuxue'])){ echo '键名“shuxue”存在<br>'; }else{ echo '键名“shuxue”不存在<br>'; } ?>
isset()
函数也可以用来检查数组中的键名是否存在,但如果检查的键名对应的值为NULL
时,isset()
函数返回FALSE
- 检查值是否存在:
in_array()
语法格式如下:in_array($needle, $array[, $strict = FALSE])
- 参数说明如下:
- $needle:为待搜索的值,如果 $needle 是字符串,则在比较时区分大小写;
- $array:为待搜索的数组;
- $strict:为可选参数,默认为 FALSE。
如果 $strict 为空或者 FALSE,则 in_array() 函数只会检查 $needle 的值是否和 $array 中的值相等;
如果 $strict 的值为 TRUE,in_array() 函数除了会检查 $needle 和 $array 中的值之外,还会比较它们的类型是否相等。
注意:array_search()函数当值存在时返回这个值的键名,不存在返回NULL<?php $array = array( "name" => "张同学", "xuehao" =>20201111111 , "gender" => "男", "score" => array( "yuwen" => 100, "shuxue" => 90, "yingyu" => 80, ) ); if(in_array('20201111111', $array)){ echo '数组中包含“20201111111”<br>'; }else{ echo '数组中不包含“20201111111”<br>'; } if(in_array('20201111111', $array, true)){ echo '数组中包含“20201111111”<br>'; }else{ echo '数组中不包含“20201111111”<br>'; } //in_array() 函数的第一个参数除了可以是一个具体的值外,还可以是一个数组。也就是说使用 in_array() 函数还可以判断一个数组是否包含另一个数组。 $score = array( "yuwen" => 100, "shuxue" => 90, "yingyu" => 80, ); if(in_array($score, $array)){ echo '数组 $array 中包含数组 $score'; }else{ echo '数组 $array 中不包含数组 $score'; } //array_search()函数也可以用来判断值是否存在 $key = array_search('20201111111', $array); if($key != null){ echo '数组中包含“20201111111”<br>'; echo $key; }else{ echo '数组中不包含“20201111111”<br>'; } ?>
- 参数说明如下:
- 检查键名或索引是否存在:
- 获取和输出
array_keys()
函数 可以取得数组中所有的键名array_values()
函数 可以取得数组中所有的值
<?php $arr = array("red" => "红色", "blue" => "蓝色", "white" => "白色"); $keyArrs = array_keys($arr); $valueArrs = array_values($arr); var_dump($keyArrs); var_dump($valueArrs); ?>
3、数组的删除
- 删除整个数组 删除整个数组的方法与释放一个变量的方法是一样的,使用unset()函数。
语法格式如下:
unset($array_name)
- 删除数组元素 删除一个数组元素,也可以用unset()来实现。
语法格式是:
unset($arr[index] | $arr[key]);
其中,$arr[index]是通过数组的下标来指定要删除的数组元素,$arr[key]是通过键名来指定要删除的数组元素。
使用unset()删除数组元素后,被删除的数组下标或者键名,直接丢弃,PHP不会对数组进行重新索引。 - 删除多个数组元素
如果需要在删除某些数组元素以后,数组能够自动重新索引,可以使用array_splice()
函数实现,并且该函数还可以一次性删除多个元素。
其语法格式如下:
array_splice(
array &$input,
int $offset,
int $length = count($input),
mixed $replacement = array()
): array
-参数
input
输入的数组。
offset
如果 offset 为正,则从 input 数组中该值指定的偏移量开始移除。
如果 offset 为负,则从 input 末尾倒数该值指定的偏移量开始移除。
length
如果该值设置为正数,则移除该数量的元素。
如果该值设置为负数,则移除从 offset 到数组末端倒数 length 为止中间所有的元素。
如果该值未设置,则移除从 offset 参数设置的位置开始直到数组末端的所有元素。
如果该值设置为零,则不会移除元素。
replacement
如果给出了 replacement 数组,则被移除的单元被此数组中的单元替代。
如果 offset 和 length 的组合结果是不会移除任何值,则 replacement 数组中的单元将被插入到 offset 指定的位置。
-返回值
返回由被提取元素组成的数组。
<?php
$a1=array("a"=>"red","b"=>"green","c"=>"blue","d"=>"yellow");
$a2=array("a"=>"purple","b"=>"orange");
print_r(array_splice($a1,0,2,$a2));
echo "<br>";
print_r($a1);
?>
- 删除重复的数组元素
一个数组中可能会存在多个相同键值的元素,如果需要将重复的元素删除,只保留一个,可以使用array_unique()函数。
其语法格式如下:
array_unique(array $array, int $sort_flags = SORT_STRING): array
array_unique() 函数用于移除数组中重复的值。如果两个或更多个数组值相同,只保留第一个值,其他的值被移除。
<?php
$input = array("a" => "green", "red", "b" => "green", "blue", "red");
$result = array_unique($input);
var_dump($result);
//索引不会重排
$input = array(4, "4", "3", 4, 3, "3");
$result = array_unique($input);
var_dump($result);
$A = array("A", "A", "B", "C", "B");
$B = array_unique($A);
var_dump($A);
?>
三、数组的遍历
1、数组遍历相关函数
key()
:获取数组当前单元的键名current()
:获取数组当前单元的值pos()
:是 current() 函数的别名end()
:将内部指针指向数组中的最后一个元素;next()
:将内部指针指向数组中的下一个元素,如果成功则返回数组中下一个元素的值,如果没有更多的数组元素则返回 FALSE;prev()
:将内部指针指向数组中的上一个元素;reset()
:将内部指针指向数组中的第一个元素;list()
: 可以把一个数组中的值分别赋给一组变量;(已废弃)each()
:返回当前元素的键名和键值,并将内部指针指向数组中的下一个元素。
<?php
$array = array(
'PHP数组学习',
'https://www.php.net/manual/zh/ref.array.php',
'current() 函数'
);
echo current($array).'<br>';
echo pos($array).'<br>';
next($array);
echo current($array).'<br>';
next($array);
next($array);
var_dump(current($array));
list($a, $b, $c) = $array;
echo '$a = '.$a.'<br>$b = '.$b.'<br>$c = '.$c. '<br>';
echo reset($array).'<br>';
echo '数组的最后一个元素是:'.end($array).'<br>';
?>
2、数组的遍历
对数组中的每个元素按顺序逐个访问一次,称为数组的“遍历”。 对数组的遍历的方法主要是通过循环结构实现,具体可以因为访问数组元素的方法不同而不同。
while
循环遍历数组
<?php
$arr = array(1, 2, 3, 4, 5, 6);
// 注意 each 自 PHP 7.2.0 起废弃
while(list($key, $value) = each($arr)){
echo $value."<br>";
}
// 替代方案
do{
echo current($arr)."<br>";
}while(next($arr) !== false && key($arr) != null);
?>
for
循环遍历数组foreach
循环遍历数组
$arr = array(1, 2, 3, 4, 5, 6);
for($i = 0; $i < count($arr); $i++){
echo $arr[$i];
echo "<br>";
}
//注意for中的变量$i的作用域
echo $i;
foreach($arr as $value){
echo $value."<br>";
}
foreach($arr as $key => $a){
echo "key 是: ". $key . ";值是: ". $a;
echo current($arr);
}
//注意foreach 中的变量$a的作用域
echo $a;
四、数组的排序
1、升序排序
sort()
函数
sort()函数不仅对数组进行排序,同时删除了原来的键名,并重新分配自动索引的键名asort()
函数
asort()函数对数组的值进行升序排序,会保持键名与值之间的关联。ksort()
函数
ksort()函数对数组的键名进行升序排序,会保持键名与值之间的关联。<?php $arr = array("a" => 5, "x" => 3, 5 => 7, "e" => 1); sort($arr); var_dump($arr); $arr = array("a" => 5, "x" => 3, 5 => 7, "e" => 1); asort($arr); var_dump($arr); $arr = array("a" => 5, "x" => 3, 5 => 7, "e" => 1); ksort($arr); var_dump($arr); ?>
2、反向排序
rsort()
函数
与sort()函数用法相同,降序排序,会重新分配自动索引的键名arsort()
函数
与asort()函数用法相同krsort()
函数
与ksort()函数用法相同<?php $arr = array("a" => 5, "x" => 3, 5 => 7, "e" => 1); rsort($arr); var_dump($arr); $arr = array("a" => 5, "x" => 3, 5 => 7, "e" => 1); arsort($arr); var_dump($arr); $arr = array("a" => 5, "x" => 3, 5 => 7, "e" => 1); krsort($arr); var_dump($arr); ?>
3、对多维数组排序
array_multisort()
函数
array_multisort()函数可以一次对多个数组排序。- 第一个参数必须是数组
- 多个数组排序,数组数量要一致
- 如果是关联型数组,排序后键名不再重新索引
- 如果是数字索引型数组,排序后键名会重新索引
- 支持排序顺序标志
- SORT_ASC 为默认值,按照升序排序
- SORT_DESC 按照降序排序
- 排序类型标志:
- SORT_REGULAR 为默认值,按照通常方法比较
- SORT_NUMERIC 按照数值比较
- SORT_STRING 按照字符串比较
<?php
$base_code = array("0", "1", "2", "3", "4");
$arr = ["a" => 8, "b" => 6, "c" => 9, "d" => 7];
array_multisort($base_code, SORT_DESC);
//多个数组排序,数组数量要一致
array_multisort($base_code, SORT_DESC, $arr);
var_dump($base_code);
var_dump($arr);
//多维数组排序,
$arr = [
[ 11, 10, 100, 2, 30],
[1, 2, 2, 3, 1]
];
array_multisort($arr[0], SORT_ASC, $arr[1], SORT_DESC);
var_dump($arr);
?>
4、对数组重新排序
shuffle()
函数
shuffle()函数是将数组用随机的顺序排列,并删除原有的键名,建立自动索引。
<?php
//注意键名
$arr = array("a" => 5, "x" => 3, 5 => 7, "e" => 1);
shuffle($arr);
var_dump($arr);
//生成验证码
$base_code = array("0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "A", "B", "C", "D", "E", "F");
shuffle($base_code);
$iden_code = "";
for ($i = 0; $i < 4; $i++) {
$iden_code .= $base_code[$i];
}
echo $iden_code;
?>
五、数组常用操作
1、数组的合并与拆分
array_merge()
函数
此函数是把一个或多个数组合并为一个新数组。
语法结构:array_merge(array $... = ?): array
- 如果输入的数组中有相同的字符串键名,则该键名后面的值将覆盖前一个值。然而,如果数组包含数字键名,后面的值将 不会 覆盖原来的值,而是附加到后面。
- 如果输入的数组存在以数字作为索引的内容,则这项内容的键名会以连续方式重新索引。
<?php
$a1 = array("a"=>"red","b"=>"green"); //定义键值为字符串的数组
$a2 = array("c"=>"blue","b"=>"yellow");
$a3 = array("c"=>"blue","d"=>"yellow");
$a4= array("3"=>"blue","5"=>"yellow","7"=>"red","9"=>"green");
//键值为整数的数组
echo "<br>合并数组含有相同的字符串键值:<br>";
print_r(array_merge($a1,$a2));
//Array ( [a] => red [b] => yellow [c] => blue )
echo "<br><br>合并数组没有相同的字符串键值:<br>";
print_r(array_merge($a1,$a3));
//Array ( [a] => red [b] => green [c] => blue [d] => yellow )
echo "<br><br>合并键名为整数的单个数组:<br>";
print_r(array_merge($a4));
//Array ( [0] => blue [1] => yellow [2] => red [3] => green )
?>
2、数组的入栈与出栈
先入后出工作机制的数据结构成为栈,先入先出工作机制的称为堆。
array_push()
函数
array_push — 将一个或多个单元压入数组的末尾(入栈) 语法:array_push(array &$array, mixed $value1, mixed $... = ?): int
array_push() 将 array 当成一个栈,并将传入的变量压入 array 的末尾。array 的长度将根据入栈变量的数目增加。和$array[] = $var;
效果相同。
<?php
$stack = array("orange", "banana");
array_push($stack, "apple", "raspberry");
print_r($stack);
?>
array_pop()
函数
array_pop — 弹出数组最后一个单元(出栈)
语法:array_pop(array &$array): mixed
array_pop() 弹出并返回 array 数组的最后一个单元,并将数组 array 的长度减一。
注意: 使用此函数后会重置(reset())array 指针。
<?php
$stack = array("orange", "banana", "apple", "raspberry");
$fruit = array_pop($stack);
print_r($stack);
?>
在 PHP 开发过程中,有相当大的部分是与数组打交道,例如入库的内容、统计相关内容等操作都离不开数组,很多信息都是用数组作为载体的。所以数组的操作在 PHP 编程中占有很大的比重,只有熟练地操作数组才能更好的编写 PHP 程序。
除了前面我们介绍到的一些函数外,PHP 中还提供了很多特定功能的数组函数,有兴趣的同学可以访问 https://www.php.net/manual/zh/ref.array.php 来查看更详细的内容。
六、综合案例
1、王者荣耀数组输出
<?php
$heros = [
"安琪拉" => [
"皮肤" => ["暗夜萝莉", "玩偶对对碰", "魔法小厨娘"],
"技能" => [
"火球术" => [350, 390, 430],
"混沌火种" => [130, 145, 160],
"炽热光辉" => [700, 1050, 1400],
],
"语音" => ["知识就是力量", "一不小心就干掉了个大家伙!", "生命就像人家的魔法师~涂涂改改又是一年!"]
],
"亚瑟" => [
]
];
//过程式编程
$key = "安琪拉";
$hero = $heros[$key];
//random_int(0, 2)是生成随机数,随机数最小值是0,最大值是2
$pifu = $hero["皮肤"][random_int(0, 2)];
//array_keys是获取数组的中的key值,并组成一维数组,此处的结果是 ["火球术", "混沌火种", "炽热光辉"]
$jinengArrs = array_keys($hero["技能"]);
$jineng = $jinengArrs[random_int(0, 2)];
$shanghai = $hero["技能"][$jineng][random_int(0, 2)];
$yuyin = $hero["语音"][random_int(0, 2)];
echo "【".$pifu."】的【".$key."】对你使用了【".$jineng."】,造成了【".$shanghai."】点伤害,并对你说出了【".$yuyin."】";
?>
2、接收用户输入的学生学号、姓名、成绩等信息,排序显示
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>学生成绩</title>
</head>
<body>
<form action="" method="POST" style="width: 70%;margin-left:15%;">
<div id="items">
<div>
<span>学号:<input type="text" name="XH[]" placeholder="请输入学号"></span>
<span>姓名:<input type="text" name="XM[]" placeholder="请输入姓名"></span>
<span>成绩:<input type="text" name="CJ[]" placeholder="请输入成绩"></span>
</div>
</div>
<a id="add" href="javascript:;">+添加一行</a>
<input type="submit" value="提交" name="postSubmit" style="margin-top:30px;">
</form>
</body>
<script>
let add = document.getElementById("add");
add.onclick = function(){
let node = document.createElement("div");
node.innerHTML = `<div>
<span>学号:<input type="text" name="XH[]" placeholder="请输入学号"></span>
<span>姓名:<input type="text" name="XM[]" placeholder="请输入姓名"></span>
<span>成绩:<input type="text" name="CJ[]" placeholder="请输入成绩"></span>
</div>`;
let items = document.getElementById("items");
items.appendChild(node);
}
</script>
</html>
<?php
if(isset($_POST['postSubmit'])){
$XH = $_POST["XH"];
$XM = $_POST["XM"];
$CJ = $_POST["CJ"];
array_multisort($CJ, SORT_DESC, $XH, $XM);
echo "<hr>";
echo "成绩排序<br>";
for($i = 0; $i < count($CJ); $i++){
echo "学号:{$XH[$i]} 姓名:{$XM[$i]} 成绩:{$CJ[$i]}";
echo "<br>";
}
}
?>