You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何正确调用Assert::ExpectException?CppUnitTestFramework异常测试报错排查

解决CppUnitTestFramework中ExpectException的C2064编译错误

这个C2064错误的核心原因很明确:你传给Assert::ExpectException的不是一个无参可调用对象,而是直接执行了AutokeyCipher::encrypt(input, primer)的结果。

为什么会报错?

ExpectException的设计逻辑是:它需要接收一个不需要任何参数的函数/可调用体,然后由框架自己去调用这个体,再捕获其中抛出的异常。而你现在的写法是直接调用了encrypt函数,相当于把encrypt的返回值(比如加密后的字符串)传给了ExpectException——这个返回值显然不是一个能接受0个参数的函数,所以编译器就抛出了C2064错误。

正确的写法

最直观也最推荐的方式是用lambda表达式把带参数的函数调用包裹起来,变成无参的可调用对象:

TEST_METHOD(test_for_correct_exception_by_input_with_whitespaces) {
    std::string input{ "meet me at the corner" };
    Assert::ExpectException<std::invalid_argument>([&]() {
        // 把你的函数调用放在lambda体内
        AutokeyCipher::encrypt(input, primer);
    });
}

这里的[&]表示按引用捕获当前作用域的变量(input和primer),lambda本身是一个无参函数,符合ExpectException的要求。当框架调用这个lambda时,才会执行encrypt函数并触发异常,进而被框架捕获验证。

如果你更倾向于用绑定的方式,也可以用std::bind来把参数绑定成无参函数:

#include <functional>

TEST_METHOD(test_for_correct_exception_by_input_with_whitespaces) {
    std::string input{ "meet me at the corner" };
    // 绑定encrypt函数和它的参数,生成无参可调用对象
    auto bound_encrypt = std::bind(&AutokeyCipher::encrypt, input, primer);
    Assert::ExpectException<std::invalid_argument>(bound_encrypt);
}

不过这种方式需要注意参数的传递方式(值还是引用),而且可读性不如lambda,所以一般优先推荐lambda写法。

内容的提问来源于stack exchange,提问作者Gino Pensuni

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.11 08:41:24