如何在find中排除目录。命令

时间:2010-11-17 22:57:02

标签: linux shell find

我正在尝试为所有JavaScript文件运行find命令,但如何排除特定目录?

以下是我们正在使用的find代码。

for file in $(find . -name '*.js')
do 
  java -jar config/yuicompressor-2.4.2.jar --type js $file -o $file
done

42 个答案:

答案 0 :(得分:1734)

如果-prune不适合您,则会:

find -name "*.js" -not -path "./directory/*"

警告:需要遍历所有不需要的目录。

答案 1 :(得分:864)

使用剪枝开关,例如,如果要排除misc目录,只需在查找命令中添加-path ./misc -prune -o

find . -path ./misc -prune -o -name '*.txt' -print

以下是多个目录的示例:

find . -type d \( -path dir1 -o -path dir2 -o -path dir3 \) -prune -o -print

这里我们排除dir1,dir2和dir3,因为在find表达式中它是一个动作,它作用于条件-path dir1 -o -path dir2 -o -path dir3(如果dir1或dir2或dir3),与{{1}进行AND运算}。进一步的操作是type -d,只需打印即可。

答案 2 :(得分:411)

我发现以下比其他提出的解决方案更容易推理:

find build -not \( -path build/external -prune \) -name \*.js
# you can also exclude multiple paths
find build -not \( -path build/external -prune \) -not \( -path build/blog -prune \) -name \*.js

