我正在尝试使用本地函数对成员变量类型std :: list进行排序。由于C ++不允许本地函数,因此Herb Sutter建议本地类,我最终得到了以下代码。但我不确定如何将函数指针传递给std::list::sort()
函数。
void MyClass::UpdateList()
std::map<ClassA*, int> myCustomOrder; //contains order for ClassA objects
class CompareMyClass
{
public:
CompareMyClass(std::map<ClassA*, int>* order) : m_order(order) { }
bool operator()(ClassA *p1, ClassA *p2) {
return m_order->find(p1) < m_order->find(p2);
return false;
}
private:
std::map<ClassA*, int>* m_order;
};
CompareMyClass compareObj(&myCustomOrder); // set the order
// sort the list
m_list.sort(compareObj); // How do I pass a function pointer at this point
}
我收到编译错误
模板参数可能不引用本地类型
由于
答案 0 :(得分:0)
正如juanchopanza所指出的那样,正如你在c ++ 11中this question所看到的那样,这个问题不再存在,所以如果可能的话,这可能是最好的方法。
如果没有,我想出了一个解决方案,如果你有少量类型的本地类(例如比较器,可能还有几个),你可能会有用。 我在前面提到的SO问题中采用了这个例子并对其进行了修改,因此它可以在C ++ 03下运行:
#include <iostream>
#include <vector>
#include <algorithm> // std::remove_if
using namespace std;
template <typename T>
class check {
public:
virtual bool operator()(T x) = 0;
};
template <typename T>
struct cheat {
cheat(check<T> *c) {_c = c;}
bool operator()(T x) {return _c->operator ()(x);}
check<T> *_c;
};
int main() {
int array[] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
std::vector<int> v( array, array+10 );
class even : public check<int>
{
public:
virtual bool operator()( int x ) { cout<<"Hi"<<endl; return !( x % 2 ); }
};
even e;
remove_if( v.begin(), v.end(), cheat<int>(&e)); // no error, prints Hi
return 0;
}
同样在https://ideone.com/HY5bIU(用Wall编写,也是迂腐......)
例如,如果我想在我的代码中使用很多一元运算符,我可以创建一个抽象类,以便我的所有运算符都可以继承它,并且我创建了一个cheat
类,它基本上就在那里只是为了帮助打电话给当地一个班级。
修改:另一个带有更小印记的选项:
#include <iostream>
#include <vector>
#include <algorithm> // std::remove_if
using namespace std;
template <typename T>
class check {
public:
virtual bool operator()(T x) = 0;
struct aid{
aid(check *p){ _c = p;}
check *_c;
bool operator()(T x){
return _c->operator ()(x);
}
};
aid retMe(){
return aid(this);
}
};
int main() {
int array[] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
std::vector<int> v( array, array+10 );
class even : public check<int>
{
public:
virtual bool operator()( int x ) { cout<<"Hi"<<endl; return !( x % 2 ); }
};
even e;
remove_if( v.begin(), v.end(), e.retMe()); // no error
return 0;
}
这里aid
类隐藏在抽象类本身中,但想法是一样的。
它确实添加了一些不必要的代码,但另一方面它并不像某些黑客那样怪诞。
答案 1 :(得分:0)
示例代码显示运算符重载,静态函数(调用注释掉)和lambda函数(调用注释掉):
#include <iostream>
#include <list>
#include <string>
class names
{
struct name_node
{
std::string name;
inline bool operator< (const name_node &rnode)
{return (this->name < rnode.name);}
static bool compare_node(const name_node & lnode, const name_node & rnode)
{return (lnode.name < rnode.name);}
};
std::list <name_node> name_list;
public:
void get_data();
void sort_data();
void show_data();
};
void names::get_data()
{
name_node nn;
std::string fruits[5] = { "peach", "cherry", "apple", "plum", "banana" };
for (size_t i = 0; i < sizeof(fruits) / sizeof(fruits[0]); i++){
nn.name = fruits[i];
name_list.push_back(nn);
}
}
void names::sort_data()
{
name_list.sort();
// name_list.sort(names::name_node::compare_node);
// name_list.sort([this](const name_node & lnode, const name_node & rnode)
// {return (lnode.name < rnode.name);});
}
void names::show_data()
{
std::list<name_node>::iterator it;
for(it = name_list.begin(); it != name_list.end(); ++it)
std::cout << (*it).name << std::endl;
};
int main()
{
names n;
n.get_data();
n.sort_data();
n.show_data();
return 0;
}