# 文件查找命令
## 1.which-whereis-locate-grep-find 命令使用

<font color='red'>which</font>&nbsp; &nbsp;&nbsp; &nbsp;&nbsp; &nbsp;查看命令的可执行文件位置

whereis&nbsp; &nbsp;&nbsp; &nbsp;查看命令的可执行文件位置及相关文件

locate&nbsp; &nbsp;&nbsp; &nbsp;&nbsp; &nbsp;配合数据库缓存，快速查看文件位置

<font color='red'>grep</font>&nbsp; &nbsp;&nbsp; &nbsp;&nbsp; &nbsp;&nbsp;&nbsp;过滤匹配，它是一个文件搜索工具

<font color='red'>find</font>&nbsp; &nbsp;&nbsp; &nbsp;&nbsp; &nbsp;&nbsp; &nbsp;查找相关文件



    [root@exercise1 ~]# which cd
    /usr/bin/cd
    [root@exercise1 ~]# whereis cd
    cd: /usr/bin/cd /usr/share/man/man1/cd.1.gz /usr/share/man/mann/cd.n.gz
    [root@exercise1 ~]# whereis ls
    ls: /usr/bin/ls /usr/share/man/man1/ls.1.gz
    [root@exercise1 ~]# 



## 2.locate

**语法： locate 文件/目录名**

**locate 命令和find -name 功能差不多，是它的另外一种写法，但是这个要比 find 搜索快的多，因为 find 命令查找的是具体目录文件，而 locate 它搜索的是一个数据库<font color='red'>/var/lib/mlocate/mlocate.db</font> ，这个数据库中存有本地所有的文件信息；这个数据库是 Linux 自动创建并每天自动更新维护。相关的配置信息在<font color='red'>/etc/updatedb.conf</font>， 查看定时任务信息在<font color='red'>/etc/cron.daily/mlocate</font>**

**优点：基于数据库查询，效率非常高**

**缺点：查询时要确保数据库是最新的，否则查找可能不正确**




    [root@exercise1 ~]# locate
    -bash: locate: 未找到命令
    [root@exercise1 ~]# yum search locate
    [root@exercise1 ~]# yum -y install mlocate.x86_64
    [root@exercise1 ~]# locate /opt/   #没有更新数据库文件
    locate: 无法执行 stat () `/var/lib/mlocate/mlocate.db': 没有那个文件或目录
    [root@exercise1 ~]# updatedb   #如果对当天文件查找，需要手动更新数据库 updatedb
    [root@exercise1 ~]# touch /opt/test.txt
    [root@exercise1 ~]# locate /opt/test.txt   #发现找不到
    [root@exercise1 ~]# updatedb
    [root@exercise1 ~]# locate /opt/test.txt   #更新过后可以查询到
    /opt/test.txt
    [root@exercise1 ~]# 

解决缺点方法：

    [root@exercise1 ~]# alias locate='updatedb && locate'   #临时别名
    [root@exercise1 ~]# vim ~/.bashrc   #当前用户生效
    #插入这条别名命令
    alias locate='updatedb && locate'
    [root@exercise1 ~]# source ~/.bashrc   #刷新生效
    [root@exercise1 ~]# vim /etc/bashrc   #全局使用
    #插入这条别名命令
    alias locate='updatedb && locate'



## 3.grep 查找使用(脚本三剑客之一)

作用：过滤,它能够使用正则表达式来搜索文本，并把结果打印出来

```
[root@home opt]# which grep
alias grep='grep --color=auto'
	/usr/bin/grep
如何临时修改关键字颜色
#a,b的意义分别表示加颜色的方式和颜色值
export GREP_COLOR='a;b'

a可以选择:【0,1,4,5,7,8】 0关闭所有属性; 1设置高亮度; 4下划线; 5闪烁; 7反显; 8消隐; 也不知道为什么没有2,3,6,9
b可以选择:【30-37或40-47】
30 black
31 red
32 green
33 yellow
34 blue
35 purple
36 cyan
37 white
30—37 设置前景色
40—47 设置背景色
```



参数：


``` 
    -v   取反
    
    -A   后接行数n：可以显示关键字后几行的内容
    
    -i   忽略大小写 
    
    ^#    以#开头 
    
    #$    以#结尾 
    
    ^$    空行
    
    -n 对过滤的内容加上行号 
    
    -o 只显示被匹配到的内容
    
    |   或者的意思
    
    -w   精确匹配
    
    -r     递归,一般跟-l参数连用
    
    -l     查看某一目录下含有文件内容
    
    -E		支持正则表达式
