2010-10-15 102 views
3

我正在編寫一個腳本,它將一個文件名作爲參數,在每行的開頭找到一個單詞 - 在這種情況下,單詞ATOM - 並打印特定列中的值。用Awk或Cut打印列?

$FILE=*.pdb * 

if test $# -lt 1 
then 
echo "usage: $0 Enter a .PDB filename" 
exit 
fi 
if test -r $FILE 
then 
grep ^ATOM $FILE | awk '{ print $18 }' | awk '{ print NR $4, "\t" $38,}' 
else 
echo "usage: $FILE must be readable" 
exit 
fi 

我有麻煩搞清楚三個問題:

  1. 如何用awk打印只包含原子作爲第一個字線
  2. 如何使用awk來只打印某些列從符合上述標準的行中,具體是第2-20列和第38-40列
  3. 我該如何指出這必須是一個pdb文件? * .PDB *

回答

1

相反的答案用法消息並退出,你的任務可以只用一個awk命令來實現。不需要grep或剪切或...

if [ $# -lt 1 ];then 
echo "usage: $0 Enter a .PDB filename" 
exit 
fi 
FILE="$1" 
case "$FILE" in 
*.pdb) 

if test -r $FILE 
then 
# do for 2-20 assuming whites paces as column separators 
awk '$1=="ATOM" && NF>18 { 
    printf "%s ",$2 
    for(i=3;i<=19;i++){ 
    printf "%s ",$i 
    } 
    printf "%s",$20 
}' "$FILE" 
else 
echo "usage: $FILE must be readable" 
exit 
fi 
;; 
*) exit;; 
esac 
+0

這真棒!謝謝ghostdog。 – Koala 2010-10-16 17:46:13

4
  1. 這將是

    awk '$1 == "ATOM"' $FILE 
    
  2. 這項任務可能是更好的成就與cut

    grep ^ATOM $FILE | cut -c 2-20,38-40 
    
  3. 如果你想確保文件名傳遞因爲腳本的第一個參數以.pdb結尾:首先,請不要(文件擴展名不要在UNIX LLY關係),其次,如果你一定要,這裏有一個方法:

    "${1%%.pdb}" == "$1" && echo "usage:..." && exit 1 
    

    這需要第一個命令行參數($1),如果存在去掉後綴.pdb,然後將其比作原始的命令行參數。如果它們匹配,它沒有後綴,所以程序打印狀態碼爲1

+0

謝謝大衛!我可以問爲什麼你說'請不要'參數不僅限於.pdb文件?如果我需要打印的欄目只是在第18-30欄中有條目的類型,我是否應該分別管道化每個欄目? grep^ATOM $ 1 |切-f 18-30 | cut -f 2-20,38-40 – Koala 2010-10-15 19:50:09

+0

@Koala:對於文件名的事情,如果你想在名字以'.txt'結尾的文件上使用你的程序怎麼辦?或'.csv'?或'.bak'?或者是一個名字沒有擴展名的文件?僅僅因爲文件名不符合一些任意的約定而使程序失敗似乎不是一件愚蠢的事情?當然,這是你的程序,所以你可以讓它檢查文件名,如果你想要的話,但如果我的經驗是任何指導,最終會有一個時候你會想擺脫檢查。其他UNIX實用程序(例如'grep'和'awk')不檢查文件名;這是有原因的。 – 2010-10-15 20:29:50

+0

至於你的問題的第二部分,關於專欄,我不明白你在問什麼。 – 2010-10-15 20:31:15