gpt4 book ai didi

C++ 调度程序参数传递

转载 作者:搜寻专家 更新时间:2023-10-31 02:04:18 25 4
gpt4 key购买 nike

我有一个无法编译的简单调度程序结构,老实说,我不知道为什么。

所以我创建了一个调度程序,您可以将一个函数绑定(bind)到调用的更新,它将调用一个名为 invoke 的静态成员函数,该函数取消引用对象实例并使用简单的 std::ostream 调用该方法引用

出于某种原因,这无法编译,但在我看来它是正确的。编译器不会给出任何好的输出:/

提前致谢

#include <iostream>
#include <list>
#include <utility>

namespace trd {

struct dispatcher {
public:
template<typename C, void(C::*M)(std::ostream & os) = C::update>
static void invoke(void * instance, std::ostream & os) {
(static_cast<C*>(instance)->*M)(os);
}

template<typename C, void(C::*M)(std::ostream & os) = &C::update>
void bind(C * instance) {
instances.push_back(std::make_pair(&invoke<C, M>, instance));
}

void operator () (std::ostream & os) {
for (auto & instance : instances)
(instance.first)(instance.second, os);
}

private:
std::list<std::pair<void(*)(std::ostream & os), void *>> instances;
};

}

struct test {
public:
void update(std::ostream & os) { os << "foo"; }
};

int main() {
trd::dispatcher dp;

test t;

dp.bind(&t);

dp(std::cout);

return 0;
}

最佳答案

您使用的是方法而不是函数,因此使用 C 风格的转换将实例转换为 void 是不好的做法。

相反,C++ 有 std::function 和 lambdas:

namespace trd {

struct dispatcher {
public:
template<typename C, void(C::*M)(std::ostream & os) = &C::update>
void bind(C * instance) {
instances.push_back([=](std::ostream & os){std::invoke(M, instance, os);});
}

void operator () (std::ostream & os) {
for (auto & instance : instances)
std::invoke(instance, os);
}

private:
std::list<std::function<void(std::ostream & os)>> instances;
};
}

将 C++17 用于 std::invoke

关于C++ 调度程序参数传递,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53747991/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com