Text-Processing

循環通過 awk 輸出

  • July 10, 2020

我有一系列的字元串。它們由標記為“節點”的較小字元串組成,有時獨立,有時由字元:,.

我想將較大的字元串(“標題”)拆分為“節點”。

我已經設法用 sed 刪除了一些額外的字元(>, ;, '),並且我正在使用 awk 將剩餘的字元串拆分:,

問題是我想循環輸出(“節點”),而不僅僅是第一個 awk 列。我嘗試過使用{print $0}for awk,但這只是列印出帶有分隔符的初始字元串等等。

請幫忙?

範例輸入(由範例中的 for 循環處理,在較大的程式碼中它是 if/else 的輸出):

>NODE_3028138_length_2215_cov_1.9513_ID_6056275:NODE_6264558_length_375_cov_4.0000_ID_12529115';
>NODE_4338305_length_1150_cov_1.0000_ID_8676609;
>NODE_3552704_length_509_cov_1.0000_ID_7105407:NODE_4456634_length_439_cov_1.9597_ID_8913267',NODE_4457268_length_491_cov_0.9657_ID_8914535';

範例輸出(沒有節點 NODE_4338305,因為它是獨立的):

NODE_3028138_length_2215_cov_1.9513_ID_6056275
NODE_6264558_length_375_cov_4.0000_ID_12529115
NODE_3552704_length_509_cov_1.0000_ID_7105407
NODE_4456634_length_439_cov_1.9597_ID_8913267
NODE_4457268_length_491_cov_0.9657_ID_8914535

理想情況下,我想遍歷上面的每個條目(NODE_3028138_length_2215_cov_1.9513_ID_6056275然後NODE_6264558_length_375_cov_4.0000_ID_12529115等)

for i in ">NODE_3028138_length_2215_cov_1.9513_ID_6056275:NODE_6264558_length_375_cov_4.0000_ID_12529115';" \
">NODE_4338305_length_1150_cov_1.0000_ID_8676609;" \
">NODE_3552704_length_509_cov_1.0000_ID_7105407:NODE_4456634_length_439_cov_1.9597_ID_8913267',NODE_4457268_length_491_cov_0.9657_ID_8914535';"
do      
if [[ $i == *":"* ]];         
then 
echo $i            
i=$(sed "s/[>;\']//g" <<< $i);            
echo $i
echo $i | awk -F '[:,]' '{print $1}' | while IFS= read -r line; do echo "$line"; done
fi; done

編輯以添加作業系統資訊:

  • 作業系統:CentOS Linux 7(核心)
  • 核心:Linux 3.10.0-1127.el7.x86_64
  • 架構:x86-64

您不需要顯示的任何步驟。如果我理解正確,您可以從一組 fasta 文件開始,格式如下:

>header
sequence

並且您想提取標題,刪除>and any'並將它們拆分為,or ;。如果是這樣,您可以直接在 fasta 文件本身上執行此操作:

$ sed -n '/^>/{s/>//; s/[,:]/\n/gp}' *.fasta | tr -d "';"
NODE_3028138_length_2215_cov_1.9513_ID_6056275
NODE_6264558_length_375_cov_4.0000_ID_12529115
NODE_3552704_length_509_cov_1.0000_ID_7105407
NODE_4456634_length_439_cov_1.9597_ID_8913267
NODE_4457268_length_491_cov_0.9657_ID_8914535

解釋

  • sed -n:禁止正常輸出,除非明確告知,否則不要列印任何內容。
  • /^>/{something}: 如果此行以 a 開頭>,請執行something.
  • s/^>//;>從行首刪除。
  • s/[,:]/\n/gp: 全部替換(全部是因為g末尾的),:換行符(\n)然後列印(因為p末尾的而列印。
  • tr -d "';":刪除任何;'

在您的評論中,您說您嘗試過'i=$(sed "s/[:,]/\n/g" <<< $i)'並且只有空格,而不是換行符。那是因為你然後跑echo $i而不是echo "$i",所以換行符失去了。


如果您確實需要對顯示的字元串集合執行此操作,您可以執行以下操作:

for i in ">NODE_3028138_length_2215_cov_1.9513_ID_6056275:NODE_6264558_length_375_cov_4.0000_ID_12529115';" ">NODE_4338305_length_1150_cov_1.0000_ID_8676609;" ">NODE_3552704_length_509_cov_1.0000_ID_7105407:NODE_4456634_length_439_cov_1.9597_ID_8913267',NODE_4457268_length_491_cov_0.9657_ID_8914535';"; do 
   sed -n '/^>/{s/>//; s/[,:]/\n/gp}' <<<"$i" | tr -d "';" ; 
done
NODE_3028138_length_2215_cov_1.9513_ID_6056275
NODE_6264558_length_375_cov_4.0000_ID_12529115
NODE_3552704_length_509_cov_1.0000_ID_7105407
NODE_4456634_length_439_cov_1.9597_ID_8913267
NODE_4457268_length_491_cov_0.9657_ID_8914535

引用自:https://unix.stackexchange.com/questions/597571