```

例子

    例1：
    [root@exercise1 opt]# vim a.txt
    #插入以下内容
    aaa
    bbb
    ccc
    ddd
    abcd
    [root@exercise1 opt]# cat a.txt 
    aaa
    bbb
    ccc
    ddd
    abcd
    [root@exercise1 opt]# grep a a.txt 
    aaa
    abcd
    [root@exercise1 opt]# 


​    
​    例2：
​    [root@exercise1 opt]# grep -v b a.txt 
​    aaa
​    ccc
​    ddd
​    [root@exercise1 opt]#


​    
​    例3：
​    [root@exercise1 opt]# grep ^# /etc/ssh/sshd_config   #以“#”开头

$OpenBSD: sshd_config,v 1.100 2016/08/15 12:32:04 naddy Exp $

This is the sshd server system-wide configuration file.  See


​    
​    
​    例4：
​    [root@exercise1 opt]# echo Abcd >> /opt/a.txt 
​    [root@exercise1 opt]# grep -i a a.txt 
​    aaa
​    abcd
​    Abcd
​    [root@exercise1 opt]# 


​    
​    
​    例5：
​    [root@exercise1 opt]# grep bash$ /etc/passwd   #以 bash 结尾
​    root:x:0:0:root:/root:/bin/bash
​    lin05:x:1112:1112::/home/lin05:/bin/bash
​    [root@exercise1 opt]# 


​    
​    
​    例6：
​    [root@exercise1 opt]# grep -n a a.txt 
​    1:aaa
​    5:abcd
​    [root@exercise1 opt]# 


​    例7：

```sh
[root@exercise1 opt]# grep "nologin\|root" /etc/passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
……  
#注： \ 表示转义符

[root@exercise1 opt]# egrep "nologin|root" /etc/passwd   #查看包括 nologin 或 root 的行
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
……
 
#注：egrep 是 grep 加强版本

[root@exercise1 opt]# grep -E "nologin|root" /etc/passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
……
```




   

  



​    例8：
​    [root@exercise1 opt]# grep -w "3306\|80" /etc/services 
​    http            80/tcp          www www-http    # WorldWideWeb HTTP
​    http            80/udp          www www-http    # HyperText Transfer Protocol
​    http            80/sctp                         # HyperText Transfer Protocol
​    mysql           3306/tcp                        # MySQL
​    mysql           3306/udp                        # MySQL


​    
​    例9：
​    [root@exercise1 opt]# grep -rl "root" /etc/
​    /etc/grub.d/00_header
​    /etc/grub.d/01_users
​    ……


​    
​    
​    例10：只将/etc/ssh/sshd_config文件的配置项列出来并显示行号
​    [root@exercise1 opt]# grep -v "^#\|^$" /etc/ssh/sshd_config 
​    HostKey /etc/ssh/ssh_host_rsa_key
​    HostKey /etc/ssh/ssh_host_ecdsa_key
​    HostKey /etc/ssh/ssh_host_ed25519_key
​    SyslogFacility AUTHPRIV
​    AuthorizedKeysFile	.ssh/authorized_keys
​    PasswordAuthentication yes
​    ChallengeResponseAuthentication no
​    GSSAPIAuthentication yes
​    GSSAPICleanupCredentials no
​    UsePAM yes
​    X11Forwarding yes
​    AcceptEnv LANG LC_CTYPE LC_NUMERIC LC_TIME LC_COLLATE LC_MONETARY LC_MESSAGES
​    AcceptEnv LC_PAPER LC_NAME LC_ADDRESS LC_TELEPHONE LC_MEASUREMENT
​    AcceptEnv LC_IDENTIFICATION LC_ALL LANGUAGE
​    AcceptEnv XMODIFIERS
​    Subsystem	sftp	/usr/libexec/openssh/sftp-server
​    [root@exercise1 opt]# 
​    
    或者
    
    [root@exercise1 opt]# cat /etc/ssh/sshd_config | grep -v ^# | grep -v ^$
    HostKey /etc/ssh/ssh_host_rsa_key
    HostKey /etc/ssh/ssh_host_ecdsa_key
    ……



## 4.find 命令使用 （必会，参数比较多）
**格式：find  pathname     -options    [-print]     [action]	** 		

​          **命令字   路径名称       选项         输出内容	  动作**

**参数：**

**pathname:   find 命令所查找的目录路径，不输入代表当前目录例如用 . 来表示当前目录，用 / 来表示系统 根目录。**


---
**find 命令选项:**

```
-name       按照文件名查找文件。     “名称”

