如何刪除兩條線之間的單線

如何刪除兩條線之間的單線

我的文件中有數百萬筆記錄,如下所示

echo "NEW Cell"
grep "2553,24" out.2A25.20090308.64436.7.HDF.txt.text = 22.58   5.39  82.09 237
echo "NEW Cell"
grep "2555,20" out.2A25.20090308.64436.7.HDF.txt.text = 24.72   5.58  82.05 237
echo "NEW Cell"
grep "2557,20" out.2A25.20090308.64436.7.HDF.txt.text = 19.75   5.62  82.11 170
grep "2557,21" out.2A25.20090308.64436.7.HDF.txt.text = 24.34   5.58  82.13 120
grep "2558,22" out.2A25.20090308.64436.7.HDF.txt.text = 22.2   5.57  82.19 120
echo "NEW Cell"
grep "2560,22" out.2A25.20090308.64436.7.HDF.txt.text = 24.69   5.62  82.25 160
grep "2561,23" out.2A25.20090308.64436.7.HDF.txt.text = 24.74   5.60  82.30 120
echo "NEW Cell"
grep "2560,24" out.2A25.20090308.64436.7.HDF.txt.text = 19.38   5.54  82.30 170
echo "NEW Cell"

現在我想刪除帶有“grep”的行,條件是它是包含“New Cell”的行之間的唯一行。也就是說,如果新儲存格之間有一行 grep,則應刪除這一行。

這個怎麼做?

我的輸出應該是這樣的

echo "NEW Cell"
grep "2557,20" out.2A25.20090308.64436.7.HDF.txt.text = 19.75   5.62  82.11 170
grep "2557,21" out.2A25.20090308.64436.7.HDF.txt.text = 24.34   5.58  82.13 120
grep "2558,22" out.2A25.20090308.64436.7.HDF.txt.text = 22.2   5.57  82.19 120
echo "NEW Cell"
grep "2560,22" out.2A25.20090308.64436.7.HDF.txt.text = 24.69   5.62  82.25 160
grep "2561,23" out.2A25.20090308.64436.7.HDF.txt.text = 24.74   5.60  82.30 120

答案1

AWK解決方案:

awk 'NR==n{ if (/NEW Cell/) { f=0 } else print r ORS gr }
     /NEW Cell/{ f=1; n=NR+2; r=$0; next }
     f && n-NR==1 && /^grep /{ gr=$0; next }1' file
  • /NEW Cell/{ f=1; n=NR+2; r=$0; next }- 遇到線時NEW Cell

    • f=1= 設定活動標誌f=1
    • n=NR+2- 設定n為要處理的以下行的最大數量(接下來的 2 行)
    • r=$0- 捕獲線
    • next- 跳到下一筆記錄
  • f && n-NR==1 && /^grep /- 遇到以關鍵字n-NR==1開頭的第二行(由 保證)grep

    • gr=$0; next- 捕捉grep行並跳到下一筆(第三筆)記錄
  • NR==n{ if (/NEW Cell/) { f=0 } else print r ORS gr }- 遇到第三條關鍵線時(由 保證NR==n

    • if (/NEW Cell/) { f=0 }- 如果已處理部分下的第 3 行包含NEW Cell- 重置當前處理f=0(跳過所有先前捕獲的行)
    • else print r ORS gr- 否則列印所有先前捕獲的行

輸出:

echo "NEW Cell"
grep "2557,20" out.2A25.20090308.64436.7.HDF.txt.text = 19.75   5.62  82.11 170
grep "2557,21" out.2A25.20090308.64436.7.HDF.txt.text = 24.34   5.58  82.13 120
grep "2558,22" out.2A25.20090308.64436.7.HDF.txt.text = 22.2   5.57  82.19 120
echo "NEW Cell"
grep "2560,22" out.2A25.20090308.64436.7.HDF.txt.text = 24.69   5.62  82.25 160
grep "2561,23" out.2A25.20090308.64436.7.HDF.txt.text = 24.74   5.60  82.30 120

答案2

緊湊型解決方案sed

sed '/NEW Cell/!{H;d;};x;/\n.*\n/!d'

如果該行不包含NEW Cell執行,H則將該行附加到保留空間並d停止對該行的處理。

因此,進一步的命令僅應用於NEW Cell行:x交換模式空間和保持空間,因此該行現在位於保持空間中,並且可以附加更多行,而模式空間包含附加到最後一行的所有內容NEW Cell。您的要求是行與行之間有多於一行NEW Cell,因此模式空間中必須至少有兩個換行符。如果沒有,則刪除它,不輸出:/\n.*\n/!d

答案3

憑藉基本的awk...

版本 1 只會刪除grepOP 描述之後的行:

awk '/^grep/ { if (f) { if (length(s) > 0) { print s; s="" } print } \
     else { f=1; s=$0 } } ! /^echo/ { print; f=0 } \
     ! /^echo/ && ! /^grep/ { print }' inputfile

版本 2 將刪除單獨的grep行以及前面的非 grep 行,該行遵循 OP 的範例輸出:

awk '/^grep/ { if (f) { if (length(s) > 0) { print s; s="" } print } \
    else { f=1; s=s "\n" $0 } } /^echo/ { s=$0; f=0 } \
    ! /^echo/ && ! /^grep/ { print }' inputfile

版本 2 的可讀形式...

/^grep/ { 
   if (found) {  # found==true : already encountered first grep line
       if (length(save) > 0) {
          print save
          save=""
       }
       print
   } else {
       found=1
       save=save "\n" $0  # append the first grep line to saved preceding line
   }
}

/^echo/ { 
    save=$0  # save this line for possible later printing
    found=0
}

# print anything else
! /^echo/ && ! /^grep/ { print }

這個長格式可以透過將內容放入檔案(例如awkfile)和 中來運行awk -f awkfile inputfile

答案4

gawk '
/\n.+\n/{
    printf("%s%s", RS, $0);
}' RS='echo "NEW Cell"\n' input.txt

解釋:

  1. RS='echo "NEW Cell"\n'-RS是輸入記錄分隔符,預設為換行符。現在改為echo "NEW Cell"\n,因此,該字串的所有出現都將被刪除,並且它們之間的所有字元都成為記錄項目。
  2. /\n.+\n/{- 僅適用於與此模式相符的記錄 - 換行符、一個或多個字元、換行符。因此,它僅匹配多行記錄,單行記錄不匹配,因為它只有一個\n.
  3. printf("%s%s", RS, $0);- 列印記錄,前面帶有RS( echo "NEW Cell"\n)。

輸出

echo "NEW Cell"
grep "2557,20" out.2A25.20090308.64436.7.HDF.txt.text = 19.75   5.62  82.11 170
grep "2557,21" out.2A25.20090308.64436.7.HDF.txt.text = 24.34   5.58  82.13 120
grep "2558,22" out.2A25.20090308.64436.7.HDF.txt.text = 22.2   5.57  82.19 120
echo "NEW Cell"
grep "2560,22" out.2A25.20090308.64436.7.HDF.txt.text = 24.69   5.62  82.25 160
grep "2561,23" out.2A25.20090308.64436.7.HDF.txt.text = 24.74   5.60  82.30 120

相關內容