首页 文章

C string ==和compare()之间的区别?

提问于
浏览
282

我刚看了一些关于使用的建议

std::string s = get_string();
std::string t = another_string();

if( !s.compare(t) ) 
{

代替

if( s == t )
{

我几乎总是使用最后一个,因为我已经习惯了它,它感觉自然,更具可读性 . 我甚至不知道有一个单独的比较功能 . 更确切地说,我认为==会调用compare() .

What are the differences? In which contexts should one way be favored to the other?

我只考虑我需要知道字符串是否与另一个字符串相同的情况 .

10 回答

  • 27

    这就是标准对 operator== 的看法

    21.4.8.2 operator ==

    template<class charT, class traits, class Allocator>
    bool operator==(const basic_string<charT,traits,Allocator>& lhs,
                    const basic_string<charT,traits,Allocator>& rhs) noexcept;
    

    返回:lhs.compare(rhs)== 0 .

    好像没有太大区别!

  • 0

    std::string::compare()返回 int

    如果 st 相等,则

    • 等于零,
      如果 s 小于 t ,则
    • 小于零,
      如果 s 大于 t ,则
    • 大于零 .

    如果您希望第一个代码段与第二个代码段相同,则应该实际读取:

    if (!s.compare(t)) {
        // 's' and 't' are equal.
    }
    

    等于运算符仅测试相等性(因此其名称)并返回 bool .

    要详细说明用例,如果您对两个字符串彼此之间的关系(更少或更多)感兴趣,那么_793126可能会很有用 . PlasmaHH合理地提到了树木,它也可以是一个字符串插入算法,旨在保持容器的排序,上述容器的二分法搜索算法,等等 .

    EDIT: 正如Steve Jessop在评论中指出的那样, compare() 对快速排序和二进制搜索算法最有用 . 仅使用std::less即可实现自然排序和二分法搜索 .

  • 3

    compare 具有用于比较子字符串的重载 . 如果你要比较整个字符串,你应该只使用 == 运算符(无论它是否调用 compare 都非常无关紧要) .

  • 1

    在内部,string :: operator ==()使用string :: compare() . 请参考:CPlusPlus - String::Operator==()

    我写了一个小应用程序来比较性能,显然如果你在调试环境中编译和运行你的代码,String :: compare()比string :: operator ==()略快 . 但是,如果在Release环境中编译和运行代码,两者都基本相同 .

    仅供参考,为了得出这样的结论,我进行了1,000,000次迭代 .

    为了在调试环境中证明为什么string :: compare更快,我去了程序集,这里是代码:

    DEBUG BUILD

    字符串::运算符==()

    if (str1 == str2)
    00D42A34  lea         eax,[str2]  
    00D42A37  push        eax  
    00D42A38  lea         ecx,[str1]  
    00D42A3B  push        ecx  
    00D42A3C  call        std::operator==<char,std::char_traits<char>,std::allocator<char> > (0D23EECh)  
    00D42A41  add         esp,8  
    00D42A44  movzx       edx,al  
    00D42A47  test        edx,edx  
    00D42A49  je          Algorithm::PerformanceTest::stringComparison_usingEqualOperator1+0C4h (0D42A54h)
    

    字符串::比较()

    if (str1.compare(str2) == 0)
    00D424D4  lea         eax,[str2]  
    00D424D7  push        eax  
    00D424D8  lea         ecx,[str1]  
    00D424DB  call        std::basic_string<char,std::char_traits<char>,std::allocator<char> >::compare (0D23582h)  
    00D424E0  test        eax,eax  
    00D424E2  jne         Algorithm::PerformanceTest::stringComparison_usingCompare1+0BDh (0D424EDh)
    

    你可以在string :: operator ==()中看到它必须执行额外的操作(添加esp,8和movzx edx,al)

    RELEASE BUILD

    字符串::运算符==()

    if (str1 == str2)
    008533F0  cmp         dword ptr [ebp-14h],10h  
    008533F4  lea         eax,[str2]  
    008533F7  push        dword ptr [ebp-18h]  
    008533FA  cmovae      eax,dword ptr [str2]  
    008533FE  push        eax  
    008533FF  push        dword ptr [ebp-30h]  
    00853402  push        ecx  
    00853403  lea         ecx,[str1]  
    00853406  call        std::basic_string<char,std::char_traits<char>,std::allocator<char> >::compare (0853B80h)
    

    字符串::比较()

    if (str1.compare(str2) == 0)
        00853830  cmp         dword ptr [ebp-14h],10h  
        00853834  lea         eax,[str2]  
        00853837  push        dword ptr [ebp-18h]  
        0085383A  cmovae      eax,dword ptr [str2]  
        0085383E  push        eax  
        0085383F  push        dword ptr [ebp-30h]  
        00853842  push        ecx  
    00853843  lea         ecx,[str1]  
    00853846  call        std::basic_string<char,std::char_traits<char>,std::allocator<char> >::compare (0853B80h)
    

    两个汇编代码都非常相似,因为编译器执行优化 .

    最后,在我看来,性能提升可以忽略不计,因此我真的会让开发人员决定哪一个是首选的,因为它们都能达到相同的结果(特别是当它是发布版本时) .

  • 108

    compare() 等同于strcmp() . == 是简单的等式检查 . compare() 因此返回一个 int== 是一个布尔值 .

  • 22

    如果字符串相等, compare() 将返回 false (嗯, 0 ) .

    所以不要轻易地换另一个 .

    使用哪个使代码更具可读性 .

  • 350

    如果您只想检查字符串相等性,请使用==运算符 . 确定两个字符串是否相等比查找排序更简单(这是compare()给出的),因此在您的情况下使用相等运算符可能会更好 .

    更长的答案:API提供了一种检查字符串相等性的方法和一种检查字符串排序的方法 . 你想要字符串相等,所以使用相等运算符(这样你的期望和库实现者的期望一致 . )如果性能很重要,那么你可能想测试两种方法并找到最快的 .

  • 5

    这里没有涉及的一件事是,它取决于我们将字符串与c字符串,c字符串与字符串或字符串与字符串进行比较 .

    一个主要的区别是,为了比较两个字符串,在进行比较之前检查大小相等,这使得==运算符比比较更快 .

    这是我在Debian 7上看到的比较

    // operator ==
      /**
       *  @brief  Test equivalence of two strings.
       *  @param __lhs  First string.
       *  @param __rhs  Second string.
       *  @return  True if @a __lhs.compare(@a __rhs) == 0.  False otherwise.
       */
      template<typename _CharT, typename _Traits, typename _Alloc>
        inline bool
        operator==(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
               const basic_string<_CharT, _Traits, _Alloc>& __rhs)
        { return __lhs.compare(__rhs) == 0; }
    
      template<typename _CharT>
        inline
        typename __gnu_cxx::__enable_if<__is_char<_CharT>::__value, bool>::__type
        operator==(const basic_string<_CharT>& __lhs,
               const basic_string<_CharT>& __rhs)
        { return (__lhs.size() == __rhs.size()
              && !std::char_traits<_CharT>::compare(__lhs.data(), __rhs.data(),
                                __lhs.size())); }
    
      /**
       *  @brief  Test equivalence of C string and string.
       *  @param __lhs  C string.
       *  @param __rhs  String.
       *  @return  True if @a __rhs.compare(@a __lhs) == 0.  False otherwise.
       */
      template<typename _CharT, typename _Traits, typename _Alloc>
        inline bool
        operator==(const _CharT* __lhs,
               const basic_string<_CharT, _Traits, _Alloc>& __rhs)
        { return __rhs.compare(__lhs) == 0; }
    
      /**
       *  @brief  Test equivalence of string and C string.
       *  @param __lhs  String.
       *  @param __rhs  C string.
       *  @return  True if @a __lhs.compare(@a __rhs) == 0.  False otherwise.
       */
      template<typename _CharT, typename _Traits, typename _Alloc>
        inline bool
        operator==(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
               const _CharT* __rhs)
        { return __lhs.compare(__rhs) == 0; }
    
  • 0

    在Visual Studio 2012调试器中,检查字符串时,只有以下方法正常工作:

    strcmp(somestring.c_str(),"")==0
    

    返回true .

    somestring.compare("")
    

    返回1,和

    somestring==""
    

    return:no运算符“==”匹配这些操作数 .

    somestring.c_str()==""
    

    return:发生了未指定的错误 .

  • 5

    假设考虑两个字符串s和t .
    给他们一些 Value .
    当您使用 (s==t) 比较它们时,它返回一个布尔值(true或false,1或0) .
    但是当你使用 s.compare(t) 进行比较时,表达式会返回一个值
    (i) 0 - 如果s和t相等
    (ii) <0 - 如果s中第一个不匹配字符的值小于t的值或者s的长度小于s的长度吨 .
    (iii) >0 - 如果t中第一个不匹配字符的值小于s的值或者t的长度小于s的长度 .

相关问题