重要提示-path之后输入的路径必须与find打印的路径完全匹配而不排除。如果这句话混淆了你,请确保在整个命令中使用完整路径:find / full / path / -not \( -path <强> /全/路径/排除/这 -prune ...。如果您想要更好的理解,请参阅注释[1]。

内部\(\)是一个与完全匹配 build/external的表达式(请参阅上面的重要说明),并且会在成功时避免遍历以下的任何内容。然后将其分组为带有转义括号的单个表达式,并以-not为前缀,这将使find跳过与该表达式匹配的任何内容。

有人可能会问,添加-not是否会使-prune隐藏的所有其他文件重新出现,答案是否定的。 -prune的工作方式是,一旦到达,该目录下的文件将被永久忽略。

这来自一个实际的用例,我需要在wintersmith生成的一些文件上调用yui-compressor,但是遗漏了需要按原样发送的其他文件。


注意[1] :如果您要排除/tmp/foo/bar并运行“find /tmp \(...”之类的查找,则必须指定-path /tmp/foo/bar。另一方面,如果您运行cd /tmp; find . \(...,则必须指定-path ./foo/bar

答案 3 :(得分:184)

这里显然有一些混淆,即跳过目录的首选语法应该是什么。

GNU意见

To ignore a directory and the files under it, use -prune

From the GNU find man page

<强>推理

-prune阻止find降级到目录中。只需指定-not -path仍然会进入跳过的目录,但只要-not -path测试每个文件,find就会为false。

-prune

的问题

-prune按照预期的目的行事,但在使用它时仍然需要注意一些事项。

  1. find打印已修剪的目录。

    • TRUE 这是预期的行为,它不会进入它。要避免完全打印目录,请使用逻辑上省略它的语法。
  2. -prune仅适用于-print,无其他操作。

    • 不正确-prune适用于-delete以外的任何操作。 为什么它不能用于删除?要使-delete工作,找到需要以DFS顺序遍历目录,因为-delete将首先删除叶子,然后是父项叶子等...但是为了指定-prune有意义,find需要命中一个目录并停止下降,这对于-depth或{{1来说显然没有意义}}。
  3. <强>性能

    我针对此问题设置了三个热门投票答案的简单测试(将-delete替换为-print以显示另一个操作示例)。结果低于

    -exec bash -c 'echo $0' {} \;

    <强>结论

    f10bit's syntaxDaniel C. Sobral's syntax平均需要10到25毫秒才能运行。不使用---------------------------------------------- # of files/dirs in level one directories .performance_test/prune_me 702702 .performance_test/other 2 ---------------------------------------------- > find ".performance_test" -path ".performance_test/prune_me" -prune -o -exec bash -c 'echo "$0"' {} \; .performance_test .performance_test/other .performance_test/other/foo [# of files] 3 [Runtime(ns)] 23513814 > find ".performance_test" -not \( -path ".performance_test/prune_me" -prune \) -exec bash -c 'echo "$0"' {} \; .performance_test .performance_test/other .performance_test/other/foo [# of files] 3 [Runtime(ns)] 10670141 > find ".performance_test" -not -path ".performance_test/prune_me*" -exec bash -c 'echo "$0"' {} \; .performance_test .performance_test/other .performance_test/other/foo [# of files] 3 [Runtime(ns)] 864843145 的{​​{3}}耗时865毫秒。所以,是的,这是一个相当极端的例子,但如果你关心运行时间并且正在做任何远程密集的事情,你应该使用-prune

    注意GetFree's syntax执行了两种-prune语法中较好的一种;但是,我强烈怀疑这是一些缓存的结果,因为切换两次运行导致相反结果的顺序,而非修剪版本总是最慢。

    测试脚本

    -prune

答案 4 :(得分:56)

一种选择是使用grep排除包含目录名称的所有结果。例如:

find . -name '*.js' | grep -v excludeddir

答案 5 :(得分:42)

这是唯一对我有用的人。

find / -name NameOfFile ! -path '*/Directory/*'

搜索“NameOfFile”,不包括“目录”。 强调明星*。

答案 6 :(得分:39)

我更喜欢-not符号......它更具可读性:

find . -name '*.js' -and -not -path directory

答案 7 :(得分:18)

使用-prune选项。所以,像:

find . -type d -name proc -prune -o -name '*.js'

'-type d -name proc -prune'仅查找名为proc的目录以进行排除 '-o'是'OR'运算符。

答案 8 :(得分:14)

这是我用来排除某些路径的格式:

$ find ./ -type f -name "pattern" ! -path "excluded path" ! -path "excluded path"

我用它来查找不在“。*”路径中的所有文件:

$ find ./ -type f -name "*" ! -path "./.*" ! -path "./*/.*"

答案 9 :(得分:13)

-prune绝对有效并且是最佳答案,因为它可以防止降级到您要排除的目录。 -not -path仍在搜索已排除的目录,但它不会打印结果,如果排除的目录已装入网络卷或您没有权限,则可能会出现问题。

棘手的部分是find非常特别关注参数的顺序,所以如果你不能正确地使用它们,那么你的命令可能不起作用。参数的顺序通常是这样的:

find {path} {options} {action}

{path}:首先放置所有与路径相关的参数,例如. -path './dir1' -prune -o

{options}:将-name, -iname, etc作为此组中的最后一个选项时,我取得了最大的成功。例如。 -type f -iname '*.js'

{action}:您在使用-print

时想要添加-prune

这是一个有效的例子:

# setup test
mkdir dir1 dir2 dir3
touch dir1/file.txt; touch dir1/file.js
touch dir2/file.txt; touch dir2/file.js
touch dir3/file.txt; touch dir3/file.js

# search for *.js, exclude dir1
find . -path './dir1' -prune -o -type f -iname '*.js' -print

# search for *.js, exclude dir1 and dir2
find . \( -path './dir1' -o -path './dir2' \) -prune -o -type f -iname '*.js' -print

答案 10 :(得分:9)

-path -prune方法也适用于路径中的通配符。这是一个find语句,它将找到服务于多个git存储库的git服务器的目录,而不包括git内部目录:

find . -type d \
   -not \( -path */objects -prune \) \
   -not \( -path */branches -prune \) \
   -not \( -path */refs -prune \) \
   -not \( -path */logs -prune \) \
   -not \( -path */.git -prune \) \
   -not \( -path */info -prune \) \
   -not \( -path */hooks -prune \)  

答案 11 :(得分:8)

要排除多个目录:

find . -name '*.js' -not \( -path "./dir1" -o -path "./dir2/*" \)

要添加目录,请添加-o -path "./dirname/*"

find . -name '*.js' -not \( -path "./dir1" -o -path "./dir2/*" -o -path "./dir3/*"\)

但是如果要排除许多目录,也许你应该使用regular expression

答案 12 :(得分:8)

有很多好的答案,我花了一些时间来理解命令的每个元素是什么以及它背后的逻辑。

find . -path ./misc -prune -o -name '*.txt' -print

find将开始在当前目录中查找文件和目录,因此find .

-o选项代表逻辑OR,并将命令的两个部分分开:

[ -path ./misc -prune ] OR [ -name '*.txt' -print ]

./misc目录的任何目录或文件都不会通过第一个测试-path ./misc。但他们将针对第二个表达进行测试。如果他们的名称与模式*.txt相对应,则会因为-print选项而打印出来。

当find到达./misc目录时,此目录仅满足第一个表达式。因此-prune选项将应用于它。它告诉find命令探索该目录。因此,./misc中的任何文件或目录都不会被find探索,也不会针对表达式的第二部分进行测试,也不会被打印。

答案 13 :(得分:7)

对于工作解决方案(在Ubuntu 12.04(精确穿山甲)上测试)...

find ! -path "dir1" -iname "*.mp3"

将搜索当前文件夹和子文件夹中的MP3文件,但dir1子文件夹除外。

使用:

find ! -path "dir1" ! -path "dir2" -iname "*.mp3"

...排除dir1 AND dir2

答案 14 :(得分:6)

您可以使用剪枝选项来实现此目的。例如:

find ./ -path ./beta/* -prune -o -iname example.com -print

或反grep“grep -v”选项:

find -iname example.com | grep -v beta

您可以在 Linux find command exclude directories from searching 中找到详细的说明和示例。

答案 15 :(得分:5)

您还可以使用正则表达式来包含/排除某些文件/ dir,如下所示:

find . -regextype posix-egrep -regex ".*\.(js|vue|s?css|php|html|json)$" -and -not -regex ".*/(node_modules|vendor)/.*" 

这只会给您所有js,vue,css等文件,但不包括node_modulesvendor文件夹中的所有文件。

答案 16 :(得分:5)

避免打印修剪后的目录的一个好技巧是在 navigator.mediaDevices.getUserMedia({ video: true, audio: false }) .then(localMediaStream => { console.log(localMediaStream); video.src =window.URL.createObjectURL(localMediaStream); }).catch(err =>{ console.error('oh why errors!!', err); }); 之后-print的右边之后使用-exec(同样适用于-or)。例如...

-prune

将打印扩展名为“ .j2”的当前目录下所有文件的路径,并跳过所有隐藏目录。Neat。但如上所述,它还将打印所跳过的每个目录的完整路径。但是,以下不是,...

find . -path "*/.*" -prune -or -iname "*.j2"

因为从逻辑上讲,在find . -path "*/.*" -prune -or -iname "*.j2" -print 运算符之后和-print之前有一个隐藏的-and。由于操作和关联性的布尔顺序,这将其绑定到-iname子句的右侧。但是文档说如果没有指定隐藏的-or(或它的任何堂兄弟... -print等),则会存在一个隐藏的-print0。那么,为什么-or打印的左侧部分没有显示呢?显然(而且,我第一次阅读手册页时并没有理解这一点),如果没有-print-或-exec,那么在没有逻辑的情况下-print就会散布这样就可以打印所有内容。如果在任何子句中甚至表达了一个print风格的操作,所有那些隐藏的逻辑操作都将消失,而您只能得到指定的内容。现在坦率地说,我可能更喜欢这样做,但是只有描述性运算符的find显然什么也没做,所以我认为这是有道理的。如上所述,这同样适用于-exec,因此以下内容为具有所需扩展名的每个文件提供了完整的ls -la列表,但没有列出每个隐藏目录的第一级,...

find . -path "*/.*" -prune -or -iname "*.j2" -exec ls -la -- {} +

对于我(以及该线程中的其他线程)来说,find语法很快就变得很巴洛克式,因此我总是投入括号以确保我知道什么绑定到什么,因此通常为类型创建一个宏-并形成所有这样的陈述,例如...

find . \( \( ... description of stuff to avoid ... \) -prune \) -or \
\( ... description of stuff I want to find ... [ -exec or -print] \)

以这种方式将世界分为两个部分很难出错。我希望这会有所帮助,尽管似乎不太可能有人阅读第30个以上的答案并投票赞成,但有人可以希望。 :-)

答案 17 :(得分:4)

find -name '*.js' -not -path './node_modules/*' -not -path './vendor/*'

似乎和

一样
find -name '*.js' -not \( -path './node_modules/*' -o -path './vendor/*' \)

并且更容易记住IMO。

答案 18 :(得分:4)

find . \( -path '.**/.git' -o -path '.**/.hg' \) -prune -o -name '*.js' -print

上面的示例查找当前目录下的所有*.js文件(文件夹.git.hg除外),与这些.git.hg的深度无关文件夹。

注意:这也可以:

find . \( -path '.*/.git' -o -path '.*/.hg' \) -prune -o -name '*.js' -print

但是我更喜欢使用**表示法来与其他工具保持一致,而这在本文中将不在讨论之列。

答案 19 :(得分:3)

find . -name '*.js' -\! -name 'glob-for-excluded-dir' -prune

答案 20 :(得分:3)

对于那些不能使用 -path -not

的旧版本UNIX用户

在SunOS 5.10 bash 3.2和SunOS 5.11 bash 4.4上进行了测试

find . -type f -name "*" -o -type d -name "*excluded_directory*" -prune -type f

答案 21 :(得分:3)

如果有人正在研究如何一次忽略多个路径。 您可以使用 bash 数组(在 GNU bash 版本 4.4.20(1)-release 上完美运行)

#!/usr/bin/env bash

# This script helps ignore unnecessary dir paths while using the find command

EXCLUDE_DIRS=(
    "! -path /*.git/*"
    "! -path /*go/*"
    "! -path /*.bundle/*"
    "! -path /*.cache/*"
    "! -path /*.local/*"
    "! -path /*.themes/*"
    "! -path /*.config/*"
    "! -path /*.codeintel/*"
    "! -path /*python2.7/*"
    "! -path /*python3.6/*"
    "! -path /*__pycache__/*"
)
find $HOME -type f ${EXCLUDE_DIRS[@]}

# if you like fzf

find $HOME -type f ${EXCLUDE_DIRS[@]} | fzf --height 40% --reverse

同样出于某种原因,您将无法忽略 /bin/ 目录路径。

答案 22 :(得分:3)

我使用find提供xgettext的文件列表,并希望省略特定目录及其内容。我尝试了-path-prune相结合的许多排列,但无法完全排除我想要删除的目录。

虽然我能够忽略我想忽略的目录的内容,但find然后将目录本身作为结果之一返回,这导致xgettext到结果崩溃(不接受目录;只接受文件)。

我的解决方案是简单地使用grep -v跳过结果中我不想要的目录:

find /project/directory -iname '*.php' -or -iname '*.phtml' | grep -iv '/some/directory' | xargs xgettext

find是否存在100%有效的论据,我无法肯定地说。在遇到一些麻烦之后,使用grep是一个快速而简单的解决方案。

答案 23 :(得分:2)

使用多个模式的另一个例子 -o -name

在根目录 / 中搜索所有 *.tpl*.tf 文件,不包括位于 /src/.terraform//code/ 中的文件。

$ find / -type f \( -name '*.tf' -o -name '*.tpl' \) \
  -and \( -not -path '/src/.terraform/*' -and -not -path '/code/*' \)


/src/debug.tf
/src/nodegroup-infra.tpl
/src/variables.tf.tpl

我用 hyperfine 测试了上面的命令;测试是在具有 3k 目录和 12k 文件的系统上进行的。我认为可以说它足够快~70ms

Benchmark #1: ./entrypoint.sh
  Time (mean ± σ):      69.2 ms ±   1.4 ms    [User: 22.6 ms, System: 43.6 ms]
  Range (min … max):    66.4 ms …  72.2 ms    42 runs

示例目录结构

/code/ 目录树

bash-5.0# tree /code
/code
├── debug.tf
├── entrypoint.sh
├── nodegroup-infra.tpl
├── tftemplate.sh
└── variables.tf.tpl

0 directories, 5 files

/src/ 目录树

bash-5.0# tree /src
/src
├── Dockerfile
├── debug.tf
├── entrypoint.sh
├── nodegroup-infra.tpl
├── terraform.tfstate
├── terraform.tfstate.backup
└── variables.tf.tpl

0 directories, 7 files

/root 目录树摘要

$ tree /
...
3382 directories, 12164 files

答案 24 :(得分:2)

以前的答案都不适合Ubuntu。 试试这个:

find . ! -path "*/test/*" -type f -name "*.js" ! -name "*-min-*" ! -name "*console*"

我找到了这个here

答案 25 :(得分:2)

以下命令有效:

find . -path ./.git -prune -o -print

如果您对查找有疑问,请使用-D tree选项查看表达式分析信息。

find -D tree . -path ./.git -prune -o -print

或使用-D all查看所有执行信息。

find -D all . -path ./.git -prune -o -print

答案 26 :(得分:2)

对于我需要的工作,这样工作,从根开始在所有服务器中查找landscape.jpg并排除/var目录中的搜索:

find / -maxdepth 1 -type d | grep -v /var | xargs -I '{}' find '{}' -name landscape.jpg

find / -maxdepth 1 -type d列出了/

中的所有 d 饰品

grep -v /var排除`/ var&#39;从列表中

xargs -I '{}' find '{}' -name landscape.jpg对列表

中的每个目录/结果执行任何命令,例如find

答案 27 :(得分:2)

这适合我在Mac上使用:

find . -name *.php -or -path "./vendor" -prune -or -path "./app/cache" -prune

对于以vendor为后缀的搜索名称,它将排除app/cachephp目录。

答案 28 :(得分:1)

TLDR::使用-path <excluded_path> -prune -o选项了解您的根目录并从那里进行搜索。不要在排除路径的末尾添加结尾/

示例:

find / -path /mnt -prune -o -name "*libname-server-2.a*" -print


要有效地使用find,我相信对文件系统目录结构有很好的了解是必不可少的。在我的家用计算机上,我具有多TB硬盘驱动器,其中大约一半的内容是使用rsnapshot(即rsync)备份的。尽管备份到物理上独立(重复)的驱动器,但它已安装在我的系统根目录(/)下:/mnt/Backups/rsnapshot_backups/

/mnt/Backups/
└── rsnapshot_backups/
    ├── hourly.0/
    ├── hourly.1/
    ├── ...
    ├── daily.0/
    ├── daily.1/
    ├── ...
    ├── weekly.0/
    ├── weekly.1/
    ├── ...
    ├── monthly.0/
    ├── monthly.1/
    └── ...

/mnt/Backups/rsnapshot_backups/目录目前约占2.9 TB,文件和文件夹约为6000万;仅仅遍历这些内容需要花费时间:

## As sudo (#), to avoid numerous "Permission denied" warnings:

# date; echo; \
  time find /mnt/Backups/rsnapshot_backups | wc -l; echo; \
  time du /mnt/Backups/rsnapshot_backups -d 0; echo; \
  time rsnapshot du    ## << more accurate re: rsnapshot footprint

Wed 22 May 2019 10:37:14 AM PDT

34:07.30    ## 34 min
60314138    ## 60.3M files, folders

3112240160  /mnt/Backups/rsnapshot_backups    ## 3.1 TB
33:51.88    ## 34 min

2.9T    /mnt/Backups/rsnapshot_backups/hourly.0/
4.1G    /mnt/Backups/rsnapshot_backups/hourly.1/
...
4.7G    /mnt/Backups/rsnapshot_backups/weekly.3/
2.9T    total    ## 2.9 TB, per sudo rsnapshot du (more accurate)
2:34:54        ## 2 hr 35 min

因此,每当我需要在/(根)分区上搜索文件时,都需要处理(如果可能的话)遍历备份分区。


示例

在该主题(How to exclude a directory in find . command)中提出的各种建议中,我发现使用接受的答案进行搜索的速度快得多,但有警告。

解决方案1 ​​

假设我要查找系统文件libname-server-2.a,但是我不想搜索我的rsnapshot备份。要快速查找系统文件,请使用排除路径/mnt- /mnt//mnt/Backups,...):

## As sudo (#), to avoid numerous "Permission denied" warnings:

# time find / -path /mnt -prune -o -name "*libname-server-2.a*" -print
/usr/lib/libname-server-2.a
real    0m8.644s              ## 8.6 sec  <<< NOTE!
user    0m1.669s
 sys    0m2.466s

## As regular user (victoria), with alternate timing mechanism,
## as using 2?/dev/null to suppress "Permission denied" warnings:

$ START="$(date +"%s")" && find 2>/dev/null / -path /mnt -prune -o \
    -name "*libname-server-2.a*" -print; END="$(date +"%s")"; \
    TIME="$((END - START))"; printf 'find command took %s sec\n' "$TIME"
/usr/lib/libname-server-2.a
find command took 3 sec     ## ~3 sec  <<< NOTE!

...在短短几秒钟内找到了该文件,而这花费了更长的时间[strong> (似乎遍历所有“排除”目录):

## As sudo (#), to avoid numerous "Permission denied" warnings:

# time find / -path /mnt/ -prune -o -name "*libname-server-2.a*" -print
find: warning: -path /mnt/ will not match anything because it ends with /.
/usr/lib/libname-server-2.a
real    33m10.658s            ## 33 min 11 sec (~231-663x slower!)
user    1m43.142s
 sys    2m22.666s

## As regular user (victoria), with alternate timing mechanism,
## as using 2?/dev/null to suppress "Permission denied" warnings:

$ START="$(date +"%s")" && find 2>/dev/null / -path /mnt/ -prune -o \
    -name "*libname-server-2.a*" -print; END="$(date +"%s")"; \
    TIME="$((END - START))"; printf 'find command took %s sec\n' "$TIME"
/usr/lib/libname-server-2.a
find command took 1775 sec    ## 29.6 min

解决方案2

此线程(SO#4210042)中提供的另一种解决方案也表现不佳:

## As sudo (#), to avoid numerous "Permission denied" warnings:

# time find / -name "*libname-server-2.a*" -not -path "/mnt"
/usr/lib/libname-server-2.a
real    33m37.911s            ## 33 min 38 sec (~235x slower)
user    1m45.134s
 sys    2m31.846s

# time find / -name "*libname-server-2.a*" -not -path "/mnt/*"
/usr/lib/libname-server-2.a
real    33m11.208s            ## 33 min 11 sec
user    1m22.185s
 sys    2m29.962s

摘要

在“解决方案1”(... -path <excluded_path> -prune -o ...)中,似乎每当添加尾随/时,该命令就会递归地输入(所有)/mnt/*目录-在我的情况下,因为有/mnt/Backups/rsnapshot_backups/*子目录,还包括约2.9 TB的文件要搜索!通过不添加结尾的/,搜索应该几乎立即完成(几秒钟内)。

“解决方案2”(... -not -path <exclude path> ...)同样似乎在递归搜索排除目录,而不返回那些匹配,但不必要地浪费了搜索时间。


在这些rsnapshot备份中进行搜索:

要在我的每小时/每天/每周/每月rsnapshot备份之一中查找文件):

$ START="$(date +"%s")" && find 2>/dev/null /mnt/Backups/rsnapshot_backups/daily.0 -name '*04t8ugijrlkj.jpg'; END="$(date +"%s")"; TIME="$((END - START))"; printf 'find command took %s sec\n' "$TIME"
/mnt/Backups/rsnapshot_backups/daily.0/snapshot_root/mnt/Vancouver/temp/04t8ugijrlkj.jpg
find command took 312 sec   ## 5.2 minutes: despite apparent rsnapshot size
                            ## (~4 GB), it is in fact searching through ~2.9 TB)

不包括嵌套目录:

在这里,我想排除一个嵌套目录,例如从/mnt/Vancouver/projects/ie/claws/data/*搜索时,/mnt/Vancouver/projects/

$ time find . -iname '*test_file*'
./ie/claws/data/test_file
./ie/claws/test_file
0:01.97

$ time find . -path '*/data' -prune -o -iname '*test_file*' -print
./ie/claws/test_file
0:00.07

旁边::在命令末尾添加-print将禁止打印排除目录:

$ find / -path /mnt -prune -o -name "*libname-server-2.a*"
/mnt
/usr/lib/libname-server-2.a

$ find / -path /mnt -prune -o -name "*libname-server-2.a*" -print
/usr/lib/libname-server-2.a

答案 29 :(得分:1)

<how-to-use-prune-option-of-find-in-shLaurence Gonsalves关于-prune如何运作的绝佳答案。

以下是通用解决方案:

find /path/to/search                    \
  -type d                               \
    \( -path /path/to/search/exclude_me \
       -o                               \
       -name exclude_me_too_anywhere    \
     \)                                 \
    -prune                              \
  -o                                    \
  -type f -name '*\.js' -print

为避免多次输入/path/to/seach/,请将find包裹在pushd .. popd对中。

pushd /path/to/search;                  \
find .                                  \
  -type d                               \
    \( -path ./exclude_me               \
       -o                               \
       -name exclude_me_too_anywhere    \
     \)                                 \
    -prune                              \
  -o                                    \
  -type f -name '*\.js' -print;         \
 popd

答案 30 :(得分:1)

我发现C源文件中的函数名称不包括* .o并排除* .swp和exclude(不是常规文件),并使用此命令排除dir输出:

find .  \( ! -path "./output/*" \) -a \( -type f \) -a \( ! -name '*.o' \) -a \( ! -name '*.swp' \) | xargs grep -n soc_attach

答案 31 :(得分:1)

最好使用exec操作而不是for循环:

find . -path "./dirtoexclude" -prune \
    -o -exec java -jar config/yuicompressor-2.4.2.jar --type js '{}' -o '{}' \;

exec ... '{}' ... '{}' \;将针对每个匹配文件执行一次,将大括号'{}'替换为当前文件名。

请注意,大括号用单引号括起来,以保护它们不被解释为shell脚本标点 *

注释

* 来自find (GNU findutils) 4.4.2手册页的示例部分

答案 32 :(得分:1)

我尝试过上面的命令,但使用“-prune”的人都不适合我。 最后我用以下命令尝试了这个:

Thread getHotels=new Thread(new Runnable() {
        @Override
        public void run() {
            ServiceManager service=new ServiceManager(getApplicationContext());
            hotels=service.GetHotels(1);
            runOnUiThread(new Runnable() {
             @Override
             public void run() {
              for (int i=0; i<hotels.length; i++) {
               glHotels.addView(hotels[i]);
             }
            }
           });
        }
    });

答案 33 :(得分:0)

我在此页面上找到了建议,许多其他页面在我的Mac OS X系统上无效。但是,我找到了一个对我有用的变体。

最大的想法是搜索Macintosh HD,但避免遍历所有外部卷,主要是Time Machine备份,映像备份,挂载共享和存档,但不必全部卸载它们,这通常是不切实际的。 / p>

这是我的工作脚本,我已将其命名为&#34; findit&#34;。

#!/usr/bin/env bash
# inspired by http://stackoverflow.com/questions/4210042/exclude-directory-from-find-command Danile C. Sobral
# using special syntax to avoid traversing. 
# However, logic is refactored because the Sobral version still traverses 
# everything on my system

echo ============================
echo find - from cwd, omitting external volumes
date
echo Enter sudo password if requested
sudo find . -not \( \
-path ./Volumes/Archive -prune -o \
-path ./Volumes/Boot\ OS\ X -prune -o \
-path ./Volumes/C \
-path ./Volumes/Data -prune -o \
-path ./Volumes/jas -prune -o \
-path ./Volumes/Recovery\ HD -prune -o \
-path ./Volumes/Time\ Machine\ Backups -prune -o \
-path ./Volumes/SuperDuper\ Image -prune -o \
-path ./Volumes/userland -prune \
\) -name "$1" -print
date
echo ============================
iMac2:~ jas$

各种路径与外部存档卷,Time Machine,虚拟机,其他已安装的服务器等有关。某些卷名称中包含空格。

良好的测试运行是&#34; findit index.php&#34;,因为该文件出现在我系统的许多地方。使用此脚本,搜索主硬盘大约需要10分钟。如果没有这些排除,则需要数小时。

答案 34 :(得分:0)

代替:

for file in $(find . -name '*.js')
do 
  java -jar config/yuicompressor-2.4.2.jar --type js $file -o $file
done

...并且由于您没有定义要排除的子目录,因此可以使用:

for file in $(find *.js -maxdepth 0 -name '*.js')
do 
  java -jar config/yuicompressor-2.4.2.jar --type js $file -o $file
done

此语法将排除所有子目录。

看看下面的例子:在我的tmp目录下,我有一个巨大的“ archive”子目录,其中包含17000-4640 = 12360文件。并且此目录位于慢速NFS上。第一种语法扫描“存档”子目录并执行不佳,而第二种语法仅扫描我当前目录中包含的“ * pdf”文件,并执行...还不错。

[tmp]$ time (find . -name "*pdf" | wc -l)
17000

real    0m40.479s
user    0m0.423s
sys     0m5.606s

[tmp]$ time (find *pdf -maxdepth 0 -name "*pdf" | wc -l)
4640

real    0m7.778s
user    0m0.113s
sys     0m1.136s

第二种语法非常有趣:在下面的示例中,我想检查文件or60runm50958.pdf是否存在并且是否存在20分钟以上。亲自了解第二种语法如何更有效。这是因为它避免了扫描存档子目录。

[tmp]$ time find . -name or60runm50958.pdf -mmin +20
./or60runm50958.pdf

real    0m51.145s
user    0m0.529s
sys     0m6.243s

[tmp]$ time find or60runm50958.pdf -maxdepth 0 -name or60runm50958.pdf -mmin +20
or60runm50958.pdf

real    0m0.004s
user    0m0.000s
sys     0m0.002s

答案 35 :(得分:0)

对于FreeBSD用户:

 find . -name '*.js' -not -path '*exclude/this/dir*'

答案 36 :(得分:0)

如果搜索目录有模式(在我的情况下大多数情况下);你可以像下面这样做:

find ./n* -name "*.tcl" 

在上面的例子中;它搜索以“n”开头的所有子目录。

答案 37 :(得分:0)

这是有效的,因为find TESTS 模式&#34; * foo * &#34;的文件:

find ! -path "dir1" ! -path "dir2" -name "*foo*"

但如果您不使用模式,则工作<find TEST )。因此,find不会使用之前评估的&#34; true &#34; &安培; &#34; &#34;布尔变量。上述表示法不工作用例的示例:

find ! -path "dir1" ! -path "dir2" -type f

没有find测试!因此,如果您需要查找没有任何模式匹配的文件,请使用-prune。此外,通过使用修剪find总是更快,而它真的跳过该目录而不是匹配它或更好地不匹配它。所以在这种情况下使用类似的东西:

find dir -not \( -path "dir1" -prune \) -not \( -path "dir2" -prune \) -type f

或:

find dir -not \( -path "dir1" -o -path "dir2" -prune \) -type f

此致

答案 38 :(得分:0)

我认为自己是bash迷,但是……在过去的两年中,还没有找到一个针对bash的用户友好解决方案。 “用户友好”是指仅需一次调用,这不需要我记住复杂的语法+我可以使用与以前相同的find语法,因此以下解决方案最适合那些^^^

复制此代码粘贴到您的shell中并获取〜/ .bash_aliases的源代码cat << "EOF" >> ~/.bash_aliases # usage: source ~/.bash_aliases , instead of find type findd + rest of syntax findd(){ dir=$1; shift ; find $dir -not -path "*/node_modules/*" -not -path "*/build/*" \ -not -path "*/.cache/*" -not -path "*/.git/*" -not -path "*/venv/*" $@ } EOF

当然,要添加或删除要排除的目录,您必须使用所选目录来编辑此别名函数...

答案 39 :(得分:0)

不确定这是否会涵盖所有边缘情况,但以下内容非常简单且易于尝试:

ls -1|grep -v -e ddl -e docs| xargs rm -rf

这应该删除当前目录中的所有文件/目录。\ n \ n \“ddls&#39;和&#39; docs&#39;。

答案 40 :(得分:-1)

#find command in linux
def : find command used to locate /search files in unix /linux system ,
      find  search for files in a directory hierarchy
1)exec   Show diagnostic information relating to -exec, -execdir, -ok and -okdir
2)-options
  -H =do not follow symoblic links while except while procesing .
  -L = follow symbolic links
  -P =never follow symbolic links

  -type c
             File is of type c:

             b      block (buffered) special

             c      character (unbuffered) special

             d      directory

             p      named pipe (FIFO)

             f      regular file

             l      symbolic  link;  this  is  never true if the -L option or the -follow option is in effect, unless the
                    symbolic link is broken.  If you want to search for symbolic links when -L is in effect, use -xtype.

             s      socket

             D      door (Solaris)

    -Delete
    Delete files; true if removal succeeded.  If the removal failed, an error message  is  issued.
    If  -delete
    #fails, find's exit status will be nonzero (when it eventually exits).


find /home/mohan/a -mindepth 3 -maxdepth 3 -type f -name "*.txt" |xargs rm -rf
find -type d -name
find -type f -Name
find /path/ -type f -iname (i is case insenstive)

#find directores a/b/c and only delete c directory inside have "*.txt "
find /home/mohan/a -mindepth 3 -maxdepth 3 -type f -name "*.txt" |xargs rm -rf
find /home/mohan/a -mindepth 3 -maxdepath 3 -type f -name "*.txt" -delete


#delete particular directory have empty file and only  we can delete empty files
find /home/mohan -type f -name "*.txt" -empty -DELETE


#find multiple files and also find empty files
find /home/mohan -type f \( -name "*.sh" -o  -name "*.txt" \) -empty

#delete empty files two or more Files
find /home/mohan -type f \( -nmae "*.sh" -o -name "*.txt" \) -empty -delete


#How to append contents of multiple files into one file
find . -type f -name '*.txt' -exec cat {} + >> output.file

#last modified files finding using less than 1 min (-n)
ls -lrth|find . -type f -mmin -1

#last modified files more than 1 min (+n)
ls -lrth|find . -type f -mmin +1


#last modified files exactly one mins
find . -type f -mmin 1

last modifiedfiles exactly in one day by using command (-mtime)
find . -type f -mtime 10

#last modified more than 10 days
find . -type  f -mtime +10

#last modified less than 10 days
find . -type f -mtime -10

#How to Find Modified Files and Folders Starting from a Given Date to the Latest Date
find . -type f  -newermt "17-11-2020"

#How to Find a List of “sh” Extension Files Accessed in the Last 30 Days--- -matdimtype
ls -lrt|find . -type f -iname ".sh" -atime -30

#How to Find a List of Files Created Today, -1 means less than min,
ls -lrt | find . -type f -ctime -1 -ls

答案 41 :(得分:-1)

我想知道目录的数量,文件是只是当前目录的文件 - 并且该代码完全符合我的要求: - )

来源

- ...    2791037 Jun  2  2011 foo.jpg
- ... 1284734651 Mär 10 16:16 foo.tar.gz
- ...          0 Mär 10 15:28 foo.txt
d ...       4096 Mär  3 17:12 HE
d ...       4096 Mär  3 17:21 KU
d ...       4096 Mär  3 17:17 LE
d ...          0 Mär  3 17:14 NO
d ...          0 Mär  3 17:15 SE
d ...          0 Mär  3 17:13 SP
d ...          0 Mär  3 17:14 TE
d ...          0 Mär  3 19:20 UN

代码

format="%s%'12d\n"

find . -type d -not -path "./*/*" | wc -l | awk -v fmt=$format '{printf fmt, " Anzahl Ordner  = ", $1-1}'
find . -type f -not -path "./*/*" | wc -l | awk -v fmt=$format '{printf fmt, " Anzahl Dateien = ", $1}'
  du . -hmS --max-depth=0 | awk -v fmt=$format '{printf fmt, " Groesse (MB)   = ", $1}'

注意:format="%s%'12d\n"格式化数字需要额外的awk

结果

Anzahl Ordner  =            8
Anzahl Dateien =            3
Groesse (MB)   =        1.228