c# - C# 通用委托(delegate)的 C++ 等效语法,以及与 lambda 的用法

标签 c# c++ templates generics

在 C# 中我可以这样做:

delegate void myFunctionDelegate<T>(T arg);

在 C++ 中,我明白我需要为函数指针的模板使用别名,但语法太奇怪了,我发现的所有示例都让我更加困惑。

以下是错误的;我该如何纠正它?

template<typename T>
using myFunctionDelegate = void (*)(T arg);

我想这样使用它:

template<class T> class Foo
{
    ...
    void someOtherFunction(myFunctionDelegate callback)
    {
        ...
        callback(someValue);
    }
}

然后:

myClassInstance.someOtherFunction([&](T arg) {
    // do something with the callback argument
});

最佳答案

您所拥有的几乎可以在句法上起作用; myFunctionDelegate 的使用只需要一个类型参数:

void someOtherFunction(myFunctionDelegate<T> callback)
                                         ^^^

如果您没有从中获得任何特别的好处,别名参数名称是可选的:

template<typename T>
using myFunctionDelegate = void(*)(T);

但是,还有一个更大的问题:函数指针不处理状态。示例调用中使用的 lambda 通过捕获它来使用状态。因此,捕获的 lambda 不能转换为函数指针。当传入这样一个 lambda 非常方便时,函数参数应该支持它。

有两种常用的方法。首先是忘记强制特定的返回和参数类型。相反,让调用者传递任何可以按照函数调用方式调用的对象(lambda、函数指针、仿函数、std::bind 的结果):

template<typename Callable>
void someOtherFunction(Callable callback) {
    ...
    callback(someValue);
}

如果调用不起作用,代码将无法编译1(不幸的是,错误不是很有帮助,但 future 的Concepts 补充可以很容易地帮助那里)。

另一方面,您可能希望明确指定函数类型。 C++ 有一个通用类型来存储任何可调用对象(参见上面的列表)。该类型是 std::function。它比简单的模板参数更重量级,但在您需要时很有用。

template<typename T>
using myFunctionDelegate = std::function<void(T)>;

void someOtherFunction(const myFunctionDelegate<T> &callback) {...}

[1]:这并不总是正确的(参见 SFINAE),但就您而言可能是正确的。

关于c# - C# 通用委托(delegate)的 C++ 等效语法,以及与 lambda 的用法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28890918/

相关文章:

c# - Facebook SDK C# Windows Phone 8.1(非 Silverlight)

c++ - Visual Studio 中的动态链接

c++ - 从子类 : gcc vs msvc 访问 protected 成员

visual-studio-2010 - 无法在 VSIX 部署模板中引用向导程序集

c++ - 如何处理空参数包的情况

c++ - 什么是在 c++ 中获取按值排序的列表中元素的序号位置的算法或代码

c# - 如何将公钥存储在机器级 RSA key 容器中

c# - 如何将(1,11,12,2,All,Others)排序为(All,1,2,11,12,Others)?

c# - 使用 ASPNETCORE_ENVIRONMENT 覆盖 Azure 上的 appsettings.json

c++ - 为什么我无法更改 `set<set<int>>` 循环中的值