如何区分和合并两个目录?


38

我知道Vim的diff模式vimdiff)使我们能够比较两个(或更多)文件的内容。

但是可以跨目录比较多个文件的内容,以便递归合并两个目录(例如DiffMerge和类似工具)吗?


您的相应文件夹是否正在使用任何类型的VCS?这将打开一系列可能无法用于平面文件夹的答案和插件。
卡莱布

Answers:


30

DirDiff.vim插件(GitHub)来递归地比较和合并两个目录。

它在两个目录上执行递归差异,并生成差异“窗口”。根据该窗口,您可以执行各种差异操作,例如以Vim的差异模式打开两个文件,将文件或目录递归复制到另一个文件或从源目录中删除目录树。

用法:

:DirDiff <dir1> <dir2>

有关更多信息/帮助: :help dirdiff

看截图:

wlee屏幕截图

也可以看看:


dedm博客的链接已断开-博客已被删除。
drevicko

1
@drevicko谢谢,我已将链接替换为已归档的链接
kenorb,

4

我使用包装脚本python来合并文件(请参见下文)。这是我用来合并~/.vim目录等的简化版本。

它应该在Python 2和3中工作;但可能不是CentOS和其他发行版附带的非常老版本的Python。

请注意,某些检查(例如检查二进制文件,或者文件是否相同)不是很快(它将读取整个文件)。您可以根据需要删除它们。

它也不会报告a是否仅出现在目录之一中...

#!/usr/bin/env python
from __future__ import print_function
import hashlib, os, subprocess, sys

if len(sys.argv) < 3:
    print('Usage: {} dir1 dir2'.format(sys.argv[0]))
    sys.exit(1)

dir1 = os.path.realpath(sys.argv[1])
dir2 = os.path.realpath(sys.argv[2])

for root, dirs, files in os.walk(dir1):
    for f in files:
        f1 = '{}/{}'.format(root, f)
        f2 = f1.replace(dir1, dir2, 1)

        # Don't diff files over 1MiB
        if os.stat(f1).st_size > 1048576 or os.stat(f2).st_size > 1048576: continue

        # Check if files are the same; in which case a diff is useless
        h1 = hashlib.sha256(open(f1, 'rb').read()).hexdigest()
        h2 = hashlib.sha256(open(f2, 'rb').read()).hexdigest()
        if h1 == h2: continue

        # Don't diff binary files
        if open(f1, 'rb').read().find(b'\000') >= 0: continue

        subprocess.call(['vimdiff', f1, f2])

3

我已经想要了一段时间。我发现最好的解决方案是使用vdwrap,效果很好。它所做的就是包装git difftool --dir-diffvimdiff。它不需要任何vim插件。

您需要做的就是告诉git difftool您使用vdwrap

git config --global difftool.vdwrap.cmd '/full/path/vdwrap $LOCAL $REMOTE'
git config --global diff.tool vdwrap

下次使用git difftool时,它将为每对文件使用单独的Vim选项卡打开Vim。

一个警告是它是Zsh脚本。将其转换为bash脚本应该非常简单,但是我还没有去做。



2

如果您只想使用vimdiff而不安装任何额外的东西,则以下命令将依次打开所有不同的文件,让您查看vimdiff的更改:

    for files in $(diff -rq dir1 dir2|grep 'differ$'|sed "s/^Files //g;s/ differ$//g;s/ and /:/g"); do 
        vimdiff ${files%:*} ${files#*:}; 
    done

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.