නූලක උපස්ථරයක් Bash හි තිබේදැයි පරීක්ෂා කරන්නේ කෙසේද


2593

මට Bash හි නූලක් ඇත:

string="My string"

එහි වෙනත් නූලක් තිබේදැයි පරීක්ෂා කරන්නේ කෙසේද?

if [ $string ?? 'foo' ]; then
  echo "It's there!"
fi

??මගේ නොදන්නා ක්‍රියාකරු කොහෙද? මම echo භාවිතා grepකරනවාද?

if echo "$string" | grep 'foo'; then
  echo "It's there!"
fi

ඒක ටිකක් අවුල් සහගතයි.


4
හායි, හිස් නූල් බොරු නම්, ඔබ එය අවුල්සහගත ලෙස සලකන්නේ ඇයි? යෝජිත විසඳුම් නොතකා මට වැඩ කළ එකම ක්‍රමය එයයි.
ericson.cepeda

1
ඔබට exprමෙහි විධානය භාවිතා කළ හැකිය
xiaodong

4
පොසික් ෂෙල් සඳහා මෙන්න එකක්: stackoverflow.com/questions/2829613/…
sehe

Answers:


3694

ඔබ ද්විත්ව වරහන් භාවිතා කරන්නේ නම්, ඔබට සිද්ධි ප්‍රකාශයකින් පිටත මාකස්ගේ පිළිතුර (* ආදේශක කාඩ්පත්) භාවිතා කළ හැකිය :

string='My long string'
if [[ $string == *"My long"* ]]; then
  echo "It's there!"
fi

ඉඳිකටු නූල් වල අවකාශයන් ද්විත්ව මිල ගණන් අතර තැබිය *යුතු බවත්, ආදේශක කාඩ්පත් පිටත තිබිය යුතු බවත් සලකන්න. සරල සංසන්දනාත්මක ක්‍රියාකරුවෙකු භාවිතා කරන බව සලකන්න (එනම් ==) රීජෙක්ස් ක්‍රියාකරු නොවේ =~.


130
පරීක්ෂණයෙන්! = වෙත මාරු වීමෙන් ඔබට සංසන්දනය ආපසු හැරවිය හැකි බව සලකන්න. පිළිතුරට ස්තූතියි!
ක්වින් ටේලර්

63
On ජොනික්: ඔබට ෂෙබාං අතුරුදහන් විය හැකිය #!/bin/sh. #!/bin/bashඒ වෙනුවට උත්සාහ කරන්න .
වැඩිදුර දැනුම් දෙන තුරු විරාමය.

10
වරහන් සහ අන්තර්ගතය අතර ඉඩක් තබන්න.
පෝල් මිල

18
ඔබට [[]] තුළ විචල්‍යයන් උපුටා දැක්වීමට අවශ්‍ය නොවේ. මෙයද එසේම ක්‍රියාත්මක වනු ඇත: [[$ string == $ needle ]] && echo found
Orwellophile

14
R ඕර්වෙලොෆිල් ප්‍රවේශම් වන්න! ඔබට අතහැර දැමිය හැක්කේ පළමු තර්කයේ ද්විත්ව උපුටා දැක්වීම් පමණි [[. Ideone.com/ZSy1gZ
nyuszika7h

618

ඔබ රීජෙක්ස් ප්‍රවේශයට කැමති නම්:

string='My string';

if [[ $string =~ "My" ]]
then
   echo "It's there!"
fi

2
ඊග්‍රෙප් රීජෙක්ස් බාෂ් ස්ක්‍රිප්ට් එකක ප්‍රතිස්ථාපනය කිරීමට සිදු විය, මෙය මනාව ක්‍රියාත්මක විය!
blast_hardcheese

114
මෙම =~ක්රියාකරු දැනටමත් තරගය සඳහා මුළු string විමසන; මෙම .*'මෙතන ගේ බාහිර වේ. එසේම, උපුටා දැක්වීම් සාමාන්‍යයෙන් බැක්ස්ලෑෂ් වලට වඩා යෝග්‍ය වේ:[[ $string =~ "My s" ]]
බුසෝර්

16
@bukzor Quotes Bash 3.2+ හි වැඩ කිරීම නවතා දමා ඇත: tiswww.case.edu/php/chet/bash/FAQ E14) . විචල්‍යයකට (උපුටා දැක්වීම් භාවිතා කරමින්) පැවරීම වඩාත් සුදුසුය, පසුව සංසන්දනය කරන්න. මේ වගේ:re="My s"; if [[ $string =~ $re ]]
seanf

36
ටෙස්ට් එය කරන්නේ නම් නැති වැලක් අඩංගු: if [[ ! "abc" =~ "d" ]]සැබෑ ය.
ක්‍රිස්වෙබ් දේව්

1
පරීක්ෂණය සිදුවන අනුපිළිවෙල වැදගත් බව සලකන්න. පහත දැක්වෙන කේත රේඛාවේ ප්‍රතිදානය ඉදිරියට යනු ඇත 2.number=2; if [[ "1, 2, 4, 5" = *${number}* ]]; then echo forward $number; fi; if [[ *${number}* = "1, 2, 4, 5" ]]; then echo backwards $number; fi;
ඩව් වැන් ඩර් ලීස්ට්

362

If ප්‍රකාශයක් භාවිතා කිරීම ගැන මට විශ්වාස නැත, නමුත් ඔබට සිද්ධි ප්‍රකාශයක් සමඟ සමාන බලපෑමක් ලබා ගත හැකිය:

case "$string" in 
  *foo*)
    # Do stuff
    ;;
esac

79
පොසික් ෂෙල් වෙඩි සඳහා අතේ ගෙන යා හැකි බැවින් මෙය බොහෝ විට හොඳම විසඳුම වේ. (aka no bashisms)
technosaurus

