テキストが多すぎて事前に申し訳ありません。既存のデータ構造を表現する方法がわかりません。
サーバーから毎時間収集された約1年分のログを受け取りました。
残念ながら、データ収集スクリプトを変更して必要な方法でファイルを構築するのは簡単ですが、まだ何千もの既存のファイルを変換する必要があります。私はここで少し苦労しており、それが私の能力の外であるかどうか、精神的にこの方法を必要以上に困難にしていると疑います。
以下は、実行の1つの基本的な繰り返しです(毎時間5分ごとに実行)。
2350
id pool type rid rset min max size used load
5 SUNWtmp_serverxd1z1 pset 1 SUNWtmp_serverxd1z1 104 104 104 0.00 6.25
4 SUNWtmp_serverxd1z2 pset 2 SUNWtmp_serverxd1z2 16 16 16 0.00 0.91
0 pool_default pset -1 pset_default 24 66K 24 0.00 1.74
id pool type rid rset min max size used load
5 SUNWtmp_serverxd1z1 pset 1 SUNWtmp_serverxd1z1 104 104 104 5.01 6.21
4 SUNWtmp_serverxd1z2 pset 2 SUNWtmp_serverxd1z2 16 16 16 0.97 0.91
0 pool_default pset -1 pset_default 24 66K 24 3.73 1.78
出力は切り捨てられますが、前のタイムスタンプから次のタイムスタンプまで50行続きます。
ブロック引用符で数字を表示する方法はわかりませんが、各実行の長さは50行です(すべて1日に約14400行のファイルにまとめられ、各行の前のフィールドは次から派生した日付です。ファイル名)。
これが彼らが望む方法です。フィールドの位置は、スペースに関する限り重要ではないようです。 2まで繰り返されると表示されますが、実際には50行(全データ収集実行)ごとに繰り返される新しいフィールド「int」を含む相対フィールド位置です。 01から始まります。
date hhmm int id pool type rid rset min max size used load
20121105 2350 01 5 SUNWtmp_serverxd1z1 pset 1 SUNWtmp_serverxd1z1 104 104 104 0.00 6.25
20121105 2350 01 4 SUNWtmp_serverxd1z2 pset 2 SUNWtmp_serverxd1z2 16 16 16 0.00 0.91
20121105 2350 01 0 pool_default pset -1 pset_default 24 66K 24 0.00 1.74
date hhmm int id pool type rid rset min max size used load
20121105 2350 02 5 SUNWtmp_serverxd1z1 pset 1 SUNWtmp_serverxd1z1 104 104 104 5.01 6.21
20121105 2350 02 4 SUNWtmp_serverxd1z2 pset 2 SUNWtmp_serverxd1z2 16 16 16 0.97 0.91
20121105 2350 02 0 pool_default pset -1 pset_default 24 66K 24 3.73 1.78
私はいくつかのsedとawk onelinerを試しましたが、残念ながら1linerが処理できるよりも洗練された方法でテキストを操作できなかったことに気づきました。その時点で、私はこのファイルにそれより複雑なものが必要であることがわかりました。
使用したい形式の例:
gawk -vdate=$DATE -vtime=$TIME '{print date " " time $0 }' ./poolstat_original_format.txt
ファイル名から派生した日付と時刻をこれら2つの変数に使用します。
私のシェルスクリプトの私の以前の経験はすべて、システムの自動化とトラブルシューティングに関するもので、テキストの移動についてはあまり実用的な経験をしていませんでした。したがって、これが実際に簡単な質問であり、私が過度に考えているものであれば…すごいです。 、役に立つコメントを送っていただきありがとうございます。
追加情報を追加したかったがキャンセルされました。
日付は渡されたファイル名から派生します。 20121003-poolstat_serverxd1z0.txt時間は50行あたり4桁です。
poolstatが実行されるたびにintフィールドを繰り返す必要があります。詳しくは下記をご覧ください。
要約すると、変更する必要がある唯一のフィールドは次のとおりです。
フィールド1、ファイル名IE:20121003-poolstat_serverxd1z0.txtから派生した8桁の日付、フィールド2、ファイルの50行ごとに4桁の時間。フィールド 3 の繰り返し回数は次のとおりです。 4ビット時間のビット3と4に基づいています。 00-05-10-15-20-25-30-35-40-45-50-55分運行。
01-02-03-04-05-06-07-08-09-10-11-12 繰り返し。
残りの部分は、既存のフィールドを印刷して1行に配置し、awk(または他の)コマンドが現在の反復を追跡しながら他の10フィールドを印刷できるようにすることです。
状況を複雑にするために、ヘッダー行のフィールドには3つの新しいフィールドが必要です。
日付hhmm整数
残りのフィールドは poolstat が提供するヘッダーです。
答え1
私のコメント質問を塩の卵として受け入れると、次のように動作します。
awk -v date=20121105 'NF == 0 {print; next;};
NF==15 && $2 == "id" {readvar=$1; for (i=1;i<15;i++) $i = $(i+1); NF=14; };
NF==14 { if (block<2) block++;
concatvars=$1; for (i=2;i<11;i++) concatvars=concatvars " " $i;
print "date hhmm int",concatvars,date,readvar,sprintf("%02d", block),"05"; };
NF==10 {readvar2=$7;
print $1,"pset 1",$1,$2,$3,$4,$5,$6,date,readvar,sprintf("%02d", block);};
NF==15 {
print readvar2,$1,"pset 2",$1,$2,$3,$4,$5,$6,date,sprintf("%02d", block),$7;
nextline=$8; for (i=9;i<15;i++) nextline=nextline " " $i; };
NF==1 {print nextline,$1}' inputfile
答え2
ブロックの先頭から時間を取得し、その後の各行にいくつかのフィールドを追加する必要があるようです。
あなたの説明によると、繰り返しをどのように実行するのかわかりません。
awk -v date=20121105 '
NF == 1 {time = $1; intv = intv%50 + 1; next}
$1 == "id" {print "date", "hhmm", "int", $0; next}
NF > 0 {$1 = date OFS time OFS sprintf("%02d", intv) OFS $1}
1
' file
出力をよりきれいにしたい場合は、awkコマンドを次にパイプします。column -t