1. find命令
1.1 根据文件或者正则表达式进行匹配
列出当前目录及子目录下所有文件和文件夹
find .
find /home -name "*.txt" #在/home目录下查找以.txt结尾的文件名
find /home -iname "*.txt" #同上, 但忽略大小写
当前目录及子目录下查找所有以.txt和.pdf结尾的文件
find . \( -name "*.txt" -o -name "*.pdf" \)
find . -name "*.txt" -o -name "*.pdf"
匹配文件路径或者文件
find /usr/ -path "*local*"
基于正则表达式匹配文件路径
指定正则规则: -regextype posix-extended
(type 类型包括 posix-awk, posix-basic, posix-egrep 和 posix-extended 四种, 默认的正则表达式类型是emacs)
find . -regex ".*\(\.txt\|\.pdf\)$"
find . -iregex ".*\(\.txt\|\.pdf\)$" #同上, 但忽略大小写
1.2 否定参数
找出/home下不是以.txt结尾的文件
find /home ! -name "*.txt"
1.3 根据文件类型进行搜索
find . -type 类型参数
参数 | 类型 |
---|---|
f | 普通文件 |
l | 符号连接 |
d | 目录 |
c | 字符设备 |
b | 块设备 |
s | 套接字 |
p | Fifo |
1.4 基于目录深度搜索
向下最大深度限制为3
find . -maxdepth 3 -type f
搜索出深度距离当前目录至少2个子目录的所有文件
find . -mindepth 2 -type f
1.5 根据文件时间戳进行搜索
find . -type f 时间戳
UNIX/Linux文件系统每个文件都有三种时间戳:
- 访问时间(-atime/天, -amin/分钟): 用户最近一次访问时间。
- 修改时间(-mtime/天, -mmin/分钟): 文件最后一次修改时间。
- 变化时间(-ctime/天, -cmin/分钟): 文件数据元(例如权限等)最后一次修改时间。
# 搜索最近七天内被访问过的所有文件
find . -type f -atime -7
# 搜索恰好在七天前被访问过的所有文件
find . -type f -atime 7
# 搜索超过七天内被访问过的所有文件
find . -type f -atime +7
# 搜索访问时间超过10分钟的所有文件
find . -type f -amin +10
# 找出比file.log修改时间更长的所有文件
find . -type f -newer file.log
1.6 根据文件大小进行匹配
find . -type f -size
文件大小单元
文件大小单元:
b —— 块(512字节)
c —— 字节
w —— 字(2字节)
k —— 千字节
M —— 兆字节
G —— 吉字节
# 搜索大于10KB的文件
find . -type f -size +10k
# 搜索小于10KB的文件
find . -type f -size -10k
# 搜索等于10KB的文件
find . -type f -size 10k
# 要列出所有长度为零的文件
find . -empty
1.7 删除匹配文件
删除当前目录下所有.txt文件
find . -type f -name "*.txt" -delete
1.8 根据文件权限/所有权进行匹配
# 当前目录下搜索出权限为777的文件
find . -type f -perm 777
# 找出当前目录下权限不是644的php文件
find . -type f -name "*.php" ! -perm 644
# 找出当前目录用户tom拥有的所有文件
find . -type f -user tom
# 找出当前目录用户组sunk拥有的所有文件
find . -type f -group sunk
1.9 借助-exec选项与其他命令结合使用
# 找出当前目录下所有root的文件, 并把所有权更改为用户tom
find .-type f -user root -exec chown tom {} \;
# -ok和-exec行为一样, 不过它会给出提示, 是否执行相应的操作。
find $HOME/. -name "*.txt" -ok rm {} \;
# 查找当前目录下所有.txt文件并把他们拼接起来写入到all.txt文件中
find . -type f -name "*.txt" -exec cat {} \;> all.txt
# 将30天前的.log文件移动到old目录中
find . -type f -mtime +30 -name "*.log" -exec cp {} old \;
# 找出当前目录下所有.txt文件并以“File:文件名”的形式打印出来
find . -type f -name "*.txt" -exec printf "File: %s\n" {} \;
# 因为单行命令中-exec参数中无法使用多个命令, 以下方法可以实现在-exec之后接受多条命令
-exec ./text.sh {} \;
1.10 搜索但跳出指定的目录
查找当前目录或者子目录下所有.txt文件, 但是跳过子目录sk
find . -path “./sk” -prune -o -name “*.txt” -print
1.11 find 逻辑运算符
- or
- and
- not
- () 将测试和运算符组合在一起以形成更大的表达式。
2. grep命令
选项 | 说明 |
---|---|
-R | 递归地搜索包含指定字符串的文件 |
-E | 使用扩展正则表达式 |
-w | 只显示包含特定单词的行 |
-l | 只输出文件名 |
-i | 大小写不敏感 |
-n | 显示指定字符串所在行的行号 |
-v | 寻找不包含指定字符串的文件 |
–include –exclude |
搜索时包含/排除指定文件 |
–exclude-dir | 排除指定目录 |
2.1 非递归搜索包含指定字符串的文件
第一个例子让我们来搜索 /etc/ 目录下所有包含 stretch 字符串的文件, 但不去搜索其中的子目录:
grep -s stretch /etc/*
/etc/os-release:PRETTY_NAME="Debian GNU/Linux 9 (stretch)"
/etc/os-release:VERSION="9 (stretch)"
grep 的 -s 选项会在发现不存在或者不能读取的文件时隐藏报错信息。结果显示除了文件名之外, 还有包含请求字符串的行也被一起输出了。
2.2 POSIX字符类
字符类 | 说明 |
---|---|
[:alnum:] | 等同于: [A-Za-z0-9] |
[:word:] | 与 [:alnum:] 相同, 并带有下划线(_)字符 |
[:alpha:] | 等同于[A-Za-z] |
[:blank:] | 包括空格和制表符 |
[:cntrl:] | ASCII控制代码, 包括ASCII字符0到31和127。 |
[:digit:] | 数字0-9 |
[:graph:] | 可见字符, 在ASCII中它包含从33到126的字符。 |
[:lower:] | 小写字母 |
[:upper:] | 大写字母 |
[:punct:] | 标点符号, 以ASCII表示, 相当于: [-!"#$%&’()*+,./:;<=>?@[\]_`{ |
[:print:] | 可打印的字符, [:graph:]中的所有字符加上空格字符。 |
[:space:] | 等同于: [ \t\r\n\v\f] |
[:xdigit:] | 用于表示十六进制数字的字符, 等同于[0-9A-Fa-f] |
3. 快速搜索命令: which 和 locate
搜索文件的最简单的命令可能就是 which 和 locate 了, 但二者都有一些局限性。which 命令只会在系统定义的搜索路径中, 查找可执行的文件, 通常用于识别命令。如果您对输入 which 时会运行哪个命令感到好奇, 您可以使用命令 which which, 它会指出对应的可执行文件。
which which
/usr/bin/which
which 命令会显示它找到的第一个以相应名称命名的可执行文件(也就是使用该命令时将运行的那个文件), 然后停止。
locate 命令更大方一点, 它可以查找任意数量的文件, 但它也有一个限制: 仅当文件名被包含在由 updatedb 命令构建的数据库时才有效。该文件可能会存储在某个位置, 如 /var/lib/mlocate/mlocate.db, 但不能用 locate 以外的任何命令读取。这个文件的更新通常是通过每天通过 cron 运行的 updatedb 进行的。