リスト内のすべての値を互いに乗算するコマンド?

リスト内のすべての値を互いに乗算するコマンド?

以下のデータのリストがありますdata.txt

Sample A
   12 
   0
   29
   238
   0
   4

基本的には生物学的サンプル(単一列)と特定遺伝子の発現(320以上の行)です。各行の各値を互いに乗算して、次のようoutput.txtな結果を得たいと思います。

-      -    -      -    -   -
0      -    -      -    -   -
348    0    -      -    -   -
2856   0    82824  -    -   -
0      0    0      0    -   -
48     0    116    952  0   -

私は現在Excelでこれを手動で実行していますが、これは痛いです。 (私は生物学者であり、UNIXやコーディング全体に精通していません。)awk(または他のコマンドを使って)これを行う方法はありますか?

また、実際には約300個のサンプル(つまり300個の別々のファイル)がありますが、data.txt300個のサンプル(つまり、300個の列、320個の行、各行と列の値)の両方を含むファイルに対してスクリプトを実行できる場合は、良いことは、data.txtoutput.txtサンプル(列)ごとに300個の別々のファイルを取得することです。

答え1

実際にはそれほど難しくありませんawk。たとえば、ファイル全体を(1d)配列に配置し、単一のデータファイルに対して二重ループを実行できます。

awk '
  NR > 1 {
    x[NR-1] = $1;
  }
  END {
    for (i=1; ;i++) {
      if (!(i in x))
        break;
      for (j=1; ;j++) {
        if (!(j in x))
          break;
        if (j < i)
          printf "%-6d", x[j]*x[i];
        else
          printf "%-6s", "-";
      }
      printf "\n";
    }
  }
  ' data.txt

上三角形をダッシュ​​で埋めようとしない場合は、直線を使用して作業する方が簡単です。つまり、ファイル全体をロードしません。

awk '
  NR > 1 {
    x[NR-1] = $1;
    for (j=1;j<NR-1;j++)
      printf "%-6d", $1*x[j];
    printf "%-6s\n", "-";
  }
  ' data.txt
-
0     -
348   0     -
2856  0     6902  -
0     0     0     0     -
48    0     116   952   0     -

データセットが大きい場合、このアプローチはメモリ使用量の面で利点を提供できます。

複数のファイル引数を処理するには少し調整が必要です。 GNU awkがある場合は、次の規則を使用できBEGINFILEますENDFILE

gawk '
  BEGINFILE {
    delete x;
  }
  FNR > 1 {
    x[FNR-1] = $1;
    next;
  }
  ENDFILE {
    n = length(x);
    for (i=1;i<=n;i++) {
      for (j=1;j<=n;j++) {
        if (j < i)
          printf "%-6d", x[j]*x[i];
        else
          printf "%-6s", "-";
      }
      printf "\n";
    }
    printf "\n";
  }
  ' data1.txt data2.txt

それ以外の場合は、gawkFNRが1にロールバックされた時点を確認してBEGINFILE / ENDFILEをシミュレートできます。


しかし、データセットが大きい場合は、GNUなどの行列演算用に構築されたものを使用することをお勧めしますoctave(基本的には製品の下部三角形が欲しいと思いますか?)

インタラクティブなOctaveインタプリタまたは次のような「バッチ」モードでこれを行うことができます。

$ octave -q << 'EOF'
> x = textread('data.txt', '%f', 'headerlines', 1);
> M = tril(x * x', -1);
> disp(M);
> EOF
      0      0      0      0      0      0
      0      0      0      0      0      0
    348      0      0      0      0      0
   2856      0   6902      0      0      0
      0      0      0      0      0      0
     48      0    116    952      0      0

特定の出力要件に応じて、単純なsave機能または機能を使用してファイルdlmwriteに書き込んだり、非常にきめ細かい出力形式を制御したい場合に使用できます。上記の三角形のゼロをダッシュ​​に置き換えるには、セルの配列を調べることをお勧めします。Mfprintf

答え2

この特定のタスクを実行できる単一のプログラムがないため、いくつかの(初級レベル)コーディングが必要です。

これを行うためにawkスクリプトを書くことは可能ですが、awkはプログラミング言語に特に適していません。 Perlはそのタスクに適した言語である可能性がありますが、汎用プログラミングまたはスクリプト言語の場合はすべて可能です。あなたはコーディングが好きではないので、あなたのためにプログラムを書いて、言語選択を彼らに任せる誰かを見つけなければなりません(彼らの提案があまりにも多くの設定努力を必要としない限り)。

私が知っている限り、SEの回答には特定のタスクの完全なコードを含めないでください。 :-)

関連情報