-perm       按照文件权限来查找文件。666 777 等

-user       按照文件属主来查找文件

-group      按照文件所属的组来查找文件

-mtime      -n / +n  按照文件的更改时间来查找文件， 
            - n 表示文件更改时间距现在 n 天以内
            + n 表示文件更改时间距现在 n 天以前
           
-atime      按照文件的访问时间来查找文件

-ctime      按照文件的属性更改时间来查找文件

-type       查找某一类型的文件 

b - 块设备文件     

d -  目录          

c - 字符设备文件     

p - 管道文件         

l - 符号链接文件      

f - 普通文件

-maxdepth      查找的目录深度

-size n   查找符合指定的文件大小的文件   +大于  -小于

-exec     对匹配的文件执行该参数所给出的其他 linux 命令，相应命令的形式为' 命令 {} \;，注意{ }和 \；
之间的空格，{}代表查到的内容

```

例子

    例1：查看当前目录下所有的 TXT 格式的文件
    [root@exercise1 opt]# find . -name "*.txt"
    ./a.txt
    [root@exercise1 opt]# 



    例2：按权限查找
    [root@exercise1 opt]# find /bin/ -perm 755   #等于 0755 权限的文件或目录
    [root@exercise1 opt]# find /bin/ -perm -644   #-perm -644   至少有 644 权限的文件或目录


​    
​    #查看系统中权限至少为 777 的文件或目录 
​    #创建一些测试文件： 
​    [root@exercise1 opt]# mkdir ccc
​    [root@exercise1 opt]# chmod 777 ccc
​    [root@exercise1 opt]# mkdir test
​    [root@exercise1 opt]# chmod 1777 test
​    [root@exercise1 opt]# touch b.sh
​    [root@exercise1 opt]# chmod 4777 b.sh 
​    #查找
​    [root@exercise1 opt]# find /opt/ -perm 777
​    /opt/ccc
​    [root@exercise1 opt]# find /opt/ -perm 1777
​    /opt/test
​    [root@exercise1 opt]# find /opt/ -perm 4777
​    /opt/b.sh
​    [root@exercise1 opt]# 




    例3：按文件类型查找
    把系统中权限不低于 777 的危险目录查找出来
    [root@exercise1 opt]# find / -type d -perm -777
    
    把系统种权限不低于777的危险文件查找出来
    [root@exercise1 opt]# find / -type f -perm -777
    find: ‘/proc/1277/task/1277/fdinfo/6’: 没有那个文件或目录
    find: ‘/proc/1277/fdinfo/6’: 没有那个文件或目录
    /opt/b.sh

​     

```
例4：查找系统中所有者是root的所有文件
[root@exercise1 opt]# find / -user root

