【问题标题】:Linux commands to copy one file to many filesLinux命令将一个文件复制到多个文件
【发布时间】:2012-03-03 22:47:49
【问题描述】:

在 Linux 上是否有单行命令/脚本可以将一个文件复制到多个文件?

cp file1 file2 file3

将前两个文件复制到第三个文件中。有没有办法将第一个文件复制到其余文件中?

【问题讨论】:

  • 一个问题是你想让file2和file3占据独立的块吗?

标签: linux cp


【解决方案1】:

cp file1 file2 ; cp file1 file3

算作“单行命令/脚本”?怎么样

for file in file2 file3 ; do cp file1 "$file" ; done

?

或者,对于“复制”的稍微宽松的感觉:

tee <file1 file2 file3 >/dev/null

【讨论】:

  • @J.F.Sebastian:是的,但是由于 OP 显然希望它不仅仅适用于两个目标文件,所以我选择了强调支持的表单。也许我应该写tee &lt;file1 &gt;file2 file3 file4 并省去两个文件的并行性?
  • 不确定这是否仍然相关,但我只想指出,使用 tee 解决方案不会保留初始文件权限。
  • @bioShark:是的——它只复制文件的内容。这就是为什么我将其描述为“稍微宽松的‘复制’”。
  • 只是为了好玩,如果您需要大量文件tee &lt;sourcefile.jpg targetfiles{01-50}.jpg &gt;/dev/null
【解决方案2】:

只是为了好玩,如果您需要大量文件:

tee &lt;sourcefile.jpg targetfiles{01-50}.jpg &gt;/dev/null-Kelvin Feb 12 at 19:52

但是有一点错别字。应该是:

tee &lt;sourcefile.jpg targetfiles{01..50}.jpg &gt;/dev/null

如上所述,这不会复制权限。

