Сравнение на низове без значение за малки и главни букви в Bash. if-else условие BASH Bash eq сравнение

Тази тема е четвъртата тема от поредицата „Bash Shell Language“. Той ще говори за такива контролни структури на езика като условни изрази. Но преди да преминете към тяхното описание, е необходимо да се спрем на някои нюанси, които ще направят разглеждането на материала по-долу по-разбираемо.
Първо, нека да разгледаме какво представлява списъкът с команди. Списъкът с команди е единична команда, конвейер или последователност от команди/тръби, разделени с един от следните оператори: ";", "&&", "||", завършващи с точка и запетая.
; - оператор за последователно изпълнение на няколко команди. Всяка следваща команда започва да се изпълнява едва след като предишната е завършена (няма значение дали е била успешна или не);
&& - оператор за изпълнение на команда само след като предходната е изпълнена успешно;
|| - операторът за изпълнение на команда само след като предишната е била изпълнена неправилно.
Кодът за успех е 0, а кодът за грешка не е нула (в зависимост от вида на грешката). Това не трябва да се бърка с конвенционалните езици за програмиране, където 1 е аналогично на true, а 0 е аналогично на false.
Сега можем да започнем директно да разглеждаме условни изрази.

case оператор

Общият синтаксис на оператора case е:

стойност на регистъра в
шаблон1) списък1;;
шаблон2 | шаблон3) списък2;;
esac

