如何基于std :: tm对容器进行排序?

时间:2011-08-17 19:38:08

标签: c++ sorting datetime containers

我需要根据std struct tm对象对自定义类进行排序。我想知道我是否正确接近这个并询问比较功能的建议。最初,我将每个std::tm成员转换为某个基数(如.NET Ticks中的DateTime),但我认为这可能过多。

我不 使用list,但我必须使用Container<MyClass*>。不过我更喜欢list。这是我的自定义类:

class MyClass
{
public:
  std::tm _datetime;
  static bool ComparePointers(MyClass*& lhs, MyClass*& rhs);
};

bool MyClass::ComparePointers(MyClass*& lhs, MyClass*& rhs)
{
  // ??
}

这是我的主要功能:

int main()
{
   std::list<MyClass*> classes;
   MyClass* class_1 = new MyClass();  classes.push_back(class_1);
   MyClass* class_2 = new MyClass();  classes.push_back(class_2);
   MyClass* class_3 = new MyClass();  classes.push_back(class_3);

   list.sort(MyClass::ComparePointers);
}

3 个答案:

答案 0 :(得分:3)

您可以使用mktimestd::tm值转换为可以比较的time_t

答案 1 :(得分:2)

最简单的解决方案是将std::tm实例转换为整数值,例如自纪元以来的秒数。对ComparePointers函数中的两个对象执行此操作,然后比较这些值。

另一个更复杂的方法是比较std::tm的每个成员,例如年,月,日,分钟等。

顺便说一句,比较功能被错误命名。您不是在比较指针,而是比较时间和日期值。

答案 2 :(得分:0)

如@ChristianAmmer所建议,您可以使用mktime()tm转换为time_t进行比较。但是自C++11起,您也可以使用lambda expression代替定义比较函数:

#include <list>
#include <ctime>
#include <memory>
#include <iostream>
using namespace std;

class MyClass {
public:
    // I added a constructor to initialize _datetime just for testing.
    MyClass() {
        time_t t = time(nullptr);
        _datetime = *localtime(&t);
        _datetime.tm_sec = rand() % 60;
    }
    tm _datetime;
};

int main() {
    list<unique_ptr<MyClass>> classes;
    classes.push_back(unique_ptr<MyClass>(new MyClass));
    classes.push_back(unique_ptr<MyClass>(new MyClass));
    classes.push_back(unique_ptr<MyClass>(new MyClass));
    // C++14: classes.push_back(make_unique<MyClass>());

    classes.sort([](unique_ptr<MyClass>& a, unique_ptr<MyClass>& b) {
        return mktime(&a->_datetime) < mktime(&b->_datetime);
    });

    for (auto const &mc : classes)
        cout << asctime(&mc->_datetime);

    return 0;
}

输出:

  

2018年7月9日星期一11:24:34
  2018年7月9日星期一11:24:41
  2018年7月9日星期一11:24:47

注1:作为C ++ 11练习,我用unique_ptr<>的实例替换了原始指针。这样,您的示例代码将不再在程序退出时泄漏MyClass指针。

注2:函数mktime()可能会修改传递的tm结构。如果这引起任何问题,那么您可以首先在lambda表达式中复制tm结构。

注3:我仅将功能localtime()asctime()用于演示。最近的Microsoft编译器认为它们不安全,建议改用localtime_s()asctime_s()

Code on Ideone