我正在尝试将函数作为参数传递,Testabc继承自MainTest,我想要传递的函数是MainTest类中的受保护函数。我没有cpp访问具有此受保护的ReadTestPoint函数的MainTest类。
下面是头文件,我在其中定义了将函数作为参数的函数。
#include <QObject>
#include <QDebug>
class TestManager
{
public:
TestManager();
~TestManager() {}
int ReadTestPointer(void *dp, unsigned int &val, int (*functioncall)(void *,
unsigned int&));
};
以下是TestManager的cpp
#include "testmanager.h"
#include<QDebug>
TestManager::TestManager(){}
int TestManager::ReadTestPointer(void* dp, unsigned int &num, int (*readt)
(void*, unsigned int&))
{
qDebug()<< "Function Pointer working";
int g;
g = (*readt)(dp, num);
return g;
}
我打电话的班级:
namespace PackageCore
{
TestAbc::TestAbc() : MainTest(){}
TestAbc::~TestAbc(){}
int TestAbc::Init()
{
// initialization code called once
m_config = reinterpret_cast<Test_BaseClass*>
(GetConfig(Test_BaseClass_INTERFACE_HASH));
return 0;
}
int TestAbc::DeInit()
{
return 0;
}
int TestAbc::Cycle()
{
TestManager m_TestManager;
unsigned int m_trigger;
int (*abc)(void *, unsigned int&) = ReadTestPoint(m_config-
>SHM_B_Trigger_U8, m_trigger);
m_TestManager.ReadTestPointer(m_config->SHM_B_Trigger_U8, m_trigger, abc);
qDebug()<< " getTrigger: " << m_trigger;
return 0;
}
}
但是我得到了编译时错误:
C:\test_manager_git\testabc.cpp:39: error: invalid conversion from 'int' to 'int (*)(void*, unsigned int&)' [-fpermissive]
int (*abc)(void *, unsigned int&) = ReadTestPoint(m_config->SHM_B_Trigger_U8, m_trigger);
The MainTest.h is below:
class MainTest : public QObject
{
Q_OBJECT
public:
// Callbacks
virtual int Init() = 0;
virtual int Cycle() = 0;
virtual int DeInit() = 0;
protected:
int ReadTestPoint (void *dp, unsigned int &val);
};
谢谢
答案 0 :(得分:0)
首先,考虑使用std::function
之类的东西,而不是滚动你自己的指针噩梦。但是让我们开始......
基本上,为了从指针调用成员函数,需要函数指针和成员实例。以下代码基于您的问题代码和添加的成员指针。
#include <iostream>
class MainTest
{
public:
protected:
int ReadTestPoint (void *dp, unsigned int &val)
{
std::cout << "protected ReadTestPoint called" << std::endl;
return 0;
}
};
class TestManager
{
public:
TestManager() {}
~TestManager() {}
int ReadTestPointer(void *dp, unsigned int &val, MainTest* instance, int (MainTest::*functioncall)(void *, unsigned int&))
{
return (instance->*functioncall)(dp, val);
}
};
class TestAbc : public MainTest
{
public:
void ExecTest()
{
TestManager testManager;
unsigned int tVal;
void* dummy = &tVal;
testManager.ReadTestPointer(dummy, tVal, this, &TestAbc::ReadTestPoint);
}
};
int main(void)
{
TestAbc test;
test.ExecTest();
return 0;
}
如果您不想限制自己使用特定会员类型,请考虑使用模板功能:
class TestManager
{
public:
TestManager() {}
~TestManager() {}
template<typename Fn>
int ReadTestPointer(void *dp, unsigned int &val, Fn functioncall)
{
return functioncall(dp, val);
}
};
它将接受使用适当参数和返回类型重载operator()
的非成员函数和对象。
您可以将成员函数指针包装在Functor
对象中:
template<typename TMember, typename TResult, typename TParam1, typename TParam2>
struct Functor
{
typedef TResult (TMember::*TFn)(TParam1, TParam2);
Functor(TMember* m, TFn func):member(m), fn(func){}
TMember* member;
TFn fn;
TResult operator()(TParam1 p1, TParam2 p2)
{
return (member->*fn)(p1, p2);
}
};
以下示例包括自由函数调用和成员函数调用:
int FreeFn(void *dp, unsigned int &val)
{
std::cout << "free function called" << std::endl;
return 1;
}
class TestAbc : public MainTest
{
public:
void ExecTest()
{
TestManager testManager;
unsigned int tVal;
void* dummy = &tVal;
testManager.ReadTestPointer(dummy, tVal, Functor<TestAbc, int, void*, unsigned int&>(this, &TestAbc::ReadTestPoint));
testManager.ReadTestPointer(dummy, tVal, FreeFn);
}
};