例5：查找系统中所有者不是root的所有文件
[root@exercise1 opt]# find / -not -user root
[root@exercise1 opt]# find / ! -user root
```



    例6：按照更改时间或访问时间等查找文件
    如果希望按照更改时间来查找文件，可以使用 mtime,atime 或 ctime 选项
**mtime:   文件最后一次修改的时间**

**atime:   最后一次访问时间**

**ctime:   文件属性的最后一次变化时间**

    希望在 root 目录下查找更改时间在 1 天以内，被黑客修改的文件 
    [root@exercise1 opt]# find /root/ -mtime -1
    /root/
    /root/.bash_history
    /root/.viminfo




    例7：查找的目录深度：                                      
    -maxdepth 1   #只查找目录第一层的文件和目录
    如：查找/bin 目录下 第一层的文件              
    [root@exercise1 opt]# find /bin/ -maxdepth 1   #/bin 后面要有/
    [root@exercise1 opt]# find /bin -maxdepth 1   #这个命令无法满足我们的需求
    /bin
    [root@exercise1 opt]# find /sbin/ -maxdepth 2   #/bin与/sbin 是特别的
    [root@exercise1 opt]# find /opt -maxdepth 1
    /opt
    /opt/a.txt
    /opt/ccc
    /opt/test
    /opt/b.sh
    /opt/bak
    /opt/pkcs11.txt
    [root@exercise1 opt]# 


​       
​    例8：查找多个类型文件 比较符的使用：
​    -a   and   并且
​    -o   or    或者 
​    +          超过
​    -          低于
​    [root@exercise1 opt]# touch a.pdf back.sh
​    [root@exercise1 opt]# find . -name "*.sh" -o -name "*.pdf"
​    ./b.sh
​    ./a.pdf
​    ./back.sh
​    [root@exercise1 opt]# find /etc/ -size +20k -a -size -50k   #找到大于20k小于50k的文件
​    /etc/etc/sysconfig/network-scripts/network-functions-ipv6
​    /etc/etc/selinux/targeted/active/modules/100/apache/hll
​    ……
​    [root@exercise1 opt]# find /etc/ -size +20k



    例9：多条件合并查找，使用(  ) 分组，  \(   前后空格，带转义符号  \) 
    例：找到当前目录下，大于10k 且小于20k，并且文件名为txt结尾或 tar 结尾的文件 
    
    [root@exercise1 opt]# find / -size +10k -a -size -20k -a \( -name "*.txt" -o -name "*.tar" \)



```
例10：过滤用法
[root@exercise1 opt]# cd /opt && touch a{1..10}.txt
[root@exercise1 opt]# find ./ -type -f |xargs grep "123"
```



#### **动作处理**

查找到一个文件后，需要对文件进行如何处理，find的默认动作是-print

  

| 动作    | 含义                                    |
| ------- | --------------------------------------- |
| -print  | 打印查找到的内容（默认）                |
| -ls     | 以长格式显示的方式打印查找到的内容      |
| -delete | 删除查找到的文件与目录                  |
| -ok     | 后面跟自定义shell命令（会提示是否操作） |
| -exec   | 后面跟自定义shell命令                   |

​    

```
例11：使用-print打印查找一的文件
[root@exrcise1 ~]# find /etc -name "ifcfg"
[root@exrcise1 ~]# find /etc -name "ifcfg" -print


例12：使用-ls打印查找到的文件，以长格式显示
[root@exrcise1 ~]# find /etc -name "ifcfg" -ls


例13：使用-delete删除文件与目录
[root@exrcise1 ~]# find ./ -name "a*" -delete

例14：批量删除空目录
[root@exrcise1 ~]# find . -type d -empty -delete
```



    例15：对查找内容执行相应命令
    -exec      这个选项参数后面可以跟自定义的 SHELL 命令，格式如下：

![exec.png](https://s2.loli.net/2022/01/20/vLFPnBg2CpU5O3T.png)

    1）、把查找到的文件列出来
    [root@exercise1 opt]# touch {1..3}.bak
    [root@exercise1 opt]# find . -name "*.bak" -exec ls -l {} \;   #exec参数不能使用别名
    -rw-r--r--. 1 root root 0 1月  20 20:20 ./1.bak
    -rw-r--r--. 1 root root 0 1月  20 20:20 ./2.bak
    -rw-r--r--. 1 root root 0 1月  20 20:20 ./3.bak



​    

    2）、把查找到的文件移动到一个指定的目录
    [root@exercise1 opt]# find . -name "*.bak" -exec mv {} /opt/bak/ \;
    mv: "./bak/1.bak" 与"/opt/bak/1.bak" 为同一文件
    mv: "./bak/2.bak" 与"/opt/bak/2.bak" 为同一文件
    mv: "./bak/3.bak" 与"/opt/bak/3.bak" 为同一文件
    [root@exercise1 opt]# ls /opt/bak/
    1.bak  2.bak  3.bak




​    

    3）、把查找到的文件复制到一个指定的目录
    [root@exercise1 opt]# find /root/ -name "*.txt" -exec cp {} /opt/ \;



```
例16：使用-ok实现文件拷贝，但会提示删除
[root@exrcise1 ~]# find /etc -name "ifcfg" -ok cp  {} /tmp \;
```










​    



​    

