【讨论】:

    【解决方案3】:

    您可以使用 bash 大括号扩展中的 ranges 来改进/简化 for 复制方法(由 @ruakh 回答):

    for f in file{1..10}; do cp file $f; done
    

    这会将file 复制到file1, file2, ..., file10

    要检查的资源:

    【讨论】:

      【解决方案4】:
      for FILE in "file2" "file3"; do cp file1 $FILE; done
      

      【讨论】:

        【解决方案5】:

        你可以使用shift:

        file=$1
        shift
        for dest in "$@" ; do
            cp -r $file $dest
        done
        

        【讨论】:

        • shift的作用是什么?
        【解决方案6】:

        cat file1 | tee file2 | tee file3 | tee file4 | tee file5 &gt;/dev/null

        【讨论】:

        • 它可能有效,但它非常不灵活。如果您要复制大文件,它可能会效率低下。
        • @StephenC 虽然它更接近原始查询
        • 如果你使用 cat 和 tee,还不如:cat file1 | tee file2 file3 file4 >/dev/null
        【解决方案7】:

        使用类似以下的内容。它适用于 zsh。

        cat 文件 > firstCopy > secondCopy >thirdCopy

        cat 文件 > {1..100} - 用于带有数字的文件名。

        这对小文件很有用。

        对于较大的文件,您应该使用前面提到的 cp 脚本。

        【讨论】:

        • 假设shell是zsh
        • 为什么文件的大小很重要?受 RAM 大小限制?
        • 因为猫处理
        【解决方案8】:

        我建议基于该脚本创建一个通用脚本和一个函数(empty-files),以清空任意数量的目标文件。

        将脚本命名为 copy-from-one-to-many 并将其放入您的 PATH。

        #!/bin/bash -e
        #  _ _____     
        # | |___ /_  __  
        # | | |_ \ \/ /  Lex Sheehan (l3x)
        # | |___) >  <   https://github.com/l3x
        # |_|____/_/\_\  
        #
        # Copy the contents of one file to many other files.
        
        source=$1
        shift
        for dest in "$@"; do
            cp $source $dest
        done
        
        exit
        

        注意事项

        上面的 shift 会从参数列表 ("$@") 中删除第一个元素(源文件路径)。

        如何清空多个文件的示例:

        用内容创建file1、file2、file3、file4和file5:

        for f in file{1..5}; do echo $f > "$f"; done
        

        清空许多文件:

        copy-from-one-to-many /dev/null file1 file2 file3 file4 file5
        

        清空许多文件更容易:

        # Create files with content again
        for f in file{1..5}; do echo $f > "$f"; done 
        
        copy-from-one-to-many /dev/null file{1..5}
        

        基于copy-from-one-to-many创建empty_files函数

        function empty-files()
        {
            copy-from-one-to-many /dev/null "$@"
        }
        

        示例用法

        # Create files with content again
        for f in file{1..5}; do echo $f > "$f"; done 
        # Show contents of one of the files
        echo -e "file3:\n $(cat file3)"
        
        empty_files file{1..5}
        # Show that the selected file no longer has contents
        echo -e "file3:\n $(cat file3)"
        

        不要只是窃取代码。改进它;用例子记录它并分享它。 - l3x


        这是一个在每个 cp 命令前加上 sudo 的版本:

        #!/bin/bash -e
        # Filename: copy-from-one-to-may
        #  _ _____     
        # | |___ /_  __  
        # | | |_ \ \/ /  Lex Sheehan (l3x)
        # | |___) >  <   https://github.com/l3x
        # |_|____/_/\_\  
        #
        # Copy the contents of one file to many other files.
        # Pass --sudo if you want each cp to be perfomed with sudo
        # Ex: copy-from-one-to-many $(mktemp) /tmp/a /tmp/b /tmp/c --sudo
        
        if [[ "$*" == *--sudo* ]]; then
            maybe_use_sudo=sudo
        fi
        
        source=$1
        shift
        for dest in "$@"; do
            if [ $dest != '--sudo' ]; then
              $maybe_use_sudo cp $source $dest
            fi
        done
        
        exit
        

        【讨论】:

          【解决方案9】:

          您可以为此使用标准脚本命令:

          重击:

           for i in file2 file3 ; do cp file1 $i ; done
          

          【讨论】:

            【解决方案10】:

            我能想到的最简单/最快的解决方案是 for 循环:

            for target in file2 file3 do; cp file1 "$target"; done
            

            以下是肮脏的 hack(我强烈建议不要这样做,并且无论如何只能在 bash 中使用):

            eval 'cp file1 '{file2,file3}';'
            

            【讨论】:

              【解决方案11】:

              使用最快 cp 操作

              seq 1 10 | xargs -P 0 -I xxx cp file file-xxx
              

              意思是

              • seq 1 10 从 1 数到 10
              • | 管它xargs
              • -P 0 并行执行 - 按需执行
              • -I xxx 每个输入的名称 xargs 接收
              • cp file file-xxx 表示将文件复制到 file-1、file-2 等

              如果文件名不同,这里是其他解决方案。
              首先有要创建的文件列表。例如

              one
              two
              three
              four
              five
              

              第二将此列表保存在磁盘上,并像以前一样使用xargs 读取列表,但不使用seq

              xargs -P 0 -I xxx cp file xxx  < list
              

              这意味着 5 个并行复制操作:

              cp file one  
              cp file two  
              cp file three  
              cp file four  
              cp file five  
              

              对于xargs,这里是幕后花絮(5 个分叉

               3833 pts/0    Ss     0:00 bash
              15954 pts/0           0:00  \_ xargs -P 0 -I xxx cp file xxx < list
              15955 pts/0           0:00      \_ cp file one
              15956 pts/0           0:00      \_ cp file two
              15957 pts/0           0:00      \_ cp file three
              15958 pts/0           0:00      \_ cp file four
              15959 pts/0           0:00      \_ cp file five
              

              【讨论】:

                【解决方案12】:

                (不使用循环)

                在Linux中将一个文件(fileA.txt)的内容复制到多个文件(fileB.txt, fileC.txt, fileD.txt), p>

                使用以下组合 cattee 命令:

                cat fileA.txt | tee fileB.txt fileC.txt fileD.txt >/dev/null
                
                • 适用于任何文件扩展名
                • 只有文件名和扩展名发生变化,其他一切都保持不变。

                【讨论】:

                  猜你喜欢
                  • 1970-01-01
                  • 1970-01-01
                  • 1970-01-01
                  • 1970-01-01
                  • 2013-10-24
                  • 2011-05-19
                  • 1970-01-01
                  • 2013-03-09
                  • 1970-01-01
                  相关资源
                  最近更新 更多