2つ以上のファイルの行をインターリーブする方法は?


10

2つのファイルを1つのファイルに出力しようとしました。私は以下のコマンドを試しました:

cat file1 file2

しかし、ここではfile2データがに追加されていfile1ます。

私が必要なのは、file11行目file2と1行file1目、2行目と2行file2目などです。

簡単な方法でこれを行う方法を誰かに教えてもらえますか?

回答:


17

そのためのアプリがあります!

$ cat file1
file1 line1
file1 line2

$ cat file2
file2 line1
file2 line2

これらのファイルを引数として渡すとpaste

$ paste -d' ' file1 file2
file1 line1 file2 line1
file1 line2 file2 line2

「file1の最初の行の後にfile2の最初の行が続き、file1の2番目の行の後にfile2の2番目の行が続く」などの場合、貼り付けられた各行の間に新しい行が必要なことを意味し、-d(区切り文字)オプションを調整します。

$ paste -d'\n' file1 file2
file1 line1
file2 line1
file1 line2
file2 line2

2

POSIX Awk; これは任意の量のファイルで機能し、ファイルは同じ量の行である必要はありません。スクリプトは、すべてのファイルが行からなくなるまで続行します。

BEGIN {
  do {
    br = ch = 0
    while (++ch < ARGC)
      if (getline < ARGV[ch]) {
        printf ch < ARGC - 1 ? $0 FS : $0 RS
        br = 1
      }
  } while (br)
}

入力に ​​'%'文字が含まれていると、printf内でそれらを評価しようとしましたが、1つの問題があります。私のアップデートは次のようになります(これが完全に正しいかどうかはわかりません):printf "%s", ((ch < ARGC - 1) ? $0 FS : $0 RS)
Scala William

0

クイックバッシュソリューション

# Takes as many file arguments as needed
function InterleaveFiles {

    local counter=0
    local hasLine=true

    while [ $hasLine == true ]; do
            hasLine=false
            for i in "$@"; do
                    line=$(awk 'NR == num_line {print; exit}' num_line=$((counter+1)) "$i")
                    if [ -n "$line" ]; then
                            echo "$line"
                    hasLine=true
                    fi
            done
            counter=$((counter+1))
    done
}

InterleaveFiles file1 file2 file3 file4


-2
paste -d '\n' file1 file2 > file3

どこfile1file2入力ファイルで、file3作成された出力となります。


1
U&Lスタック交換へようこそ!この答えは、terdonの答えとほとんど同じです。回答を改善できると思われるが、実質的に新しい情報を提供しない場合は、既存の回答の編集を提案することを検討してください。回答も投票に基づいて並べ替えられるため、各回答は独自に立つか、他の回答を参照する必要があります。そのため、シェルワンライナーには、その動作を説明する説明が必要です。
トーマス・ナイマン2014
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.