c++ - 根据长度对集合 <string> 进行排序

标签 c++ stl lambda c++11 set

我的问题与 this 有关.

我想借助作为谓词的 lambda 表达式对 set 执行 sort() 操作。

我的代码是

#include <set>
#include <string>
#include <iostream>
#include <algorithm>
int main() {
  using namespace std;
  string s = "abc";
  set<string> results;
  do {
    for (int n = 1; n <= s.size(); ++n) {
      results.insert(s.substr(0, n));
    }
  } while (next_permutation(s.begin(), s.end()));

  sort (results.begin(),results.end());[](string a, string b)->bool{

              size_t alength = a.length();
              size_t blength = b.length();
              return (alength < blength);
  });
  for (set<string>::const_iterator x = results.begin(); x != results.end(); ++x) {
    cout << *x << '\n';
  }
  return 0;
}

但是错误的数量和类型是如此复杂,以至于我无法理解如何修复它们。谁能告诉我这段代码有什么问题。

最佳答案

编辑:注意Steve Townsend's solution实际上是您要搜索的那个,因为他将我在下面作为 C++03 代码编写的内容内联为 C++0x Lambda。

另一种解决方案是自定义 std::set 排序函数:

std::set 已经订购...

std::set 有自己的顺序,一旦构造完成,您就不应更改它。所以,下面的代码:

int main(int argc, char* argv[])
{
    std::set<std::string> aSet ;

    aSet.insert("aaaaa") ;
    aSet.insert("bbbbb") ;
    aSet.insert("ccccccc") ;
    aSet.insert("ddddddd") ;
    aSet.insert("e") ;
    aSet.insert("f") ;

    outputSet(aSet) ;

    return 0 ;
}

会输出如下结果:

 - aaaaa
 - bbbbb
 - ccccccc
 - ddddddd
 - e
 - f

...但是你可以自定义它的排序功能

现在,如果需要,您可以使用自己的比较功能自定义您的集合:

struct MyStringLengthCompare
{
    bool operator () (const std::string & p_lhs, const std::string & p_rhs)
    {
        const size_t lhsLength = p_lhs.length() ;
        const size_t rhsLength = p_rhs.length() ;

        if(lhsLength == rhsLength)
        {
            return (p_lhs < p_rhs) ; // when two strings have the same
                                     // length, defaults to the normal
                                     // string comparison
        }

        return (lhsLength < rhsLength) ; // compares with the length
    }
} ;

在这个比较仿函数中,我确实处理了“相同长度但不同内容表示不同字符串”的情况,因为我相信(也许是错误的)原始程序中的行为是错误的。要在原始程序中对行为进行编码,请从代码中删除 if block 。

现在,您构建集合:

int main(int argc, char* argv[])
{
    std::set<std::string, MyStringLengthCompare> aSet ;

    aSet.insert("aaaaa") ;
    aSet.insert("bbbbb") ;
    aSet.insert("ccccccc") ;
    aSet.insert("ddddddd") ;
    aSet.insert("e") ;
    aSet.insert("f") ;

    outputSet(aSet) ;

    return 0 ;
}

集合现在将使用仿函数 MyStringLengthCompare 对其项目进行排序,因此,此代码将输出:

 - e
 - f
 - aaaaa
 - bbbbb
 - ccccccc
 - ddddddd

但要注意顺序错误!

当您创建自己的排序函数时,它必须遵循以下规则:

return true if (lhs < rhs) is true, return false otherwise

如果出于某种原因您的排序功能不遵守它,您将得到一个坏掉的集合。

关于c++ - 根据长度对集合 <string> 进行排序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3844909/

相关文章:

c++ - 可以将currying与lambda函数一起使用吗?

python - 无法生成列表以显示列表中的任何匹配项

c++ - 如何访问可变 lambda 函数参数

c++ - BigInt 计算器吐出稍微错误的结果

c++ - 我怎样才能让一个对象知道它在哪个容器中?

c++ - `std::condition_variable::wait_for` 经常调用谓词

c++ - constrain_hash 中的 unordered_set EXC_BAD_ACCESS

c++ - 当 vector<int> 长度增加时,如何设置断点?

具有变量且参数​​数量未知的 C++ 函数

C++ std::function 语法问题