【发布时间】:2010-07-28 08:55:21
【问题描述】:
我正在尝试使用 lambda 来代替函数指针,但 VS2010 似乎无法转换它。我试过像这样使用 std::function 并且它崩溃了,我不知道我这样做是否正确!
#include <windows.h>
#include <conio.h>
#include <functional>
#include <iostream>
#include <concrt.h>
void main()
{
std::function<void(void*)> f = [](void*) -> void
{
std::cout << "Hello\n";
};
Concurrency::CurrentScheduler::ScheduleTask(f.target<void(void*)>(), 0);
getch();
}
编译器无法将这样的 lambda 转换为简单的函数指针,因为它不捕获任何变量,这对我来说似乎很奇怪——即使在这种情况下,我也想知道可以做什么。
每个 lambda 的类型是否唯一?因此,我可以使用 lambda 类型作为模板参数来修改模板函数,以生成一个独特的静态函数,该函数可以被调用并有望优化?
更新
以下似乎可行,但安全吗?
#include <windows.h>
#include <conio.h>
#include <iostream>
#include <concrt.h>
template<typename Signature>
struct Bind
{
static Signature method;
static void Call(void* parameter)
{
method(parameter);
}
};
template<typename Signature>
Signature Bind<Signature>::method;
template<typename Signature>
void ScheduleTask(Signature method)
{
Bind<Signature>::method = method;
Concurrency::CurrentScheduler::ScheduleTask(&Bind<Signature>::Call,0);
}
void main()
{
ScheduleTask
(
[](void*)
{
std::cout << "Hello";
}
);
ScheduleTask
(
[](void*)
{
std::cout << " there!\n";
}
);
getch();
}
再次更新
所以在给定的帮助下,我想出了更短的:
template<typename Signature>
void (*LambdaBind(Signature))(void*)
{
struct Detail
{
static void Bind(void* parameter)
{
Signature method;
method(parameter);
}
};
return &Detail::Bind;
}
这可用于将没有 void(*)(void*) 闭包的 lambda 包装到等效的函数指针中。看来这在 VS2010 的更高版本中将变得不必要了。
那么如何让它对带有闭包的 lambda 起作用?
再次更新!
适用于 VS2010 中的闭包 - 虽然不知道它是否“安全”...
template<typename Signature>
struct Detail2
{
static std::function<void(void*)> method;
static void Bind(void* parameter)
{
method(parameter);
}
};
template<typename Signature>
std::function<void(void*)> Detail2<Signature>::method;
template<typename Signature>
void (*LambdaBind2(Signature method))(void*)
{
Detail2<Signature>::method = method;
return &Detail2<Signature>::Bind;
}
【问题讨论】:
-
Related,不会考虑重复。
-
啊,这有帮助...而且我现在有一个解决方法,我认为在我更新的问题中是安全的?
-
似乎足够安全。我将为您提供更通用的解决方案。您应该删除
static Signature method;并将Signature method;放在函数中。它是空的,所以无论如何它不会花费任何费用。 -
其实我不太明白你是怎么做到的?
-
好的,现在我明白你的意思了.. 谢谢 :)
标签: c++ visual-studio-2010 lambda c++11