2017-08-30 54 views
1

有多少個I比較兩個逗號分隔列表(主和輸入)並列出它們之間的共同值(結果),同時保留主列表中元素的順序。例如:比較兩個逗號分隔的字符串並列出公共值

案例1:

master="common,city,country" 
input="city,country" 

result="city,country" 

的情況下2:

master="common,city,country" 
input="country,pig,cat,common" 

result="common,country" 

的情況下3:

master="common,city,country" 
input="pigs,cars,train" 

result="nothing found" 

這是我的嘗試:

result="$(awk -F, -v master_list=$master'{ for (i=1;i<=NF;i++) { if (master_list~ $i) { echo $i } } } END ' <<< $input)" 

回答

2

這裏是一個AWK-oneliner解決方案:

awk -v RS=",|\n" 'NR==FNR{a[$0]=1;next} 
    {a[$0]++}a[$0]>1{r=r?r","$0:$0} 
    END{print r?r:"Nothing found"}' <(<<< $master) <(<<<$input) 

測試你的三種情況:

案例1

kent$ master="common,city,country" 
kent$ input="city,country" 
kent$ result=$(awk -v RS=",|\n" 'NR==FNR{a[$0]=1;next}{a[$0]++}a[$0]>1{r=r?r","$0:$0}END{print r?r:"Nothing found"}' <(<<< $master) <(<<<$input)) 
kent$ echo $result 
city,country 

案例2

kent$ master="common,city,country" 
kent$ input="country,pigs,cat,common" 
kent$ result=$(awk -v RS=",|\n" 'NR==FNR{a[$0]=1;next}{a[$0]++}a[$0]>1{r=r?r","$0:$0}END{print r?r:"Nothing found"}' <(<<< $master) <(<<<$input)) 
kent$ echo $result 
country,common 

案例3

kent$ master="common,city,country" 
kent$ input="pigs,cars,train" 
kent$ result=$(awk -v RS=",|\n" 'NR==FNR{a[$0]=1;next}{a[$0]++}a[$0]>1{r=r?r","$0:$0}END{print r?r:"Nothing found"}' <(<<< $master) <(<<<$input)) 
kent$ echo $result 
Nothing found 
+0

謝謝。當輸入來自用戶時,當master已經被定義爲變量時,我試圖改變你的腳本。然而,看起來我犯了一些錯誤: result =「$(awk -F,-va = $ master'{for(i = 1; i <= NF; i ++){if(a〜$ i ){print $ i}}}'<<< $ input)「 – Jaanna

+0

你沒有改變我的密碼,你正在重寫我的密碼。您正在使用不同的方法來解決問題。不知道你爲什麼把評論放在我的答案下。如果'master'是由用戶提供的,則沒有區別。我使用'master'作爲**已經定義的** shell變量,'$ input' @Jaanna也是如此 – Kent

2

您可以使用grepBASH字符串操作:

cmn() { 
    local master="$1" 
    local input="$2" 
    result=$(grep -Ff <(printf "%s\n" ${input//,/ }) <(printf "%s\n" ${master//,/ })) 
    echo "${result//$'\n'/,}" 
} 


cmn "common,city,country" "city,country" 
city,country 

cmn "common,city,country" "country,pig,cat,common" 
common,country 

cmn "common,city,country" "pigs,cars,train" 
+1

我最喜歡它。你可以使用'result = $(grep -Ff <(printf「%s \ n」$ {input //,/})<(printf「%s \ n」$ {master //,/}))'' 'echo -n'? –

+0

非常感謝@WalterA的建議。它現在被編輯回答。 – anubhava

1

可以使用通訊工具

my_comm() { 
    res=$(comm -12 <(echo "$1" | tr ',' '\n' | sort) <(echo "$2" | tr ',' '\n' | sort) | xargs | tr ' ' ',') 
    [[ -z $res ]] && echo nothing found || echo $res 
} 

> my_comm common,city,country city,country 
city,country 
> my_comm common,city,country country,pig,cat,common 
common,country 
> my_comm common,city,country pigs,cars,train 
nothing found 
相關問題