A有很多B类,A类有一个对象b。这个对象b有一个函数(calc)需要一个指向A对象中方法的指针。这个方法(有趣)在类中访问私有变量(在我的例子中只返回3)。
class A;
class B {
public:
virtual int calc ( int (A::*fun)()) { return 2*fun(); };
};
class A {
B* b;
public:
A (B* b_) : b (b_) {};
int fun() { return 3; };
int run(){ return b->calc(&A::fun); };
};
int main() {
B* b = new B();
A a(b);
a.run();
return 0;
}
如何在B类calc
方法的定义中正确使用指向方法的指针?
我收到此错误消息:
teste.cpp:10:58: error: must use ‘.*’ or ‘->*’ to call pointer-to-member function in ‘fun (...)’, e.g. ‘(... ->* fun) (...)’
virtual int calc ( int (A::*fun)()) { return 2*fun(); };
^
答案 0 :(得分:1)
如果您对std::function
方法可行,我建议使用A
方法。但是,为了完整起见,以下是如何正确使用指针到成员函数的方法。
指向成员的指针本身并不存储"当前" ->*
的实例,因此您需要明确传递它。然后使用特殊的.*
(或virtual int calc (A* value, int (A::*fun)()) {
return 2 * (value->*fun)();
};
)语法来调用它。
b->calc(this, &A::fun);
然后你将其称为me.filter
。
答案 1 :(得分:1)
您可以按照自己的方式执行此操作,但成员函数在特定实例上必须为called:
class A;
class B {
public:
virtual int calc(A* a, int (A::*fun)()) { return 2 * (a->*fun)(); };
};
class A {
B* b;
public:
A(B* b_) : b(b_) {};
int fun() { return 3; };
int run() { return b->calc(this, &A::fun); }; // now also passing this pointer
};
int main() {
B* b = new B();
A a(b);
a.run();
return 0;
}
如果没有calc()
是虚拟的,那么lambda也是一个选项:
class A;
class B {
public:
template<typename T>
int calc(T fun) { return 2 * fun(); };
};
class A {
B* b;
public:
A(B* b_) : b(b_) {};
int fun() { return 3; };
int run() {
return b->calc([this]() {return fun(); } );
};
};
int main() {
B* b = new B();
A a(b);
a.run();
return 0;
}
答案 2 :(得分:0)
如果您能够使用C ++ 11,那么您应该使用std::function和std::bind:否则您需要使用pointer to member function +指向该实例的指针。
使用C ++ 11
#include <functional>
class B {
public:
virtual int calc (std::function<int()>&& fun) { return 2 * fun(); }; };
};
class A {
B* b;
public:
A (B* b_) : b (b_) {};
int fun() { return 3; };
int run() { return b->calc(std::bind(&A::fun, this)); };
};
没有C ++ 11
class B {
public:
virtual int calc (int(A::*fnptr)(), A* a) { return 2 * (a->*fnptr)(); };
};
class A {
B* b;
public:
A (B* b_) : b (b_) {};
int fun() { return 3; };
int run() { return b->calc(&A::fun, this); };
};
参见示例here。
答案 3 :(得分:0)
定义指针类方法并将其初始化为(假设SomeFn与签名匹配):
PROCEDURE centroId(pnombre IN VARCHAR2) IS
geomEntrada SDO_GEOMETRY;
dist VARCHAR2(100);
tupla caceres%ROWTYPE;
dim SDO_DIM_ARRAY;
-- Cursor para recuperar los barrios
CURSOR cursor_barrio IS
SELECT *
FROM caceres
WHERE tipo = 'Barrio';
BEGIN
-- Recuperar la geometria del parametro de entrada
SELECT Geom INTO geomEntrada
FROM Caceres
WHERE Nombre = pnombre;
-- Obtener dim
SELECT DIMINFO INTO dim
FROM USER_SDO_GEOM_METADATA
WHERE table_name='CACERES'; --Ojo, CACERES en mayúsculas
-- Recorrer todos los barrios
OPEN cursor_barrio;
LOOP
FETCH cursor_barrio INTO tupla;
EXIT WHEN cursor_barrio%NOTFOUND;
--SDO_GEOM.SDO_LENGTH
dist := SDO_GEOM.SDO_CENTROID(geomEntrada,dim);
END LOOP;
DBMS_OUTPUT.PUT_LINE(pnombre||' have this center: ' || dist);
END centroId;
被称为:
RetType (ClassName::*pfn)(Args) = &ClassName::SomeFn;