質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

88.80%

ばらばらな名前が付いたファイルのデータにファイルの通しIDを付与してまとめたい。

解決済

回答 3

投稿 編集

  • 評価
  • クリップ 0
  • VIEW 953

一部修正しました。行と列の記載の誤記を修正し、データの追加をしました。

前提・実現したいこと

100個のばらばらな名前(A)が付いたファイル(file1)があります。
これらのファイルには10,000行位のデータ(B)があります。
これと別にこの100個のファイル名(A)が3列目に、ID番号(C)が1列目に書かれたファイル(file2)があります。

この100個のファイル(A001~100)の1行づつ(B)にID番号(C001~100)を付与して、一つのファイルにまとめたいのですが、
やり方に困っています。
file2の3列目を読んで、そのファイル名を元にファイルAを1行目から読み込み、
file2の1列目に書かれているIDをくっつけていくという作業です。
目的ファイルのイメージとしては下記の様な感じです。

C001 B001
C001 B002
C001 B003
...
C002 B001
C002 B002
C002 B003
C002 B004
C002 B005
...
C100 B001
C100 B002
C100 B003
といった感じです。

for loopを使うことでどうにか出来そうな気がするのですが、
上手く処理出来ません。
下記を試しましたが、正直後半は自分でも何をやっているのか分かっていない状態です。アドバイス頂ければ幸いです。

他の方法として、上記のfile2(1oo個のファイル名(A)が3列目に、ID番号(C)が1列目に書かれたファイル)をもとに、ファイル名を先に換えてしまう方が簡単かも知れませんので、そのやり方でも結構です。
宜しくお願いします。

試したソースコード

for f in `awk '{print $3}' file2` ; do
 while read line; do
  for i in `awk '{print $1}' file2`; do
    echo "$i $line";
     done <"$f";
      done > file3;
       done

ファイルの中身

ご指摘頂いたので、ファイルの実際の中身を一部載せます。
file2はこんなファイルです。3列目がファイル名です。

ID_001 6d822383-e59b-41a6-8680-6bc3f4d1e862    480de2f2-6f01-43e9-bc1b-77b8ec8451f5.txt    4804a20f7c4979dfbc4a25039163b7d6    538584    submitted
ID_002 bff3f31e-ee05-448d-af36-1ab183ba2ff4    fcd43085-7338-43fe-bc25-9d87b04e227f.txt    29096eca2f55808fa19cf849107e8f8e    541634    submitted
ID_003 c640cec0-1656-4ca2-92a0-afca1cf3f86c    e38e0ced-093c-44e9-9f3b-7cdd0e6b912e.txt    75a590b047e61327b56b32d88175cdce    549556    submitted
ID_004 8577ad66-1a2d-41df-99c8-ba6b4a5399ac    2e33a2c5-2196-49c4-866a-34b12d984c15.txt    8235f4a52239fe40439028f713e515c0    508395    submitted
ID_005 b826b9fc-3287-41cc-8e29-72666d2fa4f8    939eeb3c-9c0b-431f-8020-7165ee19f068.txt    35001fba081a7a8b9bba35f7a92be9b9    506780    submitted
ID_006 d1b58025-d1cc-46ef-b9cb-6f0315a5620d    e5214aa1-432a-4a47-886c-3ded1616255b.txt    905ca9f1688037beb3b77fce133a009c    524393    submitted
ID_007 6543a250-d902-4612-b64e-18404944ca3d    3828d55b-81ae-42b2-8f5e-d1dcd87e576a.txt    b0ea16a0c6cf2628f77acfd182e71195    534881    submitted
ID_008 f68912b3-1117-4793-a492-2804c7c903de    8a799dfa-c1b5-4b13-9c91-6cbfe2abbc9f.txt    3221205f01a00db20d713d3c16cc8d47    543383    submitted
ID_009 ef3a8b0a-0ce7-4d26-98cc-7e78c21db36b    09a677f2-d81d-4c3f-adf9-f8594e064e44.txt    dac19654887b2cfb081f3c5f82c8f3fa    483745    submitted
ID_010 6a8e84dc-306b-4752-95d7-d653fe91f3a3    f748bf78-4dc1-47ad-8611-8186479d3e4b.txt    b3d8f563268ed14daf59d9598b169d69    525039    submitted
ID_011 4403f1cf-51f6-45bb-8eea-2a4ee08a803c    2eaa996b-267f-4c9c-a58e-d1759c27c46c.txt    b18798c0786f15af3a0734dadae8cc19    525766    submitted

file1は例えば480de2f2-6f01-43e9-bc1b-77b8ec8451f5.txt
といったファイル名で中身は下記の通りです。

0.0679637658767
0.00471509417358
2.7638655666
0.0
4.21007764058
18.1976585455
0.0
0.141924334625
76.4268070169
0.140819865095
0.0
0.0
0.0
28.6577220146
0.0338151883479
1.77092901396
8.68206352022
0.0
0.0
6.47409128452
0.0

