我们可以使用 std::function 和 std::ref 分别替换 boost::function 和 boost::ref 吗?

Can we use std::function and std::ref to replace boost::function and boost::ref, respectively?

提问人:pesala 提问时间:11/23/2022 最后编辑:pesala 更新时间:11/24/2022 访问量:86

问:

目前,我正在从项目中删除 Boost 依赖项。我分别用 和 替换了 和 。我能够构建项目,但是在执行它的情况下,会通过异常捕获并冻结功能。boost::functionboost::refstd::functionstd::ref

此外,替换为 后,它不能直接与静态无效方法进行比较。boost::functionstd::functionstd::function<void()>

有人对此有建议吗?

bool NotificationQueue::evoke(boost::function<void()> runner) {
if (runner == &Sentinel::stop) {
    return false;
} 

}

这与 boost perfect 一起使用,当我用 std 替换 boost 时,这些更改已经完成

bool NotificationQueue::evoke(function<void()> runner) {
if (runner.target<void()>() == &Sentinel::stop) {
    return false;
} 

此外,以下错误会引发

static void stop() { throw std::logic_error("stop sentinel should not be executed"); }

我在以下代码中包含了这个停止方法

_stopFn(&Sentinel::stop)

void NotificationQueue::postStop() {

postNotification(参考(_stopFn));

unique_lock<mutex> lock(_mutex);
if (!_notificationEnabled) {
    _stopped = true;
    _enabledNotifier.notify_all();
}

}

上面的 ref 以前在 boost::ref 中

c++ 升压 std 函数 boost-ref

评论

1赞 Remy Lebeau 11/23/2022
"它通过异常捕获并冻结功能“ - 不确定我是否理解你想说什么。但是,如果您提供一个适用于 boost 但不适用于 std 的最小可重现示例,这将很有用。
0赞 sehe 11/23/2022
请在代码中显示您遇到的问题。
0赞 sehe 11/23/2022
据我所知,无论如何都不可能将任何函数<>与静态 void 方法进行比较(stackoverflow.com/q/7244881/85371)
0赞 pesala 11/23/2022
@sehe我已经编辑并包含了代码片段。

答:

1赞 sehe 11/24/2022 #1

谢谢你的片段。它们有助于查明您错过的功能。

https://en.cppreference.com/w/cpp/utility/functional/function/target 的文档包括一个示例,说明如何使用它来获得您想要的行为。target<>

让我们同时实现 和 :is_equalboost::functionstd::function

template <typename Sig>
static bool is_equal(boost::function<Sig> const& lhs, Sig* rhs) {
    return lhs == rhs;
}

template <typename Sig>
static bool is_equal(std::function<Sig> const& lhs, Sig* rhs) {
    return lhs && lhs.target_type() == typeid(Sig*) && *lhs.template target<Sig*>() == rhs;
}

现在,您可以使用 和 执行相同的测试:boost::functionstd::function

using SIG = void(int);
void foo(int) { std::puts("foo"); }
void bar(int) { std::puts("bar"); }

template <template <typename> class Function> void tests() {
    Function<SIG> f;

    assert(!is_equal(f, &foo));
    assert(!is_equal(f, &bar));

    f = foo;
    assert(is_equal(f, &foo));
    assert(!is_equal(f, &bar));

    f = bar;
    assert(!is_equal(f, &foo));
    assert(is_equal(f, &bar));
}

int main()
{
    tests<boost::function>();
    tests<std::function>();
}

Coliru 上观看直播

您可以稍微概括一下,这样它就不会假设具有完全相同签名的静态函数:http://coliru.stacked-crooked.com/a/149fe53bc30f1e70

评论

0赞 sehe 11/24/2022
顺便说一句,看起来你用来实现一个状态机,明智的做法是明确说明,而不是公开实现细节。function<>