2012-08-11 57 views
0

此功能:

source foo.bash && foo -n "a b c.txt" 

的問題是,不管是什麼我已經試過,我不能」噸得到最後一行echo "$CMD"(或echo $CMD)生成正是這種輸出:

cat -n "a b c.txt" 

如何實現這一目標?

# foo.bash 
function foo() { 
    local argv=("[email protected]"); 
    local OUT=`cat "${argv[@]}"` 
    local CMD=`echo cat "${argv[@]}"` 
    echo "--------------------------" 
    echo "$OUT" 
    echo "--------------------------" 
    echo "$CMD" 
} 

輸出是代替:

cat -n a b c.txt 

使用這個命令:foo -n \"a b c.txt\"它的工作用於命令的顯示,但它給錯誤用於經由反引號的執行。

文件"a b c.txt"是一個有效的小文本文件。

+0

我提供了一個答案,但我希望你不打算用該輸出調用eval。 – jordanm 2012-08-11 19:21:12

+0

我不確定這是否可能,當你說'foo -n「a b c.txt」'bash把參數當作'-n'&'a b c.txt'去掉引號並保留空格。在'foo -n \「a b c.txt \」'的情況下,參數是'-n',''a','b'&'c.txt「'。我不知道你是否可以做你正在嘗試做什麼,即使bash保留報價,而默認行爲恰好是剝離。也許'IFS'魔術......或其他什麼。沒什麼我能想到的 – 2012-08-11 19:27:23

+0

@ another.anon.coward是的,但是它對'local OUT = \'cat「$ {argv [@]}」\''起作用,如果它不可能的話,不應該爲那個工作。對? – Flavius 2012-08-11 19:29:53

回答

0

你走了,在number of tokens in bash variable的幫助下,我提出了正確的解決方案。

,我差點忘了爲什麼我們實際需要引用的一個的說法,這是因爲它具有多個單詞!

function foo() { 
    local argv=("[email protected]"); 
    local OUT=`cat "${argv[@]}"` 
    echo "--------------------------" 
    echo "$OUT" 
    echo "--------------------------" 
    local CMD="cat" 
    for word in "${argv[@]}"; do 
     words="${word//[^\ ]} " 
     if [[ ${#words} > 1 ]]; then 
      local CMD="$CMD \"${word}\"" 
     else 
      local CMD="$CMD $word" 
     fi 
    done 
    echo "$CMD" 
} 

希望它有助於某人。

0

你需要躲避分配的內部報價:

local CMD="cat \"${argv[@]}\"" 

而且,不需要回音連接字符串。

+0

這給出了'cat「-nab c.txt」 ',這也不是我所期望的,請注意,所提供的代碼只是一個PoC,可能有任何標誌(該命令實際上是'git'),我期望與鍵入的內容完全相同:'' cat -n「ab c.txt」' – Flavius 2012-08-11 19:23:41

+1

@Flavius - 引號永遠不會傳遞被調用的函數。 – jordanm 2012-08-11 19:47:08