26
echtechnosaurus bash tag පමණක් ඇති ප්‍රශ්නයක “bashism” විවේචනය කිරීම තරමක් අමුතු දෙයක් ලෙස මට පෙනේ :)
PP

41
@PP වඩා සීමිත විසඳුමකට වඩා විශ්වීය විසඳුමකට වැඩි කැමැත්තක් දැක්වීම එතරම් විවේචනයක් නොවේ. කරුණාකර සලකා බලන්න, වසර ගණනාවකට පසු, මිනිසුන් (මා වැනි) මෙම පිළිතුර සෙවීම සඳහා නතර වන අතර මුල් ප්‍රශ්නයට වඩා පුළුල් පරාසයකින් ප්‍රයෝජනවත් එකක් සොයා ගැනීමට සතුටු විය හැකිය. විවෘත මූලාශ්‍ර ලෝකයේ ඔවුන් පවසන පරිදි: "තේරීම හොඳයි!"
කාල් ස්මොට්‍රික්ස්

2
echtechnosaurus, FWIW [[ $string == *foo* ]]සමහර POSIX අනුකූල sh අනුවාද වලද ක්‍රියා කරයි (උදා: /usr/xpg4/bin/shSolaris 10 මත) සහ ksh (> = 88)
maxschlepzig

3
කාර්යබහුල පෙට්ටියේ අළු තරු ලකුණු නොකරයි [[... කේස් ස්විචය ක්‍රියාත්මක විය!
රේ ෆොස්

234

stringContain ප්‍රභේද (අනුකූල හෝ සිද්ධි ස්වාධීන)

මෙම සිරස් පිටාර ගැලීම් පිළිතුරු බොහෝ දුරට බාෂ් ගැන පවසන පරිදි , මම මෙම පෝස්ට් එකේ පතුලේම ස්වාධීන බාෂ් ශ්‍රිතයක් පළ කර ඇත්තෙමි ...

කෙසේ හෝ වේවා, මගේ ය

අනුකූල පිළිතුර

Bash- විශේෂිත විශේෂාංග භාවිතා කරමින් දැනටමත් පිළිතුරු රාශියක් ඇති හෙයින්, BusyBox වැනි දුප්පත් විශේෂාංග සහිත ෂෙල් වෙඩි යටතේ වැඩ කිරීමේ ක්‍රමයක් තිබේ :

[ -z "${string##*$reqsubstr*}" ]

ප්රායෝගිකව, මෙය ලබා දිය හැකිය:

string='echo "My string"'
for reqsubstr in 'o "M' 'alt' 'str';do
  if [ -z "${string##*$reqsubstr*}" ] ;then
      echo "String '$string' contain substring: '$reqsubstr'."
    else
      echo "String '$string' don't contain substring: '$reqsubstr'."
    fi
  done

මෙය Bash, Dash , KornShell ( ksh) සහ අළු (BusyBox) යටතේ පරීක්ෂා කරන ලද අතර ප්‍රති result ලය සැමවිටම:

String 'echo "My string"' contain substring: 'o "M'.
String 'echo "My string"' don't contain substring: 'alt'.
String 'echo "My string"' contain substring: 'str'.

එක් ශ්‍රිතයකට

@EeroAaltonen විසින් ඇසූ පරිදි මෙහි එකම නිරූපණයේ අනුවාදයක් ඇත, එකම ෂෙල් වෙඩි යටතේ පරීක්ෂා කර ඇත:

myfunc() {
    reqsubstr="$1"
    shift
    string="$@"
    if [ -z "${string##*$reqsubstr*}" ] ;then
        echo "String '$string' contain substring: '$reqsubstr'.";
      else
        echo "String '$string' don't contain substring: '$reqsubstr'."
    fi
}

ඉන්පසු:

$ myfunc 'o "M' 'echo "My String"'
String 'echo "My String"' contain substring 'o "M'.

$ myfunc 'alt' 'echo "My String"'
String 'echo "My String"' don't contain substring 'alt'.

දැනුම්දීම: ඔබට පැන යා යුතුය හෝ ද්විත්ව කොටු කිරීම් සහ / හෝ ද්විත්ව උපුටා දැක්වීම් කළ යුතුය:

$ myfunc 'o "M' echo "My String"
String 'echo My String' don't contain substring: 'o "M'.

$ myfunc 'o "M' echo \"My String\"
String 'echo "My String"' contain substring: 'o "M'.

සරල කාර්යය

මෙය කාර්යබහුල බොක්ස්, ඩෑෂ් සහ, ඇත්ත වශයෙන්ම බාෂ් යටතේ පරීක්ෂා කරන ලදී:

stringContain() { [ -z "${2##*$1*}" ]; }

එසේනම් දැන්:

$ if stringContain 'o "M3' 'echo "My String"';then echo yes;else echo no;fi
no
$ if stringContain 'o "M' 'echo "My String"';then echo yes;else echo no;fi
yes

JSjlver විසින් පෙන්වා දී ඇති පරිදි ඉදිරිපත් කරන ලද නූල හිස් විය හැකි නම්, ශ්‍රිතය මෙසේ වනු ඇත:

stringContain() { [ -z "${2##*$1*}" ] && [ -z "$1" -o -n "$2" ]; }

හෝ ඒඩ්‍රියන් ගුන්ටර්ගේ අදහස අනුව -oස්විචයන් වළක්වා ගැනීම :

stringContain() { [ -z "${2##*$1*}" ] && { [ -z "$1" ] || [ -n "$2" ];};}

අවසාන (සරල) ශ්‍රිතය:

පරීක්ෂණ ඉක්මන් කිරීමට හැකි වන පරිදි ප්‍රතිලෝම කිරීම:

stringContain() { [ -z "$1" ] || { [ -z "${2##*$1*}" ] && [ -n "$2" ];};}

හිස් නූල් සමඟ:

$ if stringContain '' ''; then echo yes; else echo no; fi
yes
$ if stringContain 'o "M' ''; then echo yes; else echo no; fi
no

නඩුව ස්වාධීනයි (Bash only!)

නඩුවකින් තොරව නූල් පරීක්ෂා කිරීම සඳහා, එක් එක් නූල් කුඩා අකුරට හරවන්න:

stringContain() {
    local _lc=${2,,}
    [ -z "$1" ] || { [ -z "${_lc##*${1,,}*}" ] && [ -n "$2" ] ;} ;}

චෙක් පත:

stringContain 'o "M3' 'echo "my string"' && echo yes || echo no
no
stringContain 'o "My' 'echo "my string"' && echo yes || echo no
yes
if stringContain '' ''; then echo yes; else echo no; fi
yes
if stringContain 'o "M' ''; then echo yes; else echo no; fi
no

1
මෙය ශ්‍රිතයකට තැබීමට ඔබට යම් ක්‍රමයක් සොයාගත හැකි නම් මෙය වඩාත් හොඳ වනු ඇත.
ඊරෝ ඇල්ටොනන්

2
EroEeroAaltonen මගේ (නව එකතු කළ) ශ්‍රිතය ඔබ සොයා ගන්නේ කෙසේද?
එෆ්. හවුරි

2
මම දන්නවා! සොයා ගන්න. -name "*" | xargs grep "myfunc" 2> / dev / null
බිත්තර

6
මෙය එතරම්ම අනුකූල බැවින් මෙය අපූරු ය. එක් දෝෂයක්, නමුත්: පිදුරු නූල් හිස් නම් එය ක්‍රියා නොකරයි. නිවැරදි අනුවාදය වනුයේ string_contains() { [ -z "${2##*$1*}" ] && [ -n "$2" -o -z "$1" ]; } අවසාන සිතුවිල්ලකි: හිස් නූලෙහි හිස් නූලක් තිබේද? ඉහත අනුවාදය ඔව් ( -o -z "$1"කොටස නිසා).
Sjlver

3
+1. ඉතා හොඳයි! මා සඳහා මම ඇණවුම වෙනස් කළෙමි string () {[-z "$ # 1 ## * $ 2 *}"] && [-z "$ 2" -o -n "$ 1"]; }; "කොහේද සොයන්න" "කුමක්ද සොයා ගන්න". කාර්යබහුල පෙට්ටියේ වැඩ කරන්න. ඉහත පිළිගත් පිළිතුර කාර්යබහුල කොටුවේ ක්‍රියා නොකරයි.
user3439968

151

ෂෙල් ස්ක්‍රිප්ටින් භාෂාවට වඩා අඩු සහ විධාන එකතුවක් බව ඔබ මතක තබා ගත යුතුය. සහජයෙන්ම ඔබ සිතන්නේ මෙම “භාෂාව” ඔබට ifa [හෝ a සමඟ අනුගමනය කළ යුතු බවයි [[. මේ දෙකම සාර්ථකත්වය හෝ අසාර්ථකත්වය පෙන්නුම් කරන පිටවීමේ තත්වයක් ලබා දෙන විධානයන් පමණි (අනෙක් සෑම විධානයක් මෙන්). එම හේතුව නිසා මම භාවිතා කරන්නේ grepමිස [විධානය නොවේ .

කරන්න:

if grep -q foo <<<"$string"; then
    echo "It's there"
fi

දැන් ඔබ සිතන්නේ ifඑය අනුගමනය කරන විධානයේ පිටවීමේ තත්ත්වය පරීක්ෂා කිරීමට (අර්ධ කොලන් සමඟ සම්පුර්ණයි), ඔබ පරීක්ෂා කරන නූලෙහි ප්‍රභවය නැවත සලකා නොබලන්නේ මන්ද?

## Instead of this
filetype="$(file -b "$1")"
if grep -q "tar archive" <<<"$filetype"; then
#...

## Simply do this
if file -b "$1" | grep -q "tar archive"; then
#...

මෙම -qඅපි පමණක් නැවත කේතය අවශ්ය ලෙස විකල්පය වර්ගයන් නොවේ, ප්රතිදාන දෙයක් grep. <<<කවචය ඊලඟ වචනය පුළුල් කර එය විධානයට ආදානය ලෙස භාවිතා කරයි, <<මෙහි ලේඛනයේ එක් පේළියේ අනුවාදය (මෙය සම්මත හෝ බාෂිවාදයක් දැයි මට විශ්වාස නැත).


7
ඒවා මෙහි නූල් ලෙස හැඳින්වේ (3.6.7) මම විශ්වාස කරන්නේ එය bashism බවයි
alex.pilon

10
කෙනෙකුට ක්‍රියාවලි ආදේශනය ද භාවිතා කළ හැකියif grep -q foo <(echo somefoothing); then
larsr

echoප්‍රවේශ කළ නොහැකි බව සලකන්න, ඔබ විචල්‍යයක් පසු කරන්නේ නම්, printf '%s' "$stringඒ වෙනුවට භාවිතා කරන්න.
nyuszika7h

5
මෙහි පිරිවැය ඉතා මිල අධිකය: grep -q foo <<<"$mystring"implie 1 දෙබලක කිරීම බාෂිස්වාදය වන අතර echo $mystring | grep -q fooදෙබලක 2 ක් යොදන්න (නලයට එකක් සහ දෙවනුව ධාවනය සඳහා /path/to/grep)
F. Hauri

1
String තර්ක රේඛාවේ echoබැක්ස්ලෑෂ් අනුක්‍රමයන් තිබේ නම් ධජ නොමැති බ un නෝ බ්‍රොනොස්කි හට තවමත් අනපේක්ෂිත අතේ ගෙන යා හැකි ගැටළු ඇති විය හැකිය. echo "nope\c"සමහර වේදිකාවල echo -e "nope"අනෙක් ඒවා මෙන් ක්‍රියා කිරීමට බලාපොරොත්තු වේ . printf '%s' "nope"එදිරිවprintf '%s\n' 'nope\c'
ත්‍රිත්ව

92

පිළිගත් පිළිතුර හොඳම ය, නමුත් එය කිරීමට එක් ක්‍රමයකට වඩා ඇති බැවින්, මෙහි තවත් විසඳුමක් තිබේ:

if [ "$string" != "${string/foo/}" ]; then
    echo "It's there!"
fi

${var/search/replace}වන $varපළමු උදාහරණයක් සමග searchප්රතිස්ථාපනය replace, එය සොයා නම් (එය වෙනස් නොවේ $var). ඔබ fooකිසිවක් වෙනුවට ආදේශ කිරීමට උත්සාහ කළහොත් සහ නූල වෙනස් වී තිබේ නම්, පැහැදිලිවම fooසොයාගත හැකි විය.


5
ඉහත ephemient හි විසඳුම:> `if [" $ string "! =" $ {string / foo /} "]; ඉන්පසු "එය තිබේ!" කාර්යබහුල බොක්ස් ෂෙල් අළු භාවිතා කරන විට fi` ප්‍රයෝජනවත් වේ . පිළිගත් විසඳුම කාර්යබහුල බොක්ස් සමඟ ක්‍රියා නොකරන්නේ සමහර බාෂ්ගේ නිත්‍ය ප්‍රකාශන ක්‍රියාත්මක නොවන බැවිනි.
TPoschel

1
වෙනසෙහි අසමානතාවය. හරිම අමුතු සිතුවිල්ලක්! මම එයට කැමතියි
nitinr708

1
ඔබේ
නූල

මම මෙම විසඳුම මා විසින්ම ලියා ඇත (මගේ පරිවර්ථකයා ඉහළම පිළිතුරු නොගන්නා නිසා) පසුව වඩා හොඳ එකක් සොයමින් ගිය නමුත් මෙය සොයා ගත්තේය!
බුවින්ජේ

57

එබැවින් ප්‍රශ්නයට ප්‍රයෝජනවත් විසඳුම් රාශියක් ඇත - නමුත් වේගවත්ම / අවම සම්පත් භාවිතා කරන්නේ කුමක්ද?

මෙම රාමුව භාවිතා කරමින් නැවත නැවත පරීක්ෂණ:

/usr/bin/time bash -c 'a=two;b=onetwothree; x=100000; while [ $x -gt 0 ]; do TEST ; x=$(($x-1)); done'

සෑම අවස්ථාවකදීම ටෙස්ට් වෙනුවට:

[[ $b =~ $a ]]           2.92 user 0.06 system 0:02.99 elapsed 99% CPU

[ "${b/$a//}" = "$b" ]   3.16 user 0.07 system 0:03.25 elapsed 99% CPU

[[ $b == *$a* ]]         1.85 user 0.04 system 0:01.90 elapsed 99% CPU

case $b in *$a):;;esac   1.80 user 0.02 system 0:01.83 elapsed 99% CPU

doContain $a $b          4.27 user 0.11 system 0:04.41 elapsed 99%CPU

(doContain එෆ්. හූරිගේ පිළිතුරෙහි විය)

ගිග්ල්ස් සඳහා:

echo $b|grep -q $a       12.68 user 30.86 system 3:42.40 elapsed 19% CPU !ouch!

එබැවින් සරල ආදේශන විකල්පය දීර් test පරීක්ෂණයකදී හෝ නඩුවකින් වේවා අනාවැකි කිව හැකිය. නඩුව අතේ ගෙන යා හැකි ය.

ග්‍රෙප් 100000 ක් පිටතට ගැනීම අනාවැකි කිව හැකි තරම් වේදනාකාරී ය! අවශ්‍යතාවයකින් තොරව බාහිර උපයෝගිතා භාවිතා කිරීම පිළිබඳ පැරණි රීතිය සත්‍ය වේ.


4
පිළිවෙලට මිණුම් ලකුණ. භාවිතා කිරීමට මට ඒත්තු ගැන්වීය [[ $b == *$a* ]].
පිස්සු භෞතික විද්‍යා

2
මම මෙය නිවැරදිව කියවන්නේ නම් case, කුඩාම සමස්ත කාල පරිභෝජනයෙන් ජය ගනී. ඔබට පසුව තරු ලකුණු නොමැත $b in *$a. දෝෂය නිවැරදි කිරීමට [[ $b == *$a* ]]වඩා මට තරමක් වේගවත් ප්‍රති results caseල ලැබෙනු ඇත, නමුත් එය වෙනත් සාධක මත ද රඳා පවතී.
ත්‍රිත්ව

1
ideone.com/5roEVt හි අමතර දෝෂ කිහිපයක් සමඟ මගේ අත්හදා බැලීම් කර ඇති අතර වෙනස් තත්වයක් සඳහා වන පරීක්ෂණ ( දිගු නූලෙහි ඇත්ත වශයෙන්ම නූල් නොමැති තැන). ප්‍රති Results ල බොහෝ දුරට සමාන ය; [[ $b == *$a* ]]ඉක්මන් වන අතර caseඑය ඉක්මන් වේ (හා ප්‍රසන්න POSIX- අනුකූල වේ).
ත්‍රිත්ව

28

මෙයද ක්‍රියාත්මක වේ:

if printf -- '%s' "$haystack" | egrep -q -- "$needle"
then
  printf "Found needle in haystack"
fi

Test ණාත්මක පරීක්ෂණය නම්:

if ! printf -- '%s' "$haystack" | egrep -q -- "$needle"
then
  echo "Did not find needle in haystack"
fi

මෙම විලාසිතාව තව ටිකක් සම්භාව්‍ය යැයි මම සිතමි.

මෙම --තර්කය පිරිසිදු POSIX මතිභ්රමයට, වැනි විකල්ප සමාන ආදාන නූල්, ආරක්ෂා කිරීම සඳහා භාවිතා වේ --abcහෝ -a.

සටහන: තද ලූපයක මෙම කේතය අභ්‍යන්තර බෑෂ් ෂෙල් විශේෂාංග භාවිතා කිරීමට වඩා මන්දගාමී වනු ඇත , මන්ද වෙනම ක්‍රියාවලි එකක් (හෝ දෙකක්) නිර්මාණය කර පයිප්ප හරහා සම්බන්ධ වේ.


5
... නමුත් OP කුමන බාෂ් අනුවාදයදැයි නොකියයි ; උදා: පැරණි බැෂ් (සූර්යාලෝකය වැනි) මෙම නව බෑෂ් අංග ඇතුළත් නොවිය හැකිය. (මම මේ නිශ්චිත ප්රශ්නයක් බවට (bash රටාව ගැලපෙන ක්රියාත්මක කර නැත) Solaris w / bash 2.0 මත ධාවනය තියෙනවා)
මයිකල්

2
echoකළ නොහැකි ය, ඔබ printf '%s' "$haystackඒ වෙනුවට භාවිතා කළ යුතුය .
nyuszika7h

2
නෑ, echoආරම්භ නොවී ගැලවීමකින් තොරව වචනාර්ථයෙන් පෙළ හැර වෙනත් කිසිවක් සඳහා සම්පූර්ණයෙන්ම වළකින්න -. එය ඔබට වැඩ කළ හැකි නමුත් එය අතේ ගෙන යා නොහැකි ය. විකල්පය සකසා echoතිබේද යන්න මත පදනම්ව, බාෂ්ගේ පවා වෙනස් ලෙස හැසිරෙනු xpg_echoඇත. PS: මගේ පෙර අදහස් දැක්වීමේ ද්විත්ව උපුටා දැක්වීම වසා දැමීමට මට අමතක විය.
nyuszika7h

1
මට විශ්වාස නෑ @kevinarpe, --ලැයිස්තු ගත කර නැත සඳහා POSIX පිරිවිතරprintf , එහෙත් ඔබ භාවිතා කළ යුත්තේ printf '%s' "$anything"නම් ගැටළු වළක්වා ගැනීමට, කෙසේ හෝ $anythingඅඩංගු %චරිතය.
nyuszika7h

1
inkevinarpe ඒ මත පදනම්ව, එය බොහෝ විට විය හැකිය.
nyuszika7h

21

Bash 4+ උදාහරණ. සටහන: උපුටා දැක්වීම් භාවිතා නොකිරීම වචනවල අවකාශයන් ආදිය අඩංගු වන විට ගැටළු ඇති කරයි.

මෙන්න උදාහරණ කිහිපයක් Bash 4+:

උදාහරණ 1, නූල් වලින් 'ඔව්' සඳහා පරීක්ෂා කරන්න (සිද්ධි සංවේදී නොවේ):

    if [[ "${str,,}" == *"yes"* ]] ;then

උදාහරණ 2, නූල් වලින් 'ඔව්' සඳහා පරීක්ෂා කරන්න (සිද්ධි සංවේදී නොවේ):

    if [[ "$(echo "$str" | tr '[:upper:]' '[:lower:]')" == *"yes"* ]] ;then

උදාහරණ 3, නූල් වලින් 'ඔව්' සඳහා පරීක්ෂා කරන්න (සිද්ධි සංවේදී):

     if [[ "${str}" == *"yes"* ]] ;then

උදාහරණ 4, නූල් වලින් 'ඔව්' සඳහා පරීක්ෂා කරන්න (සිද්ධි සංවේදී):

     if [[ "${str}" =~ "yes" ]] ;then

උදාහරණ 5, නිශ්චිත ගැලපීම (සිද්ධි සංවේදී):

     if [[ "${str}" == "yes" ]] ;then

උදාහරණ 6, නිශ්චිත ගැලපීම (සිද්ධි සංවේදී නොවේ):

     if [[ "${str,,}" == "yes" ]] ;then

උදාහරණ 7, හරියටම ගැලපීම:

     if [ "$a" = "$b" ] ;then

උදාහරණ 8, ආදේශක කාඩ් ගැලපීම .ext (සිද්ධි සංවේදී නොවේ):

     if echo "$a" | egrep -iq "\.(mp[3-4]|txt|css|jpg|png)" ; then

විනෝද වන්න.


17

කොහොමද මේ:

text="   <tag>bmnmn</tag>  "
if [[ "$text" =~ "<tag>" ]]; then
   echo "matched"
else
   echo "not matched"
fi

2
= ~ යනු regexp ගැලපීම සඳහා වන අතර එබැවින් OP හි අරමුණු සඳහා එය ඉතා බලවත්ය.

16

ලෙස පාවුල් සඳහන් ඔහුගේ කාර්ය සාධන සාපේක්ෂව:

if echo "abcdefg" | grep -q "bcdef"; then
    echo "String contains is true."
else
    echo "String contains is not true."
fi

මෙය මාකස් විසින් සපයන ලද පිළිතුරෙහි 'නඩුව "$ string' වැනි POSIX අනුකූල වේ , නමුත් සිද්ධි ප්‍රකාශ පිළිතුරට වඩා කියවීම තරමක් පහසුය. සිද්ධි ප්‍රකාශයක් භාවිතා කිරීමට වඩා මෙය මන්දගාමී වන බව සලකන්න. පාවුල් පෙන්වා දුන් පරිදි, එය ලූපයක් ලෙස භාවිතා නොකරන්න.


11

මෙම සිරස් පිටාර ගැලීමේ පිළිතුර අවකාශය හසුකර ගැනීමට සහ අක්ෂර ඉරීමට ඇති එකම පිළිතුර විය:

# For null cmd arguments checking   
to_check=' -t'
space_n_dash_chars=' -'
[[ $to_check == *"$space_n_dash_chars"* ]] && echo found

එය මෙම ප්‍රශ්නයටම පිළිතුරකි.
පීටර් මෝර්ටෙන්සන්

9
[[ $string == *foo* ]] && echo "It's there" || echo "Couldn't find"

echo "Couldn't findමෙම ගැලපෙන විධානයන් සඳහා පිටවීමේ තත්වයන් 0 ආපසු ලබා දීමට අවසානයේ ප්‍රකාශය හොඳ උපක්‍රමයක් බව මම එකතු කරමි .
nicodjimenez

@nicodjimenez ඔබට මෙම විසඳුම සමඟ පිටවීමේ තත්වය තවදුරටත් ඉලක්ක කළ නොහැක. තත්ව පණිවිඩ මගින් පිටවීමේ තත්වය ගිල දමනු ලැබේ ...
ජාහිඩ්

1
මා අදහස් කළේ එයයි ... ඔබ සතුව නොමැති || echo "Couldn't find"නම්, ගැලපීමක් නොමැති නම් ඔබ දෝෂ පිටවීමේ තත්වයක් ලබා දෙනු ඇත, උදාහරණයක් ලෙස ඔබ සීඅයිඅයි නල මාර්ගයක් ධාවනය කරන්නේ නම් ඔබට අවශ්‍ය නොවනු ඇත. දෝෂ රහිත පිටවීමේ තත්වයන්
nicodjimenez

9

එකකි:

[ $(expr $mystring : ".*${search}.*") -ne 0 ] && echo 'yes' ||  echo 'no'

2
exprසාමාන්‍යයෙන් ඔබට කළ යුතු ඕනෑම දෙයක් කළ හැකි ස්විස්-හමුදා-පිහිය උපයෝගීතාවයන්ගෙන් එකකි, ඔබ එය කළ යුතු ආකාරය හඳුනාගත් පසු, නමුත් එය ක්‍රියාත්මක කළ පසු, එය කරන්නේ ඇයි හෝ කෙසේද යන්න ඔබට කිසිදා මතක නැත, එබැවින් ඔබ නැවත කිසි විටෙකත් එය ස්පර්ශ නොකරන්න, එය කිසි විටෙකත් එය කරන දේ නතර නොකරනු ඇතැයි බලාපොරොත්තු වන්න.
මයිකල්

Lo ඇලෝයිස්මාඩාල් මම කිසි විටෙකත් අඩු ඡන්දය ප්‍රකාශ කළේ නැත. අවවාදයක්. අතේ ගෙන යා හැකි බව expr(උදා: පැරණි අනුවාදයන් අතර නොගැලපෙන හැසිරීම), tr (සෑම තැනකම නොගැලපේ) හෝ sed (සමහර විට ඉතා මන්දගාමී) භාවිතා කිරීම වලක්වන විට මම භාවිතා කරන්නේ දුර්ලභ අවස්ථාවන්හිදී ය. නමුත් පෞද්ගලික අත්දැකීම් වලින්, මෙම expr-වාදයන් නැවත කියවන සෑම අවස්ථාවකම , මට නැවත මිනිසා පිටුවට යා යුතුය. එබැවින්, සෑම භාවිතයක්ම exprඅදහස් දැක්විය යුතු යැයි මම අදහස් කරමි ...
මයිකල්

1
ඔබ සතුව තිබුණේ මුල් බෝර්න් කවචය පමණි. එයට පොදුවේ අවශ්‍ය වන සමහර අංග නොමැති බැවින් ඒවා ක්‍රියාත්මක කිරීම සඳහා මෙවලම් වැනි exprසහ testක්‍රියාත්මක කරන ලදි. මෙම දිනය හා වයස තුළ, සාමාන්‍යයෙන් වඩා හොඳ මෙවලම් තිබේ, ඒවායින් බොහොමයක් ඕනෑම නවීන කවචයකට සාදා ඇත. මම හිතන්නේ testතවමත් එහි රැඳී සිටින නමුත් කිසිවෙකු අතුරුදහන් වී ඇති බවක් නොපෙනේ expr.
ත්‍රිත්ව

6

මම කැමතියි sed.

substr="foo"
nonsub="$(echo "$string" | sed "s/$substr//")"
hassub=0 ; [ "$string" != "$nonsub" ] && hassub=1

සංස්කරණය කරන්න, තර්කනය:

  • නූල් වලින් උපස්ථරයක් ඉවත් කිරීමට sed භාවිතා කරන්න

  • නව නූල පැරණි නූලට වඩා වෙනස් නම්, උපස්ථරය පවතී


2
කරුණාකර යම් පැහැදිලි කිරීමක් එක් කරන්න. කේතය ලබා දීමට වඩා යටින් පවතින තර්කනය ලබා දීම වඩා වැදගත් වන්නේ එය OP හා අනෙකුත් පා readers
කයන්ට

5

grep -q මෙම කාර්යය සඳහා ප්‍රයෝජනවත් වේ.

භාවිතා කිරීම එකම awk:

string="unix-bash 2389"
character="@"
printf '%s' "$string" | awk -vc="$character" '{ if (gsub(c, "")) { print "Found" } else { print "Not Found" } }'

ප්‍රතිදානය:

සොයා ගත නොහැක

string="unix-bash 2389"
character="-"
printf '%s' "$string" | awk -vc="$character" '{ if (gsub(c, "")) { print "Found" } else { print "Not Found" } }'

ප්‍රතිදානය:

හමු විය

මුල් ප්‍රභවය: http://unstableme.blogspot.com/2008/06/bash-search-letter-in-string-awk.html


3
echoකළ නොහැකි ය, ඔබ printf '%s' "$string"ඒ වෙනුවට භාවිතා කළ යුතුය . මම පිළිතුර සංස්කරණය කරන්නේ පරිශීලකයා තවදුරටත් නොපවතින බැවිනි.
nyuszika7h

echoඅතේ ගෙන යා නොහැකි ආකාරයෙන් , y nyuszika7h?
starbeamrainbowlabs

5

මට මෙම ක්‍රියාකාරීත්වය නිතර නිතර අවශ්‍ය බව මට පෙනී ගියේය, එබැවින් මම මේ ආකාරයෙන් ගෙදර හැදූ ෂෙල් ශ්‍රිතයක් භාවිතා කරමි, .bashrcඑමඟින් මට අවශ්‍ය සෑම විටම නැවත භාවිතා කිරීමට ඉඩ සලසයි, පහසුවෙන් මතක තබා ගත හැකි නමක්:

function stringinstring()
{
    case "$2" in
       *"$1"*)
          return 0
       ;;
    esac
    return 1
}

නම් පරීක්ෂා කිරීමට $string1(කිව්වොත්, ඒබීසී ) අඩංගු වේ $string2(කිව්වොත්, 123abcABC ) මම පවත්වාගෙන යාම සඳහා අවශ්ය stringinstring "$string1" "$string2"උදාහරණයක් ලෙස, නැවත අගය කිරීම සඳහා සහ පරීක්ෂා

stringinstring "$str1" "$str2"  &&  echo YES  ||  echo NO

[["$ str" == $ substr ]] && ප්‍රතිරාවය ඔව් || echo NO
elyase

මට හොඳටම විශ්වාසයි xහැක් කිරීම අවශ්‍ය වන්නේ ඉතා පැරණි ෂෙල් වෙඩි සඳහා පමණක් බව .
nyuszika7h

5

මගේ .bash_profile ගොනුව සහ මම grep භාවිතා කළ ආකාරය:

PATH පරිසර විචල්‍යයට මගේ binනාමාවලි දෙක ඇතුළත් නම් , ඒවා එකතු නොකරන්න,

# .bash_profile
# Get the aliases and functions
if [ -f ~/.bashrc ]; then
    . ~/.bashrc
fi

U=~/.local.bin:~/bin

if ! echo "$PATH" | grep -q "home"; then
    export PATH=$PATH:${U}
fi

1
මෙය පිළිතුරක් ද?
codeforester

ඉහළට. grep, වඩා බලවත්, ලබා ගත හැකි වීමට වඩා වැඩි වූ විට, Bash එය කරන්නේ කෙසේදැයි ඉගෙන ගැනීමට කරදර වන්නේ ඇයි? රටා ලැයිස්තුවකට ගැලපීමෙන් එය තව ටිකක් දිගු කරන්න : grep -q -E 'pattern1|...|patternN'.
මොහොමඩ් බනා

4

මෙහි පිළිතුරු දී ඇති ප්‍රශ්නයේ දිගුව POSIX sh හි තවත් නූලක් තිබේදැයි ඔබ කියන්නේ කෙසේද? :

මෙම විසඳුම විශේෂ අක්ෂර සමඟ ක්‍රියා කරයි:

# contains(string, substring)
#
# Returns 0 if the specified string contains the specified substring,
# otherwise returns 1.
contains() {
    string="$1"
    substring="$2"

    if echo "$string" | $(type -p ggrep grep | head -1) -F -- "$substring" >/dev/null; then
        return 0    # $substring is in $string
    else
        return 1    # $substring is not in $string
    fi
}

contains "abcd" "e" || echo "abcd does not contain e"
contains "abcd" "ab" && echo "abcd contains ab"
contains "abcd" "bc" && echo "abcd contains bc"
contains "abcd" "cd" && echo "abcd contains cd"
contains "abcd" "abcd" && echo "abcd contains abcd"
contains "" "" && echo "empty string contains empty string"
contains "a" "" && echo "a contains empty string"
contains "" "a" || echo "empty string does not contain a"
contains "abcd efgh" "cd ef" && echo "abcd efgh contains cd ef"
contains "abcd efgh" " " && echo "abcd efgh contains a space"

contains "abcd [efg] hij" "[efg]" && echo "abcd [efg] hij contains [efg]"
contains "abcd [efg] hij" "[effg]" || echo "abcd [efg] hij does not contain [effg]"

contains "abcd *efg* hij" "*efg*" && echo "abcd *efg* hij contains *efg*"
contains "abcd *efg* hij" "d *efg* h" && echo "abcd *efg* hij contains d *efg* h"
contains "abcd *efg* hij" "*effg*" || echo "abcd *efg* hij does not contain *effg*"

පරීක්ෂණය contains "-n" "n"මෙහි ක්‍රියාත්මක නොවේ, මන්ද එය විකල්පයක් ලෙස echo -nගිල දමනු ඇත -n! ඒ සඳහා ජනප්‍රිය විසඳුමක් වන්නේ printf "%s\n" "$string"ඒ වෙනුවට භාවිතා කිරීමයි .
joeytwiddle

4

POSIX / BusyBox ප්‍රශ්නය නිවැරදි පිළිතුර (IMHO) ලබා නොදී වසා ඇති බැවින් , මම පිළිතුරක් මෙහි පළ කරමි.

හැකි කෙටිම පිළිතුර නම්:

[ ${_string_##*$_substring_*} ] || echo Substring found!

හෝ

[ "${_string_##*$_substring_*}" ] || echo 'Substring found!'

බව සටහන ද්විත්ව හැෂ් වේ අනිවාර්ය (සමහර කටු ash). [ stringvalue ]උපස්ථරය සොයාගත නොහැකි වූ විට ඉහත ඇගයීමට ලක් කෙරේ. එය කිසිදු දෝෂයක් ලබා නොදේ. උපස්ථරය සොයාගත් විට ප්‍රති result ලය හිස් වන අතර එය ඇගයීමට ලක් [ ]කරයි. නූල සම්පූර්ණයෙන්ම ආදේශ කර ඇති නිසා මෙය දෝෂ කේත 1 විසි කරයි (හේතුවෙන් *).

කෙටිම වඩාත් පොදු වාක්‍ය ඛණ්ඩය:

[ -z "${_string_##*$_substring_*}" ] && echo 'Substring found!'

හෝ

[ -n "${_string_##*$_substring_*}" ] || echo 'Substring found!'

තවත් එකක්:

[ "${_string_##$_substring_}" != "$_string_" ] && echo 'Substring found!'

හෝ

[ "${_string_##$_substring_}" = "$_string_" ] || echo 'Substring found!'

මෙම සටහන තනි සමාන ලකුණක්!


3

නිවැරදි වචන ගැලපීම:

string='My long string'
exactSearch='long'

if grep -E -q "\b${exactSearch}\b" <<<${string} >/dev/null 2>&1
  then
    echo "It's there"
  fi

3

Oobash උත්සාහ කරන්න.

එය Bash 4 සඳහා OO- විලාසිතාවේ සංගීත පුස්තකාලයකි. එයට ජර්මානු umlauts සඳහා සහය ඇත. එය Bash හි ලියා ඇත.

බොහෝ කාර්යයන් ලබා ගත හැකිය: -base64Decode, -base64Encode, -capitalize, -center, -charAt, -concat, -contains, -count, -endsWith, -equals, -equalsIgnoreCase, -reverse, -hashCode, -indexOf, -isAlnum, -isAlpha, -isAscii, -isDigit, -isEmpty, -isHexDigit, -isLowerCase, -isSpace, -isPrintable, -isUpperCase, -isVisible, -lastIndexOf, -length, -matches, -replaceAll, -replaceFirst, -startsWith, -substring, -swapCase, -toLowerCase, -toString, -toUpperCase, -trim, සහ -zfill.

අඩංගු උදාහරණය දෙස බලන්න :

[Desktop]$ String a testXccc
[Desktop]$ a.contains tX
true
[Desktop]$ a.contains XtX
false

oobash Sourceforge.net වෙතින් ලබා ගත හැකිය .


2

මම මෙම ශ්‍රිතය භාවිතා කරමි (එක් යැපීමක් ඇතුළත් කර නැති නමුත් පැහැදිලිව පෙනේ). එය පහත දැක්වෙන පරීක්ෂණ සමත් වේ. ශ්‍රිතය අගය> 0 ලබා දෙන්නේ නම්, එම නූල සොයා ගන්නා ලදි. ඒ වෙනුවට ඔබට පහසුවෙන් 1 හෝ 0 ආපසු ලබා දිය හැකිය.

function str_instr {
   # Return position of ```str``` within ```string```.
   # >>> str_instr "str" "string"
   # str: String to search for.
   # string: String to search.
   typeset str string x
   # Behavior here is not the same in bash vs ksh unless we escape special characters.
   str="$(str_escape_special_characters "${1}")"
   string="${2}"
   x="${string%%$str*}"
   if [[ "${x}" != "${string}" ]]; then
      echo "${#x} + 1" | bc -l
   else
      echo 0
   fi
}

function test_str_instr {
   str_instr "(" "'foo@host (dev,web)'" | assert_eq 11
   str_instr ")" "'foo@host (dev,web)'" | assert_eq 19
   str_instr "[" "'foo@host [dev,web]'" | assert_eq 11
   str_instr "]" "'foo@host [dev,web]'" | assert_eq 19
   str_instr "a" "abc" | assert_eq 1
   str_instr "z" "abc" | assert_eq 0
   str_instr "Eggs" "Green Eggs And Ham" | assert_eq 7
   str_instr "a" "" | assert_eq 0
   str_instr "" "" | assert_eq 0
   str_instr " " "Green Eggs" | assert_eq 6
   str_instr " " " Green "  | assert_eq 1
}

අත්හිටුවීම! දේ වන්නේ එම පරායත්ත?
පීටර් මෝර්ටෙන්සන්

"Str_escape_special_characters" ශ්‍රිතය. එය GitHub arcshell_str.sh ගොනුවේ ඇත. arcshell.io ඔබව එතැනට ගෙන එනු ඇත.
ඊතන් පෝස්ට්


0
msg="message"

function check {
    echo $msg | egrep [abc] 1> /dev/null

    if [ $? -ne 1 ];
    then 
        echo "found" 
    else 
        echo "not found" 
    fi
}

check

මෙය a හෝ b හෝ c හි කිසියම් සිදුවීමක් සොයා ගනී


0

සාමාන්‍ය ඉඳිකටු පිදුරු උදාහරණය විචල්යයන් සමඟ අනුගමනය කරයි

#!/bin/bash

needle="a_needle"
haystack="a_needle another_needle a_third_needle"
if [[ $haystack == *"$needle"* ]]; then
    echo "needle found"
else
    echo "needle NOT found"
fi
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.