目 录
一、数组
1、数组的定义
注意:在shell语句中,使用、遍历数组的时候,数组格式要写成 ${arr[@]} 或 ${arr[*]}
图示:
2、定义数组的方法
1: 法一:#默认数组下标从0开始
数组名=(value0 value1 value2 ... )
2: 方法二:
#数组下标索引可以自己设置
数组名=([0]=value [1]=value [2]=value ... )
3:
方法三:
先定义列表名,再转成数组
列表名="value0 value1 value2 ..."
数组名=($列表名)
4:
方法四:
#一般用于for/while循环进行复制
数组名[0]="value"
数组名[1]="value"
数组名[2]="value"
3、数组的数据类型
- 数值类型
- 字符类型:使用" "或’ '定义
4、获取数组长度
aa=(1 2 3 4 5)
echo ${#aa[*]}
# echo ${#数组名[*]} 或 echo ${#数组名[@]}
5、获取数据列表
数组名=(元素0 元素1 元素2 ……) 定义数组
echo ${数组名[*]} 或 echo ${数组名[@]} 获取数据列表可以用echo ${数组名[*]}或echo ${数组名[@]}
6、获取某下标赋值
数组名=(元素0 元素1 元素2 ……) 定义数组
echo ${数组名[索引值]} 输出数组索引值对应的元素,索引值为从0开始
数组的常用操作
1、遍历
#!/bin/bash
bb=(10 20 30 40 50) 定义数组
for i in ${bb[@]} for循环将数组arr内的元素依次赋值给变量i
do
echo $i 依次输出变量i的值
done
2、切片
数组名=(元素0 元素1 元素2 ……) #定义数组
echo ${bb[@]} #输出整个数组
echo ${bb[@]:索引下标:长度} #获取${数组名[@或*]:起始位置的索引下标:长度}的元素的值
echo ${bb[*]:索引下标:长度}
3、替换
数组名=(元素0 元素1 元素2 ……) 定义数组
echo ${数组名[@或*]/查找字符/替换字符} ${数组名[@或*]/要查找的字符/要替换的字符}
echo ${数组名[*]} 输出整个数组,并不会替换数组原有内容
数组名=(数组名{*}/查找字符/替换字符) 要实现改变原有数组,可以通过重新赋值实现
echo ${数组名[*]} 输出整个数组,替换数组原有内容
4、删除
数组名=(元素0 元素1 元素2 ……) 定义数组
unset 数组名[索引下标] 删除数组中索引下标所对应的的元素
unset 数组名 删除整个数组
5、数组追加元素
【方法一】
直接赋值,index是数组中的新下标
array_name[index]=value
【方法二】
和方法一一样,用${#}获取数组长度作为新增的数组下标
array_name[${#array_name[@]}] =value
【方法三】
在现有数组的基础上,在后面追加元素,赋给新数组
array_name=("${array_name[@]}" value1 ... valueN)
注意,使用方法三时:
1. 参数中的 双引号不能省略,否则,当数组 array_name 中包含空格的元素时会按空格将元素拆分成多个
2. 也不能将 [@] 替换成 [*] ,如果替换为 [*],不加双引号时与 [@] 时的表现一致
加双引号时,会将数组array_name中的所有元素作为一个元素添加到数组中。
【方法四】
在现有数组的基础上,在后面追加元素
array_name+=(value1 ... valueN)
注意:待添加元素必须用 () 括号包围起来,并且多个元素用空格分隔
6、向函数传数组参数
注意:如果只将数组名作为变量传给函数,函数只会取数组变量的第一个元素。
1.先将数组拆分成列表 ${arr[@]}
2.函数通过$@获取之前将数组拆分成的列表 $@
3.在函数中重新把列表定义成数组 newarr=($@)
4.对新的数组进行进一步的处理,在echo输出
#!/bin/bash
test () {
echo "函数接收到的参数列表为:$@" $@代表参数列表$arr
newarr=($1)
echo "函数中新的数组的值为:${newarr[@]}"
}
arr=(10 20 30 40 50)
echo "原始的数组列表为:${arr[@]}"
test $arr
7、从函数返回数组
#!/bin/bash
#从函数返回数组
#用于求数组中所有元素值得累加和
test1 () {
newarr=($@)
arrlist=${newarr[*]}
sum=0
for i in $arrlist
do
sum=$[sum+i]
done
echo $sum
}
#用于把原数组中所有的元素值乘2后生成一个新的数组并输出
test2 (){
newarr1=($@)
length=${#newarr1[@]}
for ((j=0;j<=$length-1;j++))
do
newarr1[$j]=$[${newarr1[$j]}*2]
done
echo ${newarr1[*]}
}
#########main#########
array=(10 20 30 40 50)
echo "原数组的列表为:${array[@]}"
res1=`test1 ${array[@]}`
echo "test1中的新数组的累加和为:$res1"
res2=$(test2 ${array[@]})
echo "test2中的新数组的值为:$res2"
三、数组排序算法
1、冒泡排序
比较两个相邻的元素,将值大的元素交换到右边
依次比较相邻的两个数,将比较小的数放在前面,比较大的数放在后面
#arr=(8 5 9 3 4)
read -p "请输入一个数组:" arry
#列表转数组,获取数组长度
arr=($arry)
length=${#arr[@]}
#定义比较轮数,长度-1,比如五个数,比较四轮即可
for ((i=1; i<$length; i++))
do
#确定内次比较的次数,随着i的增大而降低,因为每轮比较后,最大/小的数已经在末尾了
for((j=0; j<$length-$i; j++))
do
#获取每次用于比较的第一个、第二个数
first=${arr[$j]}
k=$[$j+1]
second=${arr[$k]}
#比较,如果前一个比后一个数大,则替换,如果是 if [ $first -lt $second ];then,则从大到小排序
if [ $first -gt $second ];then
tem=${arr[$j]}
arr[$j]=${arr[$[$j+1]]}
arr[$[$j+1]]=$tem
fi
done
done
echo "从小到大排序为:"${arr[@]}
2、直接选择排序
基本思想:
将指定排序位置与其它数组元素分别对比,如果满足条件就交换元素值,注意这里区别冒泡排序,不是交换相邻元素,而是把满足条件的元素与指定的排序位置交换(如从最后-~个元素开始排序),这样排序好的位置逐渐扩大,最后整个数组都成为已排序好的格式
#直接选择排序函数
function selectsort(){
#列表转换成数组
arr=($@)
length=${#arr[@]}
for((i=1; i<$length; i++)) #定义排序轮训次数,比如五个数只要排序四趟
do
index=0
#确定当前排序 实际最大元素的下标,从第二个元素开始比较,每次都比上次少比一次
for((j=1; j<=length-i; j++))
do
if [ ${arr[$j]} -gt ${arr[$index]} ];then #如果是从大到小,用 -lt
index=$j #如果下一个比当前index大,就把大的值给index
fi
done
#遍历完成,此时下标为index的 就是当前最大的元素
#把当前比出来的index元素的值 和当前轮循的最后一个元素进行替换
k=$[$length-$i]
tmp=${arr[$k]}
arr[$k]=${arr[$index]}
arr[$index]=$tmp
done
#别忘了返回数组
echo ${arr[@]}
}
########## mian ##########
read -p "请输入一个数组:" arry
#将列表传给选择排序函数,并获取返回的数组值
select_rest=`selectsort $arry`
echo "选择排序后的数组为:"${select_rest[@]}
3、反转排序
基本思想
把数组最后一个元素与第一个元素替换,倒数第二个元素与第二个元素替换,依次类推,直到把所有数组元素反转替换
#数组反转函数
function reversal(){
arr=($@)
length=${#arr[@]}
for((i=0; i<$length/2; i++))
do
#第一个与倒数第一个替换,第二个与倒数第二个替换
tmp=${arr[$i]}
arr[$i]=${arr[$length-1-i]}
arr[$length-1-i]=$tmp
done
echo ${arr[@]}
}
#############main##########
read -p "请输入一个数组:" arry
result=`reversal $arry`
echo "反转后的数组为:"${result[@]}
4、希尔排序
希尔排序(Shell Sort)是插入排序的一种算法,是对直接插入排序的一个优化,也称缩小增量排序。
基本思想
希尔排序是将待排序的数组元素 按下标的一定增量分组 ,分成多个子序列,然后对各个子序列进行直接插入排序算法排序;然后依次缩减增量再进行排序,直到增量为1时,进行最后一次直接插入排序,排序结束。
#!/bin/bash
arr=(7 6 8 3 1 5 2 4)
echo "当前数组元素顺序为:${arr[@]}"
length=${#arr[*]}
#把距离为gap的元素编为一个组,扫描所有组,每次循环减少增量
for ((gpg=$length/2;gpg>0;gpg/=2))
do
#对距离为gpg的元素进行排序,每一轮比较拿当前轮次最后一个元素与组内其他元素比较,将数组大的放在后面
for((i=gpg;i<length;i++))
do
temp=${arr[$i]}
for ((j=i-gpg;j>=0&&temp<${arr[$j]};j-=gpg))
do
arr[$j+$gpg]=${arr[$j]}
done
#和最左边较大的元素调换位置
arr[$j+$gpg]=$temp
done
done
echo "排序后的数组元素顺序为:${arr[*]}"