C++ 是否有类似“a”的东西;默认比较器";?
我编写了一个包装std::vector的模板,以确保始终对该向量进行排序:C++ 是否有类似“a”的东西;默认比较器";?,c++,compare,C++,Compare,我编写了一个包装std::vector的模板,以确保始终对该向量进行排序: template <typename T> class SortedVector{ public: SortedVector(bool (*comparator)(T,T)=DefaultComparator<T>){ this->comparator = comparator; } void insertValue(T newElement)
template <typename T> class SortedVector{
public:
SortedVector(bool (*comparator)(T,T)=DefaultComparator<T>){
this->comparator = comparator;
}
void insertValue(T newElement){
vect.insert(std::lower_bound(
vect.begin(),vect.end(),newElement,comparator),newElement);
}
private:
std::vector<T> vect;
bool (*comparator)(T,T);
};
作为默认参数
也许这是个愚蠢的问题。。。在不定义自己的DefaultComparator
的情况下,是否有更好的方法获得相同的结果
我不能使用C++11。没有一个标准的函数模板来做你想做的事情;但是有一个标准的函数类模板,
std::less
。如果要使用泛型函数对象,而不是将自己限制为函数指针,那么很容易将其指定为默认值:
template <typename T, typename Comparator = std::less<T> >
class SortedVector{
public:
SortedVector(Comparator comparator = Comparator()){
this->comparator = comparator;
}
void insertValue(T newElement){
// lower_bound accepts any suitable function object, so no change needed
vect.insert(std::lower_bound(
vect.begin(),vect.end(),newElement,comparator),newElement);
}
private:
std::vector<T> vect;
Comparator comparator;
};
模板
类分拣机{
公众:
SortedVector(比较器比较器=比较器(){
这个->比较器=比较器;
}
void insertValue(T新元素){
//下限接受任何合适的函数对象,因此不需要更改
向量插入(标准::下界)(
vect.begin(),vect.end(),newElement,comparator),newElement);
}
私人:
std::vector-vect;
比较器;
};
您可以使用类模板作为默认模板
template <typename T, typename C=std::less<T>>
class SortedVector
{
public:
SortedVector(C cmp=C()) : comparator(cmp)
{
}
void insertValue(T newElement){
vect.insert(std::lower_bound(
vect.begin(),vect.end(),newElement,comparator),newElement);
}
private:
std::vector<T> vect;
C comparator;
};
模板
类分拣机
{
公众:
SortedVector(C cmp=C()):比较器(cmp)
{
}
void insertValue(T新元素){
向量插入(标准::下界)(
vect.begin(),vect.end(),newElement,comparator),newElement);
}
私人:
std::vector-vect;
C比较器;
};
使用std::less
。如果你没有它,写你自己的一个很简单。我喜欢的一个变体是向量
,只有当人们阅读它时才会排序。给它写信并不能把它分类。因此,您可以跟踪前缀排序位置的“高位”标记,阅读时,您首先对“未排序”部分进行排序,然后与“已排序”部分进行合并。如果您的用例是“添加一堆数据,然后对其进行大量检查”,而不是“编辑、检查、编辑、检查”,这将产生非常好的性能。您的实现在这两个方面的性能都很差。@Yakk我对这个类的实际应用是,我必须运行数百万个元素(太多太大,无法放入任何合理的向量),并且只保留N
最低的元素。因此,首先填充然后排序不是一个选项,否则会导致一些过于复杂的事情,因为无论如何,应用程序都会因为从文件而不是其他任何东西读取这些元素而变慢。@Yakk实际上,这个问题是一个后续问题。如果您能对这个问题进行评论/回答,那就太好了,因为这里的这个问题实际上只是关于比较器的。@tobi303正如我在这里提到的,使用排序向量来查找最低的100项也是个坏主意。它是O(mnlgn)
其中m
是总元素,n
是极限。您可以在O(m lg n)
中执行此操作。注意:std::less
自C++11以来就可用。@juanchopanza我也这么认为,但它是如此…@black:没有默认参数的版本标记为“直到C++14”。它在C++98中可用,在这之前在STL中也可用。现在,它被一个(向后兼容的)版本所取代,如果您不指定参数类型,它将推断参数类型,如果您指定,它的行为将与以前完全相同。一段时间后,我又在研究这个问题,现在我想知道是否真的有必要将Comparator类型作为模板参数,而不管怎样,它将是bool(*Comparator)(const T&,const T&)
并将实际实例传递给构造函数。是否可以将其作为typedef添加到类中并跳过模板参数?(我尝试过,但编译器抱怨构造函数参数列表中Comparator Comparator=std::less
中的T
)@tobi303:通常最好使用像std::less
这样的函数类,而不是函数指针,这样函数调用是直接的、可内联的。如果出于某种原因特别不喜欢模板,可以将类型硬编码为函数指针;但性能可能会受到影响,并且需要提供函数用于默认比较器的是ion,而不是std::less。
template <typename T, typename C=std::less<T>>
class SortedVector
{
public:
SortedVector(C cmp=C()) : comparator(cmp)
{
}
void insertValue(T newElement){
vect.insert(std::lower_bound(
vect.begin(),vect.end(),newElement,comparator),newElement);
}
private:
std::vector<T> vect;
C comparator;
};