絶えず更新されているファイルからいくつかのデータを抽出しようとしていますが、grepで2つの文字列をフィルタリングする方法を見つけました。出力は次のとおりです。
! total energy = -9744.24963670 Ry
convergence has been achieved in 188 iterations
! total energy = -9744.30001681 Ry
convergence has been achieved in 140 iterations
! total energy = -9744.33953891 Ry
convergence has been achieved in 155 iterations
! total energy = -9744.36584201 Ry
convergence has been achieved in 164 iterations
! total energy = -9744.37925372 Ry
convergence has been achieved in 154 iterations
! total energy = -9744.39185493 Ry
convergence has been achieved in 153 iterations
! total energy = -9744.39836617 Ry
convergence has been achieved in 160 iterations
ここで、これらの行から次のように番号を抽出します。
!で始まる行から列番号5の番号が必要で、grep出力の次の行から列番号6の番号が必要です。
次に、これらの番号を2つの別々の列として別のファイルに次のように書き込みます。
188 -9744.24963670
140 -9744.30001681
155 -9744.33953891
164 -9744.36584201
これらすべてのgrep結果をループし、奇数行を調べて列5を印刷し、偶数行については列6を印刷するという、awkを使用したアプローチを考えていました。しかし、これを行う方法がわかりません。
個々の結果を個別に変数に抽出してみました:
var1=$(grep '!' input.file | awk '{print $5}')
および
var2=$(grep 'convergence has been achieved' input.file | awk '{print $6}')
次に、それらを次のようにファイルに書き込もうとしました:
echo $var1 $var2 > data.dat
ただし、結果は期待どおりではありません:
188
140
155
164
154
153
160 -9744.24963670
-9744.30001681
-9744.33953891
-9744.36584201
-9744.37925372
-9744.39185493
-9744.39836617
上記の形式で書く方法がわかりません。また、ファイルは絶えず更新されるので、コードの一部がwhileループと結合されて終了条件になると想像します(この最後の部分の実行方法を知っています)
これを明確に説明したと思います!
承認された回答:
awk 解決策:
awk 'v && NR==n{ print $6,v > "result.txt" }/^!/{ v=$5; n=NR+1 }' file
-
<condition1> { <statement> ... }<condition2>{ <statement> ... }
–それぞれのステートメントを含む条件は連続して評価されます -
/^!/{ v=$5; n=NR+1 }
–!
で始まる行に遭遇したとき –5番目のフィールド値$5
をキャプチャします 次の行番号を計画しますNR+1
(変数n
への割り当て ) -
v && NR==n
–最初の重要な数値がv
の場合 および現在のレコード番号NR
必要な「次の行番号」n
–値をファイルresult.txt
に出力します
result.txt
ファイルの内容:
188 -9744.24963670
140 -9744.30001681
155 -9744.33953891
164 -9744.36584201
154 -9744.37925372
153 -9744.39185493
160 -9744.39836617