2017-03-23 47 views
-1

我有一個文本文件mytext.txt替換爲值在一個文件中的每一個字,文字的每一行是一個句子:從另一個字典文件

the quick brown fox jumps over the lazy dog 
colorless green ideas sleep furiously 

然後,我有一個字典文件dict.txt像這樣:

the: A 
quick: B 
brown: C 
fox: D 
jumps: E 
over: F 
lazy: G 
dog: H 
colorless: I 
green: J 
ideas: K 
sleep: L 
furiously: M 

我想在dict.txt的值來代替mytext.txt每一個字,就像這樣:

A B C D E F A G H 
I J K L M 

如何ç我使用awk或sed來做它?

+0

另一種選擇這可能是在任何腳本語言要簡單得多。 – pvg

+2

我已經投票決定關閉此問題,因爲它似乎是針對工具或解決方案的建議的請求,而不是您自己的代碼的幫助請求。這使您的問題脫離了StackOverflow。如果評估不正確,並且確實需要編寫自己的代碼,請[將您的工作添加到您的問題中](http://stackoverflow.com/posts/42983982/edit),然後我會收回我的近距離投票。 – ghoti

回答

0
$ awk -F'[: ]' 'FNR==NR{a[$1]=$NF;next}{for(i in a)gsub(i,a[i])}1' dist mytext 

OR

$ awk -F'[: ]' 'FNR==NR{ a[$1]=$NF; next } 
    { for(i=1;i<=NF;i++) if($i in a)$i=a[$i] }1' dist mytext 

輸入

$ cat mytext 
the quick brown fox jumps over the lazy dog 
colorless green ideas sleep furiously 

$ cat dist 
the: A 
quick: B 
brown: C 
fox: D 
jumps: E 
over: F 
lazy: G 
dog: H 
colorless: I 
green: J 
ideas: K 
sleep: L 
furiously: M 

輸出

$ awk -F'[: ]' 'FNR==NR{a[$1]=$NF;next}{for(i in a)gsub(i,a[i])}1' dist mytext 
A B C D E F A G H 
I J K L M 

$ awk -F'[: ]' 'FNR==NR{a[$1]=$NF; next} 
{ for(i=1; i<=NF;i++) if($i in a)$i=a[$i] }1' dist mytext 
A B C D E F A G H 
I J K L M 
+0

完美地工作!謝謝!雖然我的字典包含一些具有多個值的鍵(:A; the:AA),並且此代碼僅與最後一個匹配。 – drstar

+0

@drstar:true,因爲'':'AA'是最後一次讀取第一個文件 –

+0

Downvoter留下您的評論爲什麼這麼說? –

1

如果您dict.txt沒有任何特殊字符,一個非常快的解決方案是dict.txt的內容轉換成一個sed expresion:

sed 's#^#s/#;s#: #/#;s#$#/g;#' dict.txt 

將導致

s/the/A/g; 
s/quick/B/g; 
s/brown/C/g; 
s/fox/D/g; 
s/jumps/E/g; 
s/over/F/g; 
s/lazy/G/g; 
s/dog/H/g; 
s/colorless/I/g; 
s/green/J/g; 
s/ideas/K/g; 
s/sleep/L/g; 
s/furiously/M/g; 

現在這可以被用於另一sed的:

sed -f <(sed 's#^#s/#;s#: #/#;s#$#/g;#' dict.txt) mytext.txt 

輸出:

A B C D E F A G H 
I J K L M 

但要注意,如果字典文件包含特別的sed的/\.* a.s.o.任何字符它wount工作

編輯:添加g到sed的

更新:

如果全字應及時更換,這將這樣的伎倆,因爲\b將查找單詞boundarys:

sed -f <(sed 's#^#s/\\b#;s#: #\\b/#;s#$#/g;#' dict.txt) mytext.txt 

thx @ jm666指出了這一點。

EDIT2:

如果dict.txt文件很長我原來的版本可能會失敗。 @SLePort的版本修復了這個問題,thx。 我以前使用"$()"代替-f <()

+1

不錯的想法。 ;)但是,怎麼樣:「在懶狗本身和'dict'上也會包含'自己:T'?需要對從最長到最短的'///'語句進行​​排序或使用'\ bword \ b'。 – jm666

+0

@ jm666:好點,取決於預期的行爲。我會更新我的答案。 –

+0

或者使用進程替換:'sed -f <(sed's#^#s /#; s#:#/#; s#$#/ g;#'dict.txt)mytext.txt' – SLePort

0

這裏是awksed

$ sed -f <(awk -F': ' '{print "s/\\b" $1 "\\b/" $2 "/g"}' dict) file 

A B C D E F A G H 
I J K L M