2012-10-10 53 views
1

我有這個字符串:如何選擇替代空間與猛砸字符串只

str='1 2 3 var="foo bar" 4 5 6' 

此外,它可能是這樣的:

str="1 2 3 var='foo bar' 4 5 6" 

我怎麼會跟+僅更換引號內的空間(雙人或單身)?

結果應該是這樣的:

1 2 3 var="foo+bar" 4 5 6 

1 2 3 var='foo+bar' 4 5 6 

萬一var爲單引號。

var可以是任何東西,它不是很強的匹配。 此外,它可能會錯過可言,像這樣:

str='1 2 3 "foo bar" 4 5 6' 

我不想用awk,sed或Perl來做到這一點。

+0

在這裏看到我的回答 - HTTP:// stackoverflow.com/questions/12821302/split-a-string-only-by-spaces-that-are-outside-quotes - 它確實是你要求 – 2012-10-10 21:27:57

回答

3

以字符爲單位循環遍歷字符串。保持一個標誌,告訴你是否在報價單內。根據該標誌,如果需要更換空間:

#! /bin/bash 
str='1 2 3 var="foo bar" 4 5 6' 

result='' 
inside=0 
for ((i=0 ; i<${#str} ; i++)) ; do 
    char=${str:i:1} 
    if [[ $char == [\"\'] ]] ; then 
     let inside=!inside 
    fi 
    ((inside)) && char=${char/ /+} 
    result+=$char 
done 
echo $result 
0
$ echo $str | awk -F= '{sub(/ /,"+",$2);}1' OFS="=" 
1 2 3 var='foo+bar' 4 5 6 

使用awk,僅在第二個字段中使用+替換空格(第二個字段恰好是由=分隔時的表達式)。

+1

請看OP,沒有awk,'var'也可能會丟失,也可能有雙引號或單引號 –

0

這是相同的choroba的回答,只是用不同的技術來遍歷字符串:

#!/bin/bash 

str='1 2 3 var="foo bar" 4 5 6' 
result='' 
declare -i inside=0 
while IFS= read -n1 char; do 
    [[ $char = [\"\'] ]] && inside=!inside 
    ((inside)) && char=${char/ /+} 
    result+=$char 
done <<< "$str" 
echo "$result"