STL multiset 设置插入顺序 C++
STL multiset setting insertion order C++
我正在使用 multiset 来存储有序对象的集合,我正在使用 operator< 来建立顺序标准,但是我做错了,因为当我遍历 multiset 打印跟踪时,我可以看到他们根本没有订购....我真的被这个问题所困扰...
我尝试在这里简化我的代码:
class CellSearch
{
public:
bool operator<(const CellSearch & C) const;
int getF() const { return _G + _H; }
private:
int _G;
int _H;
}
...
bool CellSearch::operator< (const CellSearch& C) const
{
return (this->getF() < C.getF());
}
我声明多重集的方式是:
std::multiset<CellSearch*> myOpenList;
然后我以这种方式插入一个新元素:
....
CellSearch *actualSearch = new CellSearch(start);
addOpenList(actualSearch, myOpenList);
函数如下:
void Grid::addOpenList(CellSearch* actual, std::multiset<CellSearch*>& openList)
{
openList.insert(actual);
}
我是第一次使用 multiset...实际上是我第一个不是向量的容器 :) 你能看出这里有什么问题吗?
我试着总结了代码,希望不要太多...
您的多重集正在存储指向对象的指针。因此,为了比较,它比较 指针 ,而不是对象本身。
要使其以当前形式工作,您需要将 对象 本身放入多重集。另一种选择是提供一个自定义比较器来设置,它知道取消引用指针并比较实际对象 - 但在这种情况下这是次等的,因为我根本没有看到任何存储指针的理由。
最好将 operator <
作为自由函数而不是 class 成员来实现。
如果您打算在容器中使用指针,那么您应该这样做:
template<class KEY>
struct pointer_compare {
bool operator()(const KEY* lhs, const KEY* rhs) const {
return *lhs < *rhs;
}
}
std::multiset<Search*, pointer_compare<Search>> myOpenList
问题是您不是在处理 CellSearch
对象的集合,而是在处理指向它们的指针,这使得比较器可以处理指针。
这是您可以重复用于其他指针比较的通用解决方案:
template<class T>
struct PointerComparator {
bool operator()(const T *a, const T *b) const {
return *a < *b;
}
};
std::multiset<CellSearch*, PointerComparator<CellSearch> > myOpenList;
这样您仍然可以为 CellSearch
定义 operator <
。
你可以像这样定义一个无单元仿函数:
class cmpCell
{
bool operator()(CellSearch* a, CellSearch* b)
{
return *a < *b;
}
};
然后在声明多重集时使用它:
std::multiset<CellSearch*, cmpCell> myOpenList;
我正在使用 multiset 来存储有序对象的集合,我正在使用 operator< 来建立顺序标准,但是我做错了,因为当我遍历 multiset 打印跟踪时,我可以看到他们根本没有订购....我真的被这个问题所困扰...
我尝试在这里简化我的代码:
class CellSearch
{
public:
bool operator<(const CellSearch & C) const;
int getF() const { return _G + _H; }
private:
int _G;
int _H;
}
...
bool CellSearch::operator< (const CellSearch& C) const
{
return (this->getF() < C.getF());
}
我声明多重集的方式是:
std::multiset<CellSearch*> myOpenList;
然后我以这种方式插入一个新元素:
....
CellSearch *actualSearch = new CellSearch(start);
addOpenList(actualSearch, myOpenList);
函数如下:
void Grid::addOpenList(CellSearch* actual, std::multiset<CellSearch*>& openList)
{
openList.insert(actual);
}
我是第一次使用 multiset...实际上是我第一个不是向量的容器 :) 你能看出这里有什么问题吗?
我试着总结了代码,希望不要太多...
您的多重集正在存储指向对象的指针。因此,为了比较,它比较 指针 ,而不是对象本身。
要使其以当前形式工作,您需要将 对象 本身放入多重集。另一种选择是提供一个自定义比较器来设置,它知道取消引用指针并比较实际对象 - 但在这种情况下这是次等的,因为我根本没有看到任何存储指针的理由。
最好将 operator <
作为自由函数而不是 class 成员来实现。
如果您打算在容器中使用指针,那么您应该这样做:
template<class KEY>
struct pointer_compare {
bool operator()(const KEY* lhs, const KEY* rhs) const {
return *lhs < *rhs;
}
}
std::multiset<Search*, pointer_compare<Search>> myOpenList
问题是您不是在处理 CellSearch
对象的集合,而是在处理指向它们的指针,这使得比较器可以处理指针。
这是您可以重复用于其他指针比较的通用解决方案:
template<class T>
struct PointerComparator {
bool operator()(const T *a, const T *b) const {
return *a < *b;
}
};
std::multiset<CellSearch*, PointerComparator<CellSearch> > myOpenList;
这样您仍然可以为 CellSearch
定义 operator <
。
你可以像这样定义一个无单元仿函数:
class cmpCell
{
bool operator()(CellSearch* a, CellSearch* b)
{
return *a < *b;
}
};
然后在声明多重集时使用它:
std::multiset<CellSearch*, cmpCell> myOpenList;