下篇文章:嵌入式开发 Linux 常用命令系列 2-- tmux 终端多窗口
find 语法:
find [path] [expression]
path 是要查找的目录路径,可以是一个目录或文件名,也可以是多个路径,多个路径之间用空格分隔,如果未指定路径,则默认为当前目录。
expression 是可选参数,用于指定查找的条件,可以是文件名、文件类型、文件大小等等。
expression 中可使用的选项有二三十个之多,以下列出最常用的部份:
-name pattern
:按文件名查找,支持使用通配符 *
和 ?
。
find . -name "*.c"
;-type type
:按文件类型查找,可以是 f
(普通文件)、d
(目录)、l
(符号链接)等。-size [+-]size[cwbkMG]
:按文件大小查找,支持使用 + 或 - 表示大于或小于指定大小,单位可以是 c(字节)、w(字数)、b(块数)、k(KB)、M(MB)或 G(GB)。
find /home -size +1M
,查找 /home 目录下大于 1MB 的文件。-mtime days
:按修改时间查找,支持使用 + 或 - 表示在指定天数前或后,days 是一个整数表示天数。
find /var/log -mtime +7
查找 /var/log 目录下在 7 天前修改过的文件-user username
:按文件所有者查找。-group groupname
:按文件所属组查找。-o
: 在find命令中可以用-o选项来表示逻辑"或"操作。
.txt
"文件或者".jpg
"文件,你可以使用以下命令:find . \( -name "*.txt" -o -name "*.jpg" \)
。另外,注意我们使用了 \(和\) 来组合这两个条件,因为find命令的逻辑操作符优先级是 “并” 高于 “或”,使用这两个符号可以确保逻辑"或"操作符的正确解析和执行。find 命令中用于时间的参数如下:
-amin n
:查找在 n 分钟内被访问过的文件。-atime n
:查找在 n*24 小时内被访问过的文件。-cmin n
:查找在 n 分钟内状态发生变化的文件(例如权限)。-ctime n
:查找在 n*24 小时内状态发生变化的文件(例如权限)。-mmin n
:查找在 n 分钟内被修改过的文件。-mtime n
:查找在 n*24 小时内被修改过的文件。在某种类型的文件中搜索关键字符串可以使用下面命令,比如在 .txt
文件中搜索字符串“findme”
。
find . -name "readme.txt" | xargs grep -rin "findme"
相对于 -name
,-iname
不会去区分文件名的大写。
find . -iname "Readme.txt" | xargs grep -rin "findme"
numb-1:~/kernel/linux$ find . -iname "Readme.txt" | xargs grep -rin "findme"
./readme.txt:1:fiNdme
-prune参数用于在find命令中排除掉某些目录或文件。基本上,-prune
参数告诉find
停止在当前路径下深入搜索。它是一个action,就像-print
或-delete
。
例如,如果你想要搜索整个系统中的所有.txt
文件,但希望排除掉"/path/to/exclude"
目录,你可以使用如下命令:
find / -name "*.txt" -path "/path/to/exclude" -prune -o -print
这个命令的工作原理如下:
find / -name "*.txt"
:在根目录(/
)下搜索所有的.txt文件。-path "/path/to/exclude" -prune
:如果找到的路径是"/path/to/exclude
",那么就忽略这个路径及其下面的所有内容。-o -print
:对于不被忽略的路径,打印出来。注意:条件和操作在find
命令中是按照顺序判断和执行的,所以"-prune
"需要放在你想忽略的路径之后,而打印出来的操作(如-print
)需要放在-o
之后,表示如果前面的条件不满足(即路径不是被忽略的路径),那么就执行打印操作。
通过上一节的命令虽然可以在很多文件中搜索到关键字符串,但是文件太多不好定位,可以使用 grep -v "xxx"
命令来过滤掉输出结果中包含 “xxx”
的文件。
find . -iname "Readme.txt" | xargs grep -rin "findme" | grep -v "notme"
在linux 代码下查找 __iomem
的定义:
find ./ -type d -iname "arm*" -o -iname "include" | xargs grep -irn "__iomem" | grep "define"
上面命令的含义:找到目录名带arm
的目录和 include
目录,使用grep
搜索这两个目录下文件中含有 __iomem
的文件,再次过滤出含有define
的字符串,结果如下:
./include/linux/compiler_types.h:11:# define __iomem __attribute__((noderef, address_space(__iomem)))
./include/linux/compiler_types.h:37:# define __iomem
xargs
通常与管道|
一起使用,以处理生成大量结果的命令(如find
或grep
)。
花括号{}
在xargs
命令中通常用作一个占位符,表示xargs
命令在处理输入时要替换的位置。
例如,如果你有一个命令find / -name "*.log" | xargs -I {} mv {} /var/log/
,这个命令会查找系统中所有扩展名为.log
的文件,并将其移动到/var/log/
目录下。在这个例子中的-I {}
表示将find
命令的输出(即“.log”文件)作为mv
命令的输入,并将该输出替换到{}
的位置。
简单来说,{}
在xargs
中的作用就是标记输入在最终命令中的位置,xargs
会将其替换为实际的输入。
找到.ko
后缀的文件并将其拷贝到家目录下的demo目录:
find . -name "*.ko" | xargs -I{} cp "{}" ~/demo/
-exec
和xargs
都是处理文件和文件夹的强大工具,在Linux命令行中经常出现。它们都可以用来将一个命令应用到由其他命令(如find)生成的一组文件上。然而,它们在行为和性能上有一些关键的区别。
-exec
是f ind命令的一个选项,用来对匹配的每个文件执行特定的命令。例如,将所有.txt文件移动到一个新的目录可以这样写:
find . -name "*.txt" -exec mv {} ./new_directory/ \;
在这个命令中,{}
代表find找到的每个文件,而\;
表示-exec
的结束。
与此相反,xargs
是一个独立的命令,它的输入是一个命令的输出,然后将其作为参数传递给另一个命令。例如,使用xargs删除所有.txt文件可以这样写:
find . -name "*.txt" | xargs rm
在这个命令中,find找到的每个文件名都被传递给xargs,然后xargs将这些文件名作为rm命令的参数。
关于性能,当处理大量文件时,xargs
通常比-exec
更高效。这是因为-exec
会为每个文件单独创建一个新的进程来执行命令,而xargs
则会尽可能地把多个文件名打包成一组,然后在一个进程中执行命令。这意味着,如果你有数千或数百万个文件要处理,使用xargs
通常会更快。
然而,-exec
在处理含有空格、换行或其他特殊字符的文件名时,比xargs更安全和可靠。当然,如果使用xargs -0
和find -print0
,也可以安全地处理这些特殊文件名。