最終的に欲しいのはこんな感じのファイルです。

ID_001 0.0679637658767
ID_001 0.00471509417358
ID_001 2.7638655666
ID_001 0.0
ID_001 4.21007764058
ID_001 18.1976585455
ID_001 0.0
...
ID_002 1.77092901396
ID_002 8.68206352022
ID_002 0.0
ID_002 0.0

...
  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 過去に投稿した質問と同じ内容の質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

質問への追記・修正、ベストアンサー選択の依頼

  • asahina_dev

    2016/07/30 19:41

    元データのサンプルファイルを書くべき

    キャンセル

回答 3

checkベストアンサー

0

自分もノーテストなんで。(^_^;

awk '{print $1,$3}' file2 | \
while read id fn
do
  sed "s/^/$id /" $fn >>file3
done

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2016/07/30 20:51

    ありがとうございます。
    うまくワークしました!
    もう少し、皆さんのやり方を参考にさせて頂きたいので質問をクローズせずにおかせてください。

    キャンセル

0

タイポしてたらごめんなさい。(ノーテスト)

file1=$1; # file1.txt 
cat $file1 | while read line;
do
    id=$(   echo $line | cut -d '\t' -f 1);
    file2=$(echo $line | cut -d '\t' -f 3);

    for line2 in $(cat $file2);
    do
        echo $id $lien2;
    done;
done;

多分TSVだとみたので '\t' になってますが スペース区切りなら ' ' にしてください。

 処理概要

  1. ファイル1を設定(引数化のため)
  2. 1行ずつ処理
    4.その行の id を取得
    5.その行の file2 を取得
    7.ファイル2をループ
    9.出力形式を指定して出力

※ sh ファイル化して リダイレクトして file3 に出力してください。

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2016/07/30 21:13

    ありがとうございます。
    基本的には上手くいきました。

    ただ、file1が1列じゃなくて2列になった場合は、
    ID、1列目、2列目ではなくて

    ID、1列目
    ID、2列目
    となってしまいました。

    キャンセル

  • 2016/07/30 21:25

    その場合は file2 でも `id` `file2` をとるような処理を追加してください

    キャンセル

0

皆さんと異なるものに敢えてしました。sed方が良いとは思ってます。

while read -a arr; do
 awk -v ar=${arr[0]} '{print ar,$0}' ${arr[2]} >>file3
done<file2

ご説明不足にて失礼いたしました。

while read -a arr;do
    #whileのreadにてfile2を変数arrに読み込みます。1行づつ
    #その際whileに-aを付ける事でarrに配列として値がセットされます。
    #file2は空白でセパレートされているのでデフォルトで分離されます。
    #他の場合,であればIFSで変更できます。
    #${arr[0]},${arr[1]},${arr[2]}に値file2の値がセットされます。

 awk -v ar=${arr[0]} '{print ar,$0}' ${arr[2]} >>file3
      #awkの内部の変数arに値を設定する為に-vを使います。${arr[0]}をar変数に渡します。
      #${arr[2]}はファイル名が展開(awk実行前)されますので awkの入力ファイルとなります。<file2
      #awkでは$0で入力ファイル行の全体を示しています、その前にarr変数値をつけます。
      #arr,$0とカンマを入れると空白間に付けて出力します,カンマで無く空白だと結合し出力されます。
      #print出力は>>でfaile3へ追加します。

done<file2
    #whileへの入力ファイルとします。

読み方のポイントは、bashが必ず先に処理を行った後にawkが実行される事に有ります。bashにとってはawkはただのコマンドです。whileにてfile2の行数分awk実行されます。
さらに速度を求めるのであればfile2の読込みもawkで全て行うと早なると思います(修正大変ですが)。bashのloopは速度が出ないので。

言った手前書きました旨く行くとよいのですが・・・

awk '{cc=$1;ff=$3;while(getline <ff >0){print cc,$0;}}' file2 >>file3

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2016/07/31 19:15

    ありがとうございます。
    上手くいきました。1.7MBのファイル180個くらいで合計350MB位のファイルになるのですが、一番速かったです。

    キャンセル

  • 2016/09/22 01:03

    古い質問の続きで申し訳ありません。
    回答頂いたときに何をしているのか良く分からなかったのですが、awkを少し調べれば分かるものと思っていました。
    でも、色々調べても何でうまくいくのかさっぱり分かりません。
    お手数お掛けしますが、それぞれ何をしているのか解説して頂けないでしょうか?
    宜しくお願いします。

    キャンセル

  • 2016/09/22 17:00

    ありがとうございます!
    とてもわかりやすかったです。すっきりしました。
    readのaオプション説明が持っている本やwebページには無く、arr[0]が$0と同じように行全部を示すのかと思っていました。

    全部awkでやるものも上手く動きました。
    あまりにも速くて失敗したかと思ったぐらいでした。
    また宜しくお願いします。

    キャンセル

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 88.80%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる

関連した質問

同じタグがついた質問を見る