我正在编写一个bash脚本,我需要将包含空格的字符串传递给我的bash脚本中的函数。
例如:
#!/bin/bash
myFunction
{
echo $1
echo $2
echo $3
}
myFunction "firstString" "second string with spaces" "thirdString"
运行时,我期望的输出是:
firstString
second string with spaces
thirdString
然而,实际输出的是:
firstString
second
string
有没有办法将带空格的字符串作为单个参数传递给bash中的函数?
答案 0 :(得分:143)
你应该加上引号,而且你的函数声明是错误的。
myFunction()
{
echo "$1"
echo "$2"
echo "$3"
}
和其他人一样,它对我也有用。告诉我们您正在使用的shell版本。
答案 1 :(得分:17)
上述问题的另一个解决方案是将每个字符串设置为变量,使用由文字美元符号\$
表示的变量调用该函数。然后在函数中使用eval
来读取变量并按预期输出。
#!/usr/bin/ksh
myFunction()
{
eval string1="$1"
eval string2="$2"
eval string3="$3"
echo "string1 = ${string1}"
echo "string2 = ${string2}"
echo "string3 = ${string3}"
}
var1="firstString"
var2="second string with spaces"
var3="thirdString"
myFunction "\${var1}" "\${var2}" "\${var3}"
exit 0
然后输出:
string1 = firstString
string2 = second string with spaces
string3 = thirdString
在尝试解决类似的问题时,我遇到了UNIX的问题,认为我的变量是空间分隔的。我试图使用awk
将管道分隔的字符串传递给函数,以设置稍后用于创建报告的一系列变量。我最初尝试了ghostdog74发布的解决方案,但无法让它工作,因为并非我的所有参数都在引号中传递。在为每个参数添加双引号后,它开始按预期运行。
以下是我的代码之前的状态,并且在状态之后完全正常运行。
之前 - 非功能代码
#!/usr/bin/ksh
#*******************************************************************************
# Setup Function To Extract Each Field For The Error Report
#*******************************************************************************
getField(){
detailedString="$1"
fieldNumber=$2
# Retrieves Column ${fieldNumber} From The Pipe Delimited ${detailedString}
# And Strips Leading And Trailing Spaces
echo ${detailedString} | awk -F '|' -v VAR=${fieldNumber} '{ print $VAR }' | sed 's/^[ \t]*//;s/[ \t]*$//'
}
while read LINE
do
var1="$LINE"
# Below Does Not Work Since There Are Not Quotes Around The 3
iputId=$(getField "${var1}" 3)
done<${someFile}
exit 0
After - 功能代码
#!/usr/bin/ksh
#*******************************************************************************
# Setup Function To Extract Each Field For The Report
#*******************************************************************************
getField(){
detailedString="$1"
fieldNumber=$2
# Retrieves Column ${fieldNumber} From The Pipe Delimited ${detailedString}
# And Strips Leading And Trailing Spaces
echo ${detailedString} | awk -F '|' -v VAR=${fieldNumber} '{ print $VAR }' | sed 's/^[ \t]*//;s/[ \t]*$//'
}
while read LINE
do
var1="$LINE"
# Below Now Works As There Are Quotes Around The 3
iputId=$(getField "${var1}" "3")
done<${someFile}
exit 0
答案 2 :(得分:6)
此问题的最简单解决方案是,在运行shell脚本时,您只需要使用\"
作为空格分隔的参数:
#!/bin/bash
myFunction() {
echo $1
echo $2
echo $3
}
myFunction "firstString" "\"Hello World\"" "thirdString"
答案 3 :(得分:5)
你对myFunction的定义是错误的。它应该是:
myFunction()
{
# same as before
}
或:
function myFunction
{
# same as before
}
无论如何,它看起来很好,并且在Bash 3.2.48上对我有效。
答案 4 :(得分:1)
对我有用的简单解决方案 - 引用$ @
Test(){
set -x
grep "$@" /etc/hosts
set +x
}
Test -i "3 rb"
+ grep -i '3 rb' /etc/hosts
我可以验证实际的grep命令(感谢set -x)。
答案 5 :(得分:1)
我迟到了9年,但更灵活的方式是
function myFunction
{
for i in $*; do echo $i; done;
}
答案 6 :(得分:-1)
如果您的初始文本已设置为字符串类型变量,则可以扩展此问题,例如:
function status(){
if [ $1 != "stopped" ]; then
artist="ABC";
track="CDE";
album="DEF";
status_message="The current track is $track at $album by $artist";
echo $status_message;
read_status $1 "$status_message";
fi
}
function read_status(){
if [ $1 != "playing" ]; then
echo $2
fi
}
在这种情况下,如果你没有将status_message变量作为字符串向前传递(由“”包围),它将被拆分为一组不同的参数。
“$ variable”:目前的曲目是ABC在DEF的CDE
$ variable :
答案 7 :(得分:-2)
有同样的问题,事实上问题不是函数和函数调用,而是我作为参数传递给函数。
该函数是从脚本体中调用的 - 'main' - 所以我从命令行传递“st1 ab”“st2 cd”“st3 ef”并使用myFunction $ * <传递给函数/ p>
$ *会导致问题,因为它会扩展为一组字符,这些字符将在使用空格作为分隔符的函数调用中进行解释。
解决方案是将显式参数处理中的函数调用从'main'更改为函数:调用将是myFunction“$ 1”“$ 2”“$ 3”,它将保留字符串中的空格作为引号将界定论点...... 因此,如果参数可以包含空格,则应在所有函数调用中显式处理它。
由于这可能是长时间搜索问题的原因,因此永远不要使用$ *来传递参数......
希望有一天能帮到某个人...... 一月