我有兩個文件:master.tbl
和sites.lst
該檔案master.tbl
是一個站點列表,包含其連接埠配置、連接埠名稱、IP 位址等。包含站點配置的行如此排列,並由空格分隔:
{server} {SITE NAME} {port name} {configuration flags}
連接埠名稱由小寫站點名稱、破折號、「P」和連接埠號碼組成。
例子:
server01 HAWAII23-USR hawaii23-P1 blah-configuration-blah-arguments
server01 HAWAII23-ADM hawaii23-P2 blah-configuration-blah-arguments
server01 HAWAII23-ADM hawaii23-P3 blah-configuration-blah-arguments
server01 HAWAII23-USR hawaii23-P4 blah-configuration-blah-arguments
sites.lst
是我需要搜尋文件的網站列表master.tbl
。
我需要註解掉(#
在行首插入 a ),並提取stoplist.lst
滿足以下所有條件的每一行的伺服器名稱和連接埠名稱(到名為 的檔案中):
- 包含中列出的任何網站名稱
sites.lst
- 包含“-ADM”
- 連接埠號碼大於“2”(範例
hawaii23-P3
:)
在上面的範例中,該master.tbl
文件將如下所示:
server01 HAWAII23-USR hawaii23-P1 blah-configuration-blah-arguments
server01 HAWAII23-ADM hawaii23-P2 blah-configuration-blah-arguments
#server01 HAWAII23-ADM hawaii23-P3 blah-configuration-blah-arguments
server01 HAWAII23-USR hawaii23-P4 blah-configuration-blah-arguments
……並且stoplist.lst
將包含(假設HAWAII23
位於 中sites.lst
):
server01 hawaii23-P3
master.lst
幾乎有 300,000 行,所以手動執行此操作會......很糟糕。
答案1
這是一個awk
解決方案:
awk 'NR==FNR{z[$0"-ADM"]++;next}
{p=$3;sub(/.*-P/, "", p); if ($2 in z && p > 2)
{print $1,$3 > "stoplist.lst"; $0="#"$0}}1' sites.lst master.tbl
sites.lst
首先讀取並將$0"-ADM"
(即網站名稱 + 字串-ADM
)設定為陣列的索引z
。然後,它會將第三個欄位中master.tbl
的值提取為and,如果滿足條件(第二個欄位在且大於 2),它將列印第一個和第三個欄位並註解掉該行。 請注意,它不會就地編輯文件,但如果一切正常,您始終可以重定向到另一個文件並覆蓋原始文件(儘管最近您可以選擇)。-P
p
z
p
stoplist.lst
gnu awk
-i inplace