我有一个shell脚本与这段代码:
var=`hg st -R "$path"`
if [ -n "$var" ]; then
echo $var
fi
但是条件代码总是执行,因为hg st总是打印至少一个换行符。
是否有一个简单的方法从$var中剥离空白(如PHP中的trim())?
or
有没有处理这个问题的标准方法?
我可以使用sed或AWK,但我认为有一个更优雅的解决方案来解决这个问题。
我有一个shell脚本与这段代码:
var=`hg st -R "$path"`
if [ -n "$var" ]; then
echo $var
fi
但是条件代码总是执行,因为hg st总是打印至少一个换行符。
是否有一个简单的方法从$var中剥离空白(如PHP中的trim())?
or
有没有处理这个问题的标准方法?
我可以使用sed或AWK,但我认为有一个更优雅的解决方案来解决这个问题。
当前回答
这修整了前端和末端的多个空间
whatever=${whatever%% *}
无论= ${无论# *}
其他回答
Use:
trim() {
local orig="$1"
local trmd=""
while true;
do
trmd="${orig#[[:space:]]}"
trmd="${trmd%[[:space:]]}"
test "$trmd" = "$orig" && break
orig="$trmd"
done
printf -- '%s\n' "$trmd"
}
它适用于各种空格,包括换行符, 不需要修改shop。 它保留内部空白,包括换行符。
单元测试(用于手动检查):
#!/bin/bash
. trim.sh
enum() {
echo " a b c"
echo "a b c "
echo " a b c "
echo " a b c "
echo " a b c "
echo " a b c "
echo " a b c "
echo " a b c "
echo " a b c "
echo " a b c "
echo " a b c "
echo " a N b c "
echo "N a N b c "
echo " Na b c "
echo " a b c N "
echo " a b c N"
}
xcheck() {
local testln result
while IFS='' read testln;
do
testln=$(tr N '\n' <<<"$testln")
echo ": ~~~~~~~~~~~~~~~~~~~~~~~~~ :" >&2
result="$(trim "$testln")"
echo "testln='$testln'" >&2
echo "result='$result'" >&2
done
}
enum | xcheck
你可以使用tr删除换行符:
var=`hg st -R "$path" | tr -d '\n'`
if [ -n $var ]; then
echo $var
done
这没有不必要的通配符问题,而且,内部空白是未修改的(假设$IFS被设置为默认值,即' \t\n')。
它一直读取到第一个换行符(但不包括换行符)或字符串的结尾,以先到者为准,并删除任何前导和尾随空格以及\t字符的混合。如果你想保留多行(同时去掉开头和结尾换行符),请使用read -r -d " var << eof;但是请注意,如果您的输入恰好包含\neof,它将在之前被切断。(其他形式的空白,即\r、\f和\v,即使您将它们添加到$IFS,也不会被剥离。)
read -r var << eof
$var
eof
Bash有一个称为参数展开的特性,它允许基于所谓的模式替换字符串(模式类似于正则表达式,但有基本的区别和限制)。 [flussence的原文:Bash有正则表达式,但它们隐藏得很好:]
下面演示如何从变量值中删除所有空白(甚至来自内部)。
$ var='abc def'
$ echo "$var"
abc def
# Note: flussence's original expression was "${var/ /}", which only replaced the *first* space char., wherever it appeared.
$ echo -n "${var//[[:space:]]/}"
abcdef
Use:
var=`expr "$var" : "^\ *\(.*[^ ]\)\ *$"`
它去掉了开头和结尾的空格,我认为这是最基本的解决方案。不是Bash内置的,但'expr'是coreutils的一部分,所以至少不需要像sed或AWK这样的独立实用程序。