Проверьте, не является ли строка ни пустой, ни пробелом в сценарии оболочки


93

Я пытаюсь запустить следующий сценарий оболочки, который должен проверять, не является ли строка ни пробелом, ни пустой. Однако я получаю одинаковый результат для всех трех упомянутых строк. Я также пробовал использовать синтаксис "[[", но безрезультатно.

Вот мой код:

str="Hello World"
str2=" "
str3=""

if [ ! -z "$str" -a "$str"!=" " ]; then
        echo "Str is not null or space"
fi

if [ ! -z "$str2" -a "$str2"!=" " ]; then
        echo "Str2 is not null or space"
fi

if [ ! -z "$str3" -a "$str3"!=" " ]; then
        echo "Str3 is not null or space"
fi

Я получаю следующий результат:

# ./checkCond.sh 
Str is not null or space
Str2 is not null or space

В сценариях оболочки пустые строки называются нулевыми строками?
Джозия Йодер,

Ответы:


124

Вам нужно пространство по обе стороны от !=. Измените свой код на:

str="Hello World"
str2=" "
str3=""

if [ ! -z "$str" -a "$str" != " " ]; then
        echo "Str is not null or space"
fi

if [ ! -z "$str2" -a "$str2" != " " ]; then
        echo "Str2 is not null or space"
fi

if [ ! -z "$str3" -a "$str3" != " " ]; then
        echo "Str3 is not null or space"
fi

Спасибо большое, это работает. Но мне интересно, почему в присваивании не используется пробел, а в сравнении.
Шубханшу Мишра

5
^^ Это синтаксис. Первое слово в командной строке - это команда, а последующие - аргументы. var=value [command [args]]это синтаксис, в котором переменной присваивается значение. для сравнения [( /usr/bin/[) - это команда, и она требует, чтобы var1,! = & var2 были тремя отдельными аргументами. var1! = var2 - единственный аргумент.
anishsane

63

Для проверки пустой строки в оболочке

if [ "$str" == "" ];then
   echo NULL
fi

ИЛИ

if [ ! "$str" ];then
   echo NULL
fi

9
Оператор равенства строк оболочки - =. Это ==непереносимый хакер, изобретенный авторами оболочки, чтобы запутать умы молодых программистов.
Йенс

17

Если вам нужно проверить любое количество пробелов, а не только одно, вы можете сделать это:

Чтобы удалить строку лишнего пробела (также объединяет пробелы в середине с одним пробелом):

trimmed=`echo -- $original`

В --гарантирует , что если $originalсодержит переключатели понято эхом, они все равно будут рассматриваться как нормальные аргументы , которые будут выводиться. Кроме того , важно не ставить ""вокруг $original, или пространства не будут удалены.

После этого вы можете просто проверить, $trimmedпуст ли.

[ -z "$trimmed" ] && echo "empty!"

3
В оболочке Bourne я получаю «-» в качестве значения усеченного.
Шридхар Сарнобат

Согласно этому сообщению , эхо не интерпретирует - означает конец опций. В моей оболочке Bash я получаю тот же результат, что и Шридхар Сарнобат
Mr.C

9

Еще один быстрый тест на наличие в строке чего-то, кроме пробела.

if [[ -n "${str// /}" ]]; then
    echo "It is not empty!"
fi

«-n» означает строку ненулевой длины.

Тогда первые две косые черты означают совпадение всего следующего, в нашем случае пробелов. Затем за третьей косой чертой следует замещающая (пустая) строка и закрывается знаком "}". Обратите внимание на отличие от обычного синтаксиса регулярных выражений.

Вы можете узнать больше о манипуляциях со строками в сценариях оболочки bash здесь .


не [[ -n "$1" ]]то же самое, что [[ ! -z "$1" "]]?
Александр Миллс

@AlexanderMills, вы правы, использование -n сделало бы его немного короче. Я просто обновил ответ соответственно.
elomage

6

Чтобы проверить, пуста ли строка или содержит только пробелы, вы можете использовать:

shopt -s extglob  # more powerful pattern matching

if [ -n "${str##+([[:space:]])}" ]; then
    echo '$str is not null or space'
fi

См. Раздел « Расширение параметров оболочки и сопоставление с образцом» в Руководстве по Bash.


1
[ $(echo $variable_to_test | sed s/\n// | sed s/\ //) == "" ] && echo "String is empty"

Удаление всех символов новой строки и пробелов из строки приведет к тому, что пустая строка будет сведена к нулю, что можно проверить и принять меры.

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.