1.读取文件行
1.1 读取最后一行
awk 'END {print}'sed -n '$p'
1.2 读取最后两行
sed '$!N;$!D'awk '{b=a"\n"$0;a=$0}END{print b}'
2.判断
| 标识 |
意义 |
适用范围 |
| -z “$str1” |
当串的长度为0时则为真 |
字符串 |
| -n “$str2” |
当串的长度大于0时则为真 |
字符串 |
| “$str1” |
当串为非空时则为真(与上等价) |
字符串 |
| “$str1” = “$str2” |
当两个串有相同内容和长度时则为真 |
字符串 |
| “$str1” == “$str2” |
当两个串有相同内容和长度时则为真(严格相等) |
字符串 |
| “$str1” != “$str2” |
当两个串不等时则为真 |
字符串 |
| “$str1” < “$str2” |
str1排序后在str2之前则为真 |
字符串 |
| “$str1” > “$str2” |
str1排序后在str2之后则为真 |
字符串 |
| “$int1” -eq “$int2” |
两数相等则为真 |
数字 |
| “$int1” -ne “$int2” |
两数不等则为真 |
数字 |
| “$int1” -gt “$int2” |
int1大于int2则为真 |
数字 |
| “$int1” -ge “$int2” |
int1大于等于int2则为真 |
数字 |
| “$int1” -lt “$int2” |
int1小于int2则为真 |
数字 |
| “$int1” -le “$int2” |
int1小于等于int2则为真 |
数字 |
| -a FILE |
如果FILE存在则为真 |
文件 |
| -b FILE |
如果FILE存在且是一个块特殊文件则为真 |
文件 |
| -c FILE |
如果FILE存在且是一个字特殊文件则为真 |
文件 |
| -d FILE |
如果FILE存在且是一个目录则为真 |
文件 |
| -e FILE |
如果FILE存在则为真 |
文件 |
| -f FILE |
如果FILE存在且是一个普通文件则为真 |
文件 |
| -g FILE |
如果FILE存在且已经设置了SGID则为真 |
文件 |
| -h FILE |
如果FILE存在且是一个符号连接则为真 |
文件 |
| -k FILE |
如果FILE存在且已经设置了粘制位则为真 |
文件 |
| -p FILE |
如果FILE存在且是一个名字管道则为真 |
文件 |
| -r FILE |
如果FILE存在且是可读的则为真 |
文件 |
| -s FILE |
如果FILE存在且大小不为0则为真 |
文件 |
| -u FILE |
如果FILE存在且设置了SUID(set user ID)则为真 |
文件 |
| -w FILE |
如果FILE存在且是可写的则为真 |
文件 |
| -x FILE |
如果FILE存在且是可执行的则为真 |
文件 |
| -O FILE |
如果FILE存在且属有效用户ID则为真 |
文件 |
| -G FILE |
如果FILE存在且属有效用户组则为真 |
文件 |
| -L FILE |
如果FILE存在且是一个符号连接则为真 |
文件 |
| -N FILE |
如果FILE存在前且最后一次打开时被修改了则为真 |
文件 |
| -S FILE |
如果FILE存在且是一个套接字则为真 |
文件 |
| FILE1 -nt FILE2 |
如果FILE1比FILE2要新或者FILE1存在而FILE2不存在则为真 |
文件 |
| FILE1 -ot FILE2 |
如果FILE1比FILE2要老或者FILE2存在而FILE1不存在则为真 |
文件 |
| FILE1 -ef FILE2 |
如果FILE1和FILE2指向相同的设备和节点号则为真 |
文件 |
| -t FD |
如果文件描述符FD打开且指向一个终端则为真 |
文件描述符FD |
| -o OPTIONNAME |
如果shell选项”OPTIONNAME”开启则为真 |
shell |
| -a |
与 |
逻辑 |
| -o |
或 |
逻辑 |
| ! |
非 |
逻辑 |
-z “$str1”等类似情况一定要用双引号,不然会出现判断错误(这块可以多研究下各种情况下的表现)
3.区分操作系统
| 命令 |
结果(Mac) |
结果(Linux) |
| uname |
Darwin |
Linux |
| uname -a |
Darwin bogon 17.3.0 Darwin Kernel Version 17.3.0: Thu Nov 9 18:09:22 PST 2017; root:xnu-4570.31.3~1/RELEASE_X86_64 x86_64 |
Linux 13c1548ff7bb 4.9.125-linuxkit #1 SMP Fri Sep 7 08:20:28 UTC 2018 x86_64 x86_64 x86_64 GNU/Linux |
| uname -m |
x86_64 |
x86_64 |
| uname -n |
bogon |
13c1548ff7bb(容器ID) |
| uname -p |
i386 |
x86_64 |
| uname -r |
17.3.0 |
4.9.125-linuxkit |
| uname -s |
Darwin |
Linux |
| uname -v |
Darwin Kernel Version 17.3.0: Thu Nov 9 18:09:22 PST 2017; root:xnu-4570.31.3~1/RELEASE_X86_64 |
#1 SMP Fri Sep 7 08:20:28 UTC 2018 |
4.sed命令
4.1 删除
1.说明# d标识为删除buffer# 删除语法一般为sed 'ADDRESS'd filenamesed /PATTERN/d filename# 要删除的串可以用以下三种方式表示nd(最后一行无法使用该形式,$d会报错,要加引号)'nd''n'd2.删除第n行sed nd filename3.从第n行开始,每隔m行删除(mac无法使用,m=0代表从第n行开始,直接删除到末尾)sed n~m+1d filename4.删除从第n行到第m行sed n,md filename5.删除最后一行($代表最后,使用$时一定要加引号,'$d'和'$'d都行,不加报错)sed '$d' filename6.行匹配删除(包含该字符串的所有行)sed '/System/d' filename7.删除从匹配行到末尾sed '/System/,$d' filename8.删除匹配行之后n行(匹配行也算在n之内,mac无效,无论n多大,只会删除匹配行)sed '/System/,+nd' filename9.清除空行sed '/^$/d' filename10.正则删除sed '/System.*/d' filename11.对原文件生效加-i才可以对文件进行真正的更改
4.2 插入
# 从第n行后添加内容1.linux系统# 直接添加一行,之后的行会下移# 方式一(一定要单引号,双引号不支持)sed -e na\\'newLine String\' filename# 方式二sed -e 'na newLine String' filename2.mac系统# 内容会新起一行,但之前的行内容不会下移一行,而是会放在新插入内容之后sed 'na\'$'\n''newLine String' filename# 在n行前插入,之前的内容不会下移一行,而是会放在新插入内容之后sed 'ni\'$'\n''newLine String' filename# a与i的区别在于i在n行首插入,并挤压原内容,而a在n行后新起行插入,并挤压n行下一行内容
4.3 修改
1.把world1改成world0,s表示替换,g表示全局(这里有没有g效果一样)sed "s/world1/world0/" filename2.把第2行,第4行所有的hello替换为welcomesed "2,4s/hello/welcome/" filename3.找到world3所在行,把所有的hello替换为welcome(不加g只会替换第一个)sed "/world3/s/hello/welcome/g" filename4.正则匹配修改,把所有的world+一个数字改成beijing(不加g则world10及以上都不会匹配到,而加g则会匹配到,world10->bejing0,world11->beijing1)sed "s/world[0-9]/beijing/g" filename5.变量 \(.*\)会匹配出一个变量,\1表示第一个变量,\2表示第二个变量,以下相当于交换-符号左右两边字符的位置sed "s/\(.*\)-\(.*\)/\2-\1/g" filename6.把2-5行替换为字符串China(第6行会紧接着China)sed '2,5c\'$'\n''China' filename
4.4 查看
# p打印buffer(记得使用时加上-n选项)1.查看最后一行内容sed -n '$p' filename2.查看第一行内容sed -n '1p' filename3.查看第一行到第二行内容sed -n '1,3p' filename4.查看所有包含beijing所在的行sed -n '/beijing/p' filename
4.5 读取和写入数据
1.把filename2的内容放在filename1的第一行之后(另起一行,内容添加完比后再另起一行接原内容),r进行读取写入filename1,返回修改过后的filename1,filename2保持不变sed "1r filename2" filename12.把filename1的第一行内容覆盖写入到filename2,返回filename1无变化,查到filename2只有filename1的第一行,可衍生出5.3sed "1w filename2" filename13.把filename1的第3-5行数据,写入到filename2中sed "3,5w filename2" filename1
4.6 平台差异
# sed命令在mac系统中和linux系统中表现不一样,具体为第1点删除时的1.3和1.7中表现,另外1.10对文件生效处理方式也不一样1.mac系统# -i后面强制要接备份文件,如果不想备份,直接写''即可,写了备份文件名称,则生成的完整备份文件名为filenamebackfilename,连文件后缀也连在一起sed -i backfilename '$d' filename2.linux系统sed -i '$d' filename