Логическата последователност на изпълнение на оператора на случая:
а) търси се първият шаблон, съответстващ на стойността;
б) ако се намери, се изпълнява съответният списък от команди, завършващи с ";;";
в) контролът се прехвърля върху отчетите след изграждането на случая.
Шаблонът и списъкът са разделени със знака ")". Един списък от команди може да отговаря на няколко условия, тогава те трябва да бъдат разделени със символа „|“.
В шаблоните можете да използвате символите “*”, “?”, “”, които бяха разгледани във втората тема от поредицата. С тяхна помощ можете да приложите инструкция, която действа по подразбиране в команда за превключване на езици като C, PHP.
Ето пример за използване на случай:
echo -n "[Универсален преглед] Посочете името на файла: "; прочетете случай на файл "$File" в *.jpg|*.gif|*.png) eog $File ;; *.pdf) evince $File ;; *.txt) по-малко $File ;; *.html) firefox $File ;; /dev/*) echo "Е, това са страшни файлове." ;; *) echo "Добре, добре - не е толкова универсално." echo "Не съм запознат с този тип файл. Не знам как да го прегледам." ;; esac
Друг пример за използване на конструкцията case:
echo "Грешка. На кого да изпратя съобщението?" echo "До шефа: b" echo "До колеги: c" echo "До никого: който и да е ключ" прочетете отговор случай $answer в b|B) mail –s "дневник на грешки" шеф< error.log;; c|C) mail –s "Help! error log" –c denis nick < error.log;; *) echo "error"; exit;; esac

Условно if изявление

Общият синтаксис на оператора if е:

ако списък1 тогава
списък2

фи

Квадратните скоби тук показват незадължителни конструкции. Логическата последователност на изпълнение на оператора на случая:
а) списък1 се изпълнява;
б) ако се изпълнява без грешки, се изпълнява list2. В противен случай се изпълнява list3 и ако завърши без грешки, се изпълнява list4. Ако list3 също върне код за грешка, list5 се изпълнява;
в) управлението се прехвърля към операторите, следващи конструкцията if.
Ето пример за използване на if:
if grep -q Bash file then echo "Файлът съдържа поне една Bash дума." фи
Когато if и then се появяват на един и същи ред, конструкциите if и then трябва да завършват с точка и запетая. Например:
$ако [$? –ne 0]; след това ехо „Грешка“; фи
Сега, като знаем, че е възможно да поставим if и then на един и същ ред, нека пренапишем горния пример:
if grep -q Bash файл; then echo "Файлът съдържа думата Bash." фи

Тестът и условните изрази

В горния пример се използва проверка на условие вместо анализиране на изходния код. Две форми на този тест са еквивалентни: вградената тестова команда и [условие]. Например, за да проверите съществуването на файл, трябва да напишете:
тест –д<файл>
или
[ -е<файл> ]
Ако се използват квадратни скоби, те трябва да бъдат разделени една от друга с интервал, тъй като "[" е името на командата, а "]" е задължителният последен аргумент за нейното завършване.
Ако условието е проверено успешно, се връща 0, а ако е невярно, се връща код на грешка 1.
Командата test може да провери дали даден низ е празен. Непразният низ води до изходен код 0. Празен, съответно – 1. Например:
$test $USER; ехо $?
Дизайнът "" е по-универсален в сравнение с "". Това е разширена версия на тестовата команда. В рамките на тази конструкция не се извършва допълнителна интерпретация на имена на файлове и аргументите не се разделят на отделни думи, но е разрешено заместване на параметри и команди. Например:
file=/etc/passwd if [[ -e $file ]] then echo „Намерен е файл с парола.“ фи
Конструкцията "" е за предпочитане пред "", тъй като ще помогне да се избегнат някои логически грешки. Например операторите "&&", "||", "<" и ">" вътре " " са напълно приемливи, докато вътре " " генерират съобщения за грешка.
Конструкцията "(()) ви позволява да оценявате аритметични изрази в нея. Ако резултатът от изчислението е нула, се връща код за грешка. Резултат от изчисление, различен от нула, създава код за връщане 0. Това е точно обратното на теста и инструкциите "", обсъдени по-горе.
Операторът if позволява вложени проверки:
if echo "Следващото *if* е вътре в първото *if*." if [[ $comparison = "integer" ]] then ((a< b)) else [[ $a < $b ]] fi then echo "$a меньше $b" fi

Условните изрази могат да се комбинират с помощта на обикновени логически операции:
! <выражение>– отказ;
<выражение1>–а<выражение2>– логическо И;
<выражение1>–о<выражение2>– логическо ИЛИ.

Елементарни условни изрази за файлове:
-e - файлът съществува;
-f - обикновен файл (не е директория или файл на устройство);
-s - ненулев размер на файла;
-d - файлът е директория;
-b - файлът е блоково устройство (флопи, cdrom и др.);
-c - файлът е символно устройство (клавиатура, модем, звукова карта и др.);
-p - файлът е канал;
-h - файлът е символна връзка;
-L - файлът е символна връзка;
-S - файлът е сокет;
-t - файлът е свързан с крайното устройство;
-r - файлът е четим (за потребителя, стартирал скрипта);
-w - файлът може да се записва (за потребителя, стартирал скрипта);
-x - файлът е достъпен за изпълнение (за потребителя, стартирал скрипта);
-g - (sgid) флаг за файл или директория е зададен;
-u - (suid) флаг за файла е зададен;
-k - флагът за лепкав бит е зададен;
-O - ​​вие сте собственик на файла;
-G - принадлежите към същата група като файла;
-N - файлът е променен от последното четене;
файл1 -nt файл2 – файл1 е по-нов от файл2;
file1 -ot file2 – файл1 е по-стар от файл2;
file1 -ef file2 – file1 и file2 са „твърди“ връзки към един и същи файл.

Елементарни условни изрази за сравняване на низове:
-z низ – дължината на низа е 0;
-n низ – дължината на низа не е равна на 0;
line1 == line2 – редовете съвпадат (подобно на “=”);
line1 !== line2 – редовете не съвпадат (подобно на „!=");
ред1< строка2 – строка1 предшествует строке2 в лексикографическом порядке;
ред1 > ред2 – ред1 следва ред2 в лексикографски ред.
Аритметичен условен израз има формата:
аргумент1 операция аргумент2, където аргументите са цели числа и са разрешени следните операции:
-eq – равен;
-ne – не е равно;
-lt – по-малко;
-le – по-малко или равно;
-gt – повече;
-ge – по-голямо или равно на;
< - меньше (внутри двойных круглых скобок);
<= - меньше или равно (внутри двойных круглых скобок);
> - по-голямо от (в двойни скоби);
>= - по-голямо или равно на (в двойни скоби).

Нека пренапишем предишния пример с помощта на израз if:
echo "Грешка. На кого да изпратя съобщението?" echo "Шеф: b" echo "Колеги: c" echo "Никой: никакъв ключ" прочете отговор if [ "$answer" == "b" –o "$answer" == "B" ]; след това mail –s "дневник на грешки" шеф< error.log; elif [ "$answer" == "c" –o "$answer" == "C" ]; then mail –s "Help! error log" –c denis nick < error.log; else echo "error"; exit; fi

В следващата тема ще продължа да разглеждам контролните структури на интерпретатора на команди bash. А именно, ще бъдат разгледани операторите за цикъл. А сега чакам коментари и критики :).

UPD: Благодаря на потребителя

Условието if-else се използва в BASH скриптовеЧесто. Самото състояние има малко странен вид [[ условие ]]. Обърнете внимание на вдлъбнатините. Без тях състоянието няма да работи. Ето списък с логически оператори за условието [[ ? ]]:

Списък с логически оператори, които
използва се за конструкция if-then-else-fi

#!/bin/bash if [[ $1 > 2 ]] then # if [[ ? ]] echo $1" е по-голямо от 2" else # ако не съвпада echo $1" е по-малко от 2 или 2" fi

Някои от вас може да сметнат оператора за равенство -eq за странен. Опитайте да използвате познати оператори >

Да приемем, че имате скрипт и трябва да потвърдите потребителя. Ако потребителят не е root, скриптът ще спре.

#!/bin/bash if [ "$(whoami)" != "root" ]; then echo "Нямате разрешение да стартирате $0." изход 1; фи

Често трябва да проверите променлива, за да видите дали има стойност. Ако няма нищо в променливата, тогава можете да спрете скрипта.

#!/bin/bash if [ -n "$num" ]; тогава "променливата има нещо и можете да започнете друг процес" else echo "празна променлива, спрете скрипта" изход 0; фи

Ако променливата е празна, тогава тя може да бъде попълнена.

#!/bin/bash if [ -z "$num" ]; then echo "променливата е празна" num=1 else echo "num="$num fi

На празна променлива може да се присвои стойност по подразбиране. Този запис е по-кратък от предишния пример.

#!/bin/bash # Напишете DEFAULT, ако няма аргументи от командния ред [ -z "$arg1" ] && arg1=DEFAULT echo $arg1

В Bash shell скриптове можем да извършваме сравнения на числа. За да извършите операция за сравнение на числа в Bash, трябва да използвате състоянието „test“ в рамките на if или цикъл. В тази публикация ще ви кажем как да сравнявате числа в bash.

Оператори за Bash сравнение на числа

операторкакво прави тойпример
-еквсравнява числа в bash за равенство, връща 0, ако е равноако [ $a -eq $b ] тогава
-geсравняване на числа в bash, ако са по-големи или равни. Резултатът връща 0, ако е по-голям или равен наif [ $a -ge $b ] тогава
-gtсравнява числата в bash, ако са по-големи.ако [ $a -gt $b ] тогава
-leСравнява числата в bash, ако са по-малки или равни.if [ $a -le $b ] тогава
- ltсравнява числа в bash, ако е по-малко.ако [ $a -lt $b ] тогава
-несравнява числата в bash, ако не са равни или не.if [ $a -ne $b ] тогава

Подробни примери за оператори за сравнение на числа в Bash:

1. оператор-екв

Този оператор сравнява числата, проверява дали стойността е равна или не. Ако е равно, тогава се връща 0.

# cat test.sh #!/bin/bash echo "въведете стойността на променливата" read a echo "въведете стойността на променливата" read b if [ $a -eq $b ] then echo "Върната стойност:: $ ?" echo "a и b са равни" else echo "Върната стойност:: $?" echo "a и b не са равни" fi #

Екзекуция:

# sh test.sh въведете стойността на променлива 2 въведете стойността на променлива 3 Върната стойност:: 1 a и b не са равни # sh test.sh въведете стойността на променлива 2 въведете стойността на променлива 2 Върната стойност:: 0 a и b са равни #

В горния пример взехме числата 2 и 3 за първи път и системата върна стойност 1, но когато взехме същите стойности за a и b, променливата връща стойност нула.

2. оператор-ge

Този оператор сравнява числата и проверява дали стойностите са по-големи или равни на. Ако стойността е по-голяма или равна на, тогава върнатата стойност е 0.

# cat test1.sh #!/bin/bash #compare програма за -ge echo "въведете стойността на променливата" read a echo "въведете стойността за променливата b" прочетете b if [ $a -ge $b ] тогава echo "върната стойност: : $?" echo "a е по-голямо или равно на b" else echo "върната стойност:: $?" echo "a не е по-голямо или равно на b" fi #

3. оператор -gt

Този оператор за сравнение на числа ще тества числото да е по-голямо. Ако стойността е по-голяма, връща 0.

# cat test2.sh #!/bin/bash #сравнителна програма за -gt b=100 echo "въведете стойност, по-голяма от 100" прочетете a if [ $a -gt $b ] then echo "Много добро" else echo "Не много добър " fi

4. оператор-le

Този оператор за сравнение на числа ще тества стойности за по-малко или равно на. Ако е по-малко или равно на, тогава върнатата стойност е 0.

#сравнете програма за -le b=5 echo "въведете стойност, по-малка или равна на 5" прочетете a if [ $a -le $b ] тогава echo "всички са правилни" else echo "неправилно" fi #

5. оператор- lt

Този оператор за сравнение на числа ще тества стойности за по-малко от. Ако числото е по-малко, тогава върнатата стойност е 0.

Сравняването на низове в Bash не създава проблеми, докато не се опитате да сравните два низа по начин, който не е чувствителен към главни и малки букви. Ще дам няколко варианта за решаване на проблема, който използвам сам. Особеността на тези решения е, че те използват само вградените възможности на Bash shell.

Като начало ще създам две променливи, str1 и str2, съдържащи низовете за сравнение. Това са тези, които ще бъдат използвани в следващите примери на код.

#!/bin/bash str1 = "Низ за сравнение" str2 = "низ за сравнение"

Първата версия на сравнение на низове без значение за малки и големи букви, която искам да предложа, използва управление на опциите на обвивката с помощта на вградената команда shopt.

shopt -s nocasematch [[ $str1 == $str2 ]] && echo "съвпадение" || echo "не съвпада" shopt -u nocasematch

Следващата версия на сравнение на низове без значение за малки и големи букви се основава на принципа на независимо преобразуване на низове в общ регистър. Този вариант на код работи на Bash 4 и по-нови версии. Използването му на по-ранна версия на Bash ще доведе до грешка.

Така че, за да сравните низове, преобразувани в малки букви, можете да използвате следната опция за код.

[[ " $( str1 , ) " == " $( str2 , ) " ]] && ехо "съвпадение" || ехо "не съвпада"

Ако искате да конвертирате сравняваните низове в главни букви, можете да използвате следния код.

[[ " $( str1 ^^ ) " == " $( str2 ^^ ) " ]] && ехо "съвпадение" || ехо "не съвпада"

Като алтернатива, конвертирането на низове в единичен регистър може да се извърши по време на деклариране на променливи. За да направите това, използвайте вградената команда declare в обвивката.

За да декларирате променлива, съдържаща текст с малки букви, използвайте следния код.

#!/bin/bash declare -l str = "Camel Case String"

В резултат на изпълнението на този код, променливата str ще съдържа низ с малки букви, въпреки факта, че присвоеният низ е написан с главни букви. Можете да промените регистъра на буквите на низ, който вече е зададен в променлива, както следва.

#!/bin/bash str = "Camel Case String" declare -l str str = $str echo $str

За да преобразувате низ в главни букви, в примера с код по-горе, трябва да промените извикването на командата declare, като използвате ключа -u вместо ключа -l.

Сега сравнението на низове без значение за малки и главни букви с помощта на командата declare може да се извърши по следния начин.

declare -l str1_l = $str1 declare -l str2_l = $str2 [[ $str1_l == $str2_l ]] && echo "match" || ехо "не съвпада"

Всяка от дискутираните опции за сравнение на низове, които не са чувствителни към регистър, може да се използва при писане на Bash скриптове. Следователно, ако използвате Bash версия 4 или по-нова, можете да изберете този, който ви харесва най-много. Ако версията на Bash е по-ниска от 4, тогава трябва да използвате първата опция, като посочите опцията nocasematch с помощта на вградената команда на shopt shell.

Когато пишат скриптове в Bash, не само опитни програмисти, но и нови в Bash shell се сблъскват с работа с низове. Това най-често се налага при четене на команди, въведени от потребителя като аргументи на изпълним скрипт, както и при обработка на текстови файлове. И една от необходимите техники в този случай е сравнението на низове.

Тази статия ще разгледа сравняването на Bash низове, както и някои нюанси при използването на операции за сравнение и разрешаването на често срещани грешки.

Тези операции ви позволяват да определите дали сравняваните низове са еднакви:

  • = - равно, например if [ "$x" = "$y" ]
  • == - синоним на оператора "=", например if [ "$x" == "$y" ]
  • != - не е равно, напр if [ "$x" != "$y" ]

#!/bin/bash
testuser=антон
ако [ $USER = $testuser ]
тогава
echo "Добре дошъл $testuser"
фи

Резултатът от скрипта:

При тестване за равенство с помощта на командата тест(синоним на квадратни скоби) всички препинателни знаци и разлики в случай на букви от сравняваните низове се вземат предвид.

Някои характеристики на сравнението на низове с шаблони:

# връща true, ако низът, съдържащ се в $x, започва със знака "y"
[[ $x == y* ]]
# връща true, ако низът от $x е равен на точно два знака "y*"
[[ $x == "y*" ]]
# връща true, ако $x съдържа името на файл, съдържащ се в текущата директория, който започва с "y"
[$x == y*]
# връща true, ако низ $x е равен на два знака "y*".
[ "$x" == "y*" ]

Например, проверка на bash низ, за ​​да видите дали започва със знака y:

#!/bin/bash
x=yandex
[[ $x == y* ]]
ехо $?

Резултат от изпълнението на кода:

Скриптът изведе 0 (нула), защото поискахме да се покаже кодът за грешка на последната изпълнена инструкция. А код 0 означава, че скриптът е изпълнен без грешки. И наистина – променлива $xсъдържа низа yandex, който започва със знака "y". В противен случай може да се изпише "1". Това е доста удобен начин за отстраняване на грешки в скриптове.

Сравняване на низове по азбучен ред в Bash

Задачата става по-трудна, когато се опитвате да определите дали даден ред е предшественик на друг ред във възходяща последователност за сортиране. Хората, които пишат bash скриптове, често се сблъскват с два проблема по отношение на операторите по-голямо от и по-малко от спрямо сравненията на низове на Linux, които имат доста прости решения:

Първо, знаците по-голямо от и по-малко от трябва да бъдат екранирани, като пред тях поставите обратна наклонена черта (\), защото в противен случай обвивката ще ги третира като знаци за пренасочване, а низовете като имена на файлове. Това е един от онези случаи, в които е доста трудно да се открие грешката.

#!/bin/bash
# неправилно използване на оператори за сравнение на низове
val1=бейзбол
val2=хокей
ако [ $val1 > $val2 ]
тогава

друго

фи

Какво получавате, ако сравните bash низовете:

Както можете да видите, само символът „по-голямо от“ в непосредствената си форма доведе до неправилни резултати, въпреки че не бяха генерирани грешки. В този случай този знак е причинил изходния поток да бъде пренасочен, така че не са открити синтактични грешки и в резултат на това файл, наречен хокей:

За да разрешите тази грешка, трябва да избегнете знака ">", така че условието да изглежда така:

...
ако [ $val1 \> $val2 ]
...

Тогава резултатът от програмата ще бъде правилен:

Второ, низовете, подредени с помощта на операторите по-голямо от и по-малко от, са подредени по различен начин, отколкото при командата вид. Тук проблемите са по-трудни за разпознаване и може изобщо да не ги срещнете, ако сравнението не вземе предвид регистъра на буквите. В отбор видИ тестсравнението се извършва по различни начини:

#!/bin/bash
val1=Тестване
val2=тестване
ако [ $val1 \> $val2 ]
тогава
echo "$val1 е по-голямо от $val2"
друго
echo "$val1 е по-малко от $val2"
фи

Резултат от кода:

В отбор тестредовете с главни букви първо ще предхождат редовете с малки букви. Но ако запишете същите данни във файл, към който след това приложите командата вид, тогава редовете с малки букви ще бъдат първи:

Разликата между работата им е, че в тестЗа да се определи редът на сортиране, подредбата на знаците в ASCII таблицата се взема като основа. IN видИзползва се редът на сортиране, определен за настройките за локал.

Проверка на низ за празна стойност

Сравнение с помощта на оператори -zИ използвани за определяне дали дадена променлива съдържа съдържание. По този начин можете да намерите bash празни редове. Пример:

#!/bin/bash
val1=тестване
val2=""
# проверява дали низът е празен
ако [ -n $val1 ]
тогава
echo "Низът "$val1" не е празен"
друго
echo "Низът "$val1" е празен"
фи
# проверява дали низът е празен
ако [ -z $val2 ]
тогава
echo "Низът "$val2" е празен"
друго
echo "Низът "$val2" не е празен"
фи
ако [ -z $val3 ]
тогава
echo "Низът "$val3" е празен"
друго
echo "Низът "$val3" не е празен"
фи

Резултат от кода:

Този пример създава две низови променливи - val1И val2. Операция определя дали дадена променлива има val1ненулева дължина и -zчекове val2И val3до нула. Трябва да се отбележи, че последният не е дефиниран до момента на сравнението, но интерпретаторът смята, че дължината му все още е равна на нула. Този нюанс трябва да се вземе предвид при различни проверки на скриптове. И ако не сте сигурни каква стойност се съдържа в променливата и дали изобщо е зададена, струва си да я проверите с помощта на оператора или -zи едва след това да го използвате по предназначение.

Струва си да се обърне внимание на функцията . Ако му бъде подадена недекларирана или празна променлива за тестване, тя ще върне true, а не false. За такива случаи трябва да затворите тествания низ (променлива) в двойни кавички, така че да изглежда така:

...
if [ -n "$val1" ]
...

заключения

Има определени нюанси в представените Bash операции за сравнение на низове, които си струва да се разберат, за да се предотвратят грешки в скрипта. Но на практика има много такива ситуации, така че е невъзможно да запомните всичко (да не говорим за описание).

Дял