使用myclass :: operator&lt;(myclass&amp; other)</myclass *>对std :: list <myclass *>进行排序

时间:2011-06-19 18:00:13

标签: c++ std

我有一个std::list<myclass*>,在我的班级中我定义了myclass::operator<(myclass &other)

我使用std::list.sort()函数,但它不会更改该列表中的任何内容。也许只是对指针进行排序?

如何对该列表中的实际项目进行排序?

5 个答案:

答案 0 :(得分:13)

您正在排序指针值,而不是myclass值。您必须编写自己的谓词,通过取消引用来比较指针:

template <typename T> bool PComp(const T * const & a, const T * const & b)
{
   return *a < *b;
}

std::vector<Foo*> myvec;
std::list<Foo*> mylist;
std::sort(myvec.begin(), myvec.end(), PComp<Foo>);
mylist.sort(PComp<Foo>);

顺便说一下,我认为您无法使用std::list std::sort<algorithm>进行排序,因为它不是随机访问。正如MerickOWA所说,使用成员函数sort。 (但这通常比排序随机访问容器效率低。)或者,您可以立即将对象存储在排序容器中,如std::set<Foo*, PPred>,其中PPred是谓词的仿函数版本:

struct PPred {
  template <typename T> inline bool operator()(const T * a, const T * b) const
  { return *a < *b; }
};

答案 1 :(得分:3)

有几个答案建议使用一个明确采用两个指针的谓词;这将适用于你有一个原始指针容器的当前情况,但它不适用于任何其他可解除引用的类型,如智能指针或迭代器。

为什么不去更一般的路线并匹配任何类型?

struct indirect_compare
{
    template <typename T>
    bool operator()(const T& lhs, const T& rhs) const 
    {
        return *lhs < *rhs;
    }
}

虽然T*不需要const引用,但复制相对昂贵的智能指针类型(例如std::shared_ptr)或无法复制(例如std::unique_ptr)是必要的。

或者,您可以考虑使用Boost的indirect_iterator之类的东西,它将间接移动到迭代器中,并且可以使代码更清晰。

答案 2 :(得分:2)

它将指针排序为std :: sort(Container)使用运算符&lt;定义T.这里T是myclass *,然后使用指针比较对它进行排序。

你可以将一个自定义的比较器函子传递给std :: sort,所以一个需要两个myclass *并返回正确的比较:

template<class T>
struct ptr_comparison
{
   bool operator()(T* a, T* b) { return *a < *b; } 
};

list<myclass*> mylist;

// later

mylist.sort(ptr_comparison<myclass>());

答案 3 :(得分:2)

假设列表中没有NULL指针,只需执行

bool ptrsorter( myclass *a, myclass *b ) {
  return *a < *b;
  }

mylist.sort( ptrsorter );

或者如果你有幸使用更新的编译器(使用C ++ 0x支持),你可以使用lambda表达式:

mylist.sort( []( myclass *a, myclass *b ) { return *a < *b } );

答案 4 :(得分:0)

我正在尝试PComp模板示例,由于其他类将使用PComp,因此我将std :: list所持有的类卡在了include文件中。但是,当我编译任务时,我得到了:

In member function ‘EcTVoid FdFtTSBFDFTableLoadAppl::IngestTableProducts(const string&, const EcTInt&)’:
/mms_builds/working/jkerich/MMS_SDF/sw/mms/dms/FdFtTSB/src/FdFtTSBFDFTableLoadAppl.C:782:53  error: no matching function for call to ‘std::list<FoFmVirtualTbl*>::sort(<unresolved overloaded function type>)’
   myIngestedTables.sort(sorter.PComp<FoFmVirtualTbl>); // sorted list
                                                     ^
/mms_builds/working/jkerich/MMS_SDF/sw/mms/dms/FdFtTSB/src/FdFtTSBFDFTableLoadAppl.C:782:53  note: candidates are:
In file included from /usr/include/c++/4.8.2/list:64:0,
                 from /mms_builds/working/jkerich/MMS_SDF/sw/mms/foscommon/common/FoCf/include/FoCfConfigSetup.h:11,
                 from /mms_builds/working/jkerich/MMS_SDF/sw/mms/foscommon/common/FoCf/include/FoCfTypes.h:156,
                 from /mms_builds/working/jkerich/MMS_SDF/sw/mms/dms/FdFtTSB/src/FdFtTSBFDFTableLoadAppl.C:18:
/usr/include/c++/4.8.2/bits/list.tcc:353:5: note: void std::list<_Tp, _Alloc>::sort() [with _Tp = FoFmVirtualTbl*; _Alloc = std::allocator<FoFmVirtualTbl*>]
     list<_Tp, _Alloc>::
     ^
/usr/include/c++/4.8.2/bits/list.tcc:353:5: note:   candidate expects 0 arguments, 1 provided
/usr/include/c++/4.8.2/bits/list.tcc:430:7: note: void std::list<_Tp, _Alloc>::sort(_StrictWeakOrdering) [with _StrictWeakOrdering = bool (FoFmVirtualTbl::*)(const FoFmVirtualTbl* const&, const FoFmVirtualTbl* const&); _Tp = FoFmVirtualTbl*; _Alloc = std::allocator<FoFmVirtualTbl*>]
       list<_Tp, _Alloc>::
       ^
/usr/include/c++/4.8.2/bits/list.tcc:430:7: note:   no known conversion for argument 1 from ‘<unresolved overloaded function type>’ to ‘bool (FoFmVirtualTbl::*)(const FoFmVirtualTbl* const&, const FoFmVirtualTbl* const&)’
In file included from /ecs/MMS_SDF/RogueWave/13.2/dbg/rw/config/rwconfig_tls.h:9:0,
                 from /ecs/MMS_SDF/RogueWave/13.2/dbg/rw/compiler.h:5,
                 from /ecs/MMS_SDF/RogueWave/13.2/dbg/rw/defs.h:46,
                 from /ecs/MMS_SDF/RogueWave/13.2/dbg/rw/cstring.h:33,
                 from /mms_builds/working/jkerich/MMS_SDF/sw/mms/foscommon/common/FoCf/include/FoCfTypes.h:11,
                 from /mms_builds/working/jkerich/MMS_SDF/sw/mms/dms/FdFtTSB/src/FdFtTSBFDFTableLoadAppl.C:18:

模板是这样的:

template <typename T> bool PComp(const T * const & a, const T * const & b)
{
    EcTInt status = a->compareTo(b);
    return ((status == -1) ? true : false);
}

我在FdFtTSBFDFTableLoadAppl.C中尝试的呼叫是:

myIngestedTables.sort(PComp<FoFmVirtualTbl>);   // sorted list

FoFmVirtualTbl sorter;
myIngestedTables.sort(sorter.PComp<FoFmVirtualTbl>);    // sorted lis

t

仅当在FdFtTSBFDFTableTableLoadAppl中声明模板时,它才能正常编译。那么,如果模板在其他某些类中,我将如何编译它呢?