【问题标题】:How to check if a string is a substring of another?如何检查一个字符串是否是另一个字符串的子字符串?
【发布时间】:2013-05-12 06:05:08
【问题描述】:

我在 bash 中有以下字符串

str1="any string"
str2="any"

我想检查str2是否是str1的子串

我可以这样做:

c=`echo $str1 | grep $str2`
if [ $c != "" ]; then
    ...
fi

有没有更有效的方法?

【问题讨论】:

    标签: string shell


    【解决方案1】:

    您可以使用通配符扩展*

    str1="any string"
    str2="any"
    
    if [[ "$str1" == *"$str2"* ]]
    then
      echo "str2 found in str1"
    fi
    

    请注意,* 扩展不适用于单个 [ ]

    【讨论】:

    • 在这种情况下是否需要引号?我认为[[]] 相对于[] 的主要优势之一是不需要引用...
    • 是的。如果我在必要时错过了一个,它会咬人,但额外的不会伤害。这是我强迫自己一直做的事情之一 ;-)
    • 免责声明:那不是我。 ;-)
    • @DevSolar 呵呵..我知道不是你 :)
    【解决方案2】:

    您可以使用 bash 正则表达式匹配而不使用 grep

    if [[ $str1 =~ $str2 ]]; then
        ...
    fi
    

    请注意,正则表达式模式不需要任何周围的斜杠或引号。如果你想使用 glob 模式匹配,只需使用 == 而不是 =~ 作为运算符。

    一些例子可以在here找到。

    【讨论】:

      【解决方案3】:
      str1="any string"
      str2="any"
      

      老派(Bourne shell 风格):

      case "$str1" in *$str2*)
          echo found it
      esac
      

      新学校(如演讲者所示),但请注意右侧的字符串将被视为正则表达式:

      if [[ $str1 =~ $str2 ]] ; then
          echo found it
      fi
      

      但这也可以,即使您并不完全期待它:

      str2='.*[trs].*'
      if [[ $str1 =~ $str2 ]] ; then
          echo found it
      fi
      

      使用grep 很慢,因为它会产生一个单独的进程。

      【讨论】:

      • +1 表示case 表达式。但这不是老派,它是当前最先进的,因为它具有 POSIXly 便携性。顺便说一句,无需引用 $str1;在case 之后没有进行分词。
      • 我不会假设所有现有的 Unix 主机都符合 POSIX 标准。该 case 表达式与比 [[ ... =~ ... ]] 语法更老的系统兼容 - 几十年前。因此更便携。
      • 那么我们的协议非常激烈。 case 查找子字符串的方式适用于任何 Bourne shell,因此是最先进的,并且是无条件首选的。任何使用像 [[ ]] 这样的 bashism 的人都需要学习可移植性课程。 :-)
      【解决方案4】:
      if echo $str1 | grep -q $str2    #any command 
         then
         .....
      fi
      

      【讨论】:

        猜你喜欢
        • 2019-05-11
        • 1970-01-01
        • 2011-02-07
        • 1970-01-01
        • 2010-10-13
        • 2022-03-31
        相关资源
        最近更新 更多