关于bash:在嵌套文件结构中查找缺少的文件名

Find missing filenames in nested filestructure

本问题已经有最佳答案,请猛点这里访问。

我有一个源目录,其子目录包含文件。 我还有一个目标目录,其中包含具有其他结构的子目录。

1
2
3
4
5
6
fileNames = <get all file names from source directory>
for fileName in fileNames {
    if <not found in destination directory> {
         print fileName
    }
}

我怎么能在上面做伪代码?

编辑:

1
2
3
4
5
6
7
Example file structure:
./sourcedir/file1.txt
./sourcedir/foldera/file2.txt
./sourcedir/foldera/missingfile.txt

./destdir/file2.txt
./destdir/folderb/file1.txt

所以应该打印missingfile.txt。 但不是file1.txt或file2.txt,因为它们可以在destdir的某个地方找到。

EDIT2:
我设法做了一个Python实现,这是我的目标。 尝试时我遇到了bash答案的麻烦。 在bash中可以做得更简单吗?

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
import os
import fnmatch

sourceDir ="./sourcedir"
destinationDir ="./destdir"

def find_files(directory, pattern):
    for root, dirs, files in os.walk(directory):
        for basename in files:
            if fnmatch.fnmatch(basename, pattern):
                filename = os.path.join(root, basename)
                yield filename

print sourceDir
for sourcefilename in find_files(sourceDir, '*'):
     #if not sourcefilename.lower().endswith(('.jpg', '.jpeg', '.gif', '.png','.txt','.mov','3gp','mp4','bmp')):
     #  continue
     shouldPrint = True
     for destfilename in find_files(destinationDir, '*'):
         sourceBaseName = os.path.basename(sourcefilename)
         destBaseName = os.path.basename(destfilename)
         if sourceBaseName == destBaseName:
             shouldPrint = False
             break
     if shouldPrint:
         print 'Missing file:', sourcefilename


使用bash可以通过运行diff -r source_dir target_dir | grep Only.*source_dir | awk '{print $4}'轻松完成。

  • diff -r source_dir target_dir显示source_dir和target_dir之间的差异
  • grep Only.*source_dir将过滤掉源目录中但不在目标目录中的所有文件
  • awk '{print $4}'将过滤掉文件名

有点破解,但你可以用finddiff做一些事情,不需要Python:

1
2
diff -u <(cd sourcedir && find . -type f) <(cd destdir && find . -type f) |\
grep"^\-\./" | sed 's/^-//'

这会将sourcedir中的文件列表与destdir中的文件列表进行比较,然后仅打印出sourcedir中但不包含在destdir中的文件。