`std::function<void()>` 是 C++11 引入的一种通用的函数包装器(functors)

std::function<void()> 是 C++11 引入的一种通用的函数包装器(functors),可以包装任何可调用的对象(如函数指针、lambda 表达式、绑定后的成员函数等)。void Application::Schedule(std::function<void()> callback) 是一个成员函数的声明,表示 Application 类中的 Schedule 方法接受一个可调用对象作为参数。

以下是对这段代码的详细解释:

1. 函数声明

cpp 复制代码
void Application::Schedule(std::function<void()> callback)
  • void:表示该函数没有返回值。
  • Application::Schedule :表示这是 Application 类的成员函数,名为 Schedule
  • std::function<void()> callback :参数是一个 std::function 对象,类型为 std::function<void()>,表示它是一个不接受参数且没有返回值的可调用对象。

2. std::function<void()> 的作用

std::function<void()> 是一个通用的函数包装器,可以包装以下类型的可调用对象:

  • 普通函数
  • Lambda 表达式
  • 绑定后的成员函数(使用 std::bind
  • 其他仿函数(functors)

3. 函数的实现

你需要实现这个成员函数。以下是一个可能的实现示例,展示了如何将 callback 添加到一个任务队列中,并可能在一个单独的线程中执行:

cpp 复制代码
#include <iostream>
#include <vector>
#include <functional>
#include <thread>
#include <mutex>

class Application {
private:
    std::vector<std::function<void()>> task_queue_;
    std::mutex mutex_;
    std::thread worker_;

    void WorkerThread() {
        while (true) {
            std::function<void()> task;
            {
                std::lock_guard<std::mutex> lock(mutex_);
                if (task_queue_.empty()) {
                    continue; // 如果任务队列为空,继续等待
                }
                task = task_queue_.back();
                task_queue_.pop_back();
            }
            task(); // 执行任务
        }
    }

public:
    Application() {
        worker_ = std::thread(&Application::WorkerThread, this);
    }

    ~Application() {
        {
            std::lock_guard<std::mutex> lock(mutex_);
            task_queue_.clear(); // 清空任务队列
        }
        worker_.join(); // 等待工作线程结束
    }

    void Schedule(std::function<void()> callback) {
        std::lock_guard<std::mutex> lock(mutex_);
        task_queue_.push_back(callback);
    }
};

4. 代码解析

  • task_queue_ :一个存储任务的队列,每个任务是一个 std::function<void()>
  • mutex_ :一个互斥锁,用于保护对 task_queue_ 的访问。
  • WorkerThread:一个工作线程,不断从任务队列中取出任务并执行。
  • Schedule:将任务添加到任务队列中。

5. 使用示例

以下是如何使用 Schedule 函数的示例:

cpp 复制代码
#include <iostream>

void SimpleFunction() {
    std::cout << "Simple function called!" << std::endl;
}

class My class {
public:
    void MemberFunction() {
        std::cout << "Member function called!" << std::endl;
    }
};

int main() {
    Application app;

    // 调度普通函数
    app.Schedule(SimpleFunction);

    // 调度 lambda 表达式
    app.Schedule([]() {
        std::cout << "Lambda expression called!" << std::endl;
    });

    // 调度绑定后的成员函数
    MyClass obj;
    app.Schedule(std::bind(&MyClass::MemberFunction, &obj));

    // 等待一段时间以确保任务被执行
    std::this_thread::sleep_for(std::chrono::seconds(1));

    return 0;
}

6. 注意事项

  • 线程安全 :如果 Schedule 函数可能被多个线程同时调用,需要使用互斥锁(如 std::mutex)来保护对共享资源(如 task_queue_)的访问。
  • 异常处理:如果任务队列中的任务可能抛出异常,需要在工作线程中捕获并处理这些异常。
  • 性能:频繁地调度任务可能会导致性能下降,特别是在任务非常轻量级的情况下。

7. 总结

void Application::Schedule(std::function<void()> callback) 是一个典型的任务调度函数,接受任何可调用对象作为参数,并将其添加到任务队列中。通过使用 std::function,可以灵活地包装各种类型的可调用对象,使得任务调度更加通用和方便。

相关推荐
虚拟之4 分钟前
36、stringstream
c++
我很好我还能学9 分钟前
【面试篇 9】c++生成可执行文件的四个步骤、悬挂指针、define和const区别、c++定义和声明、将引用作为返回值的好处、类的四个缺省函数
开发语言·c++
南岩亦凛汀1 小时前
在Linux下使用wxWidgets进行跨平台GUI开发
c++·跨平台·gui·开源框架·工程实战教程
曦月逸霜2 小时前
第34次CCF-CSP认证真题解析(目标300分做法)
数据结构·c++·算法
galaxy_strive2 小时前
绘制饼图详细过程
开发语言·c++·qt
Unpredictable2223 小时前
【VINS-Mono算法深度解析:边缘化策略、初始化与关键技术】
c++·笔记·算法·ubuntu·计算机视觉
PingdiGuo_guo4 小时前
C++智能指针的知识!
开发语言·c++
Chuncheng's blog4 小时前
CentOS 7如何编译安装升级gcc至7.5版本?
linux·运维·c++·centos
愚润求学6 小时前
【C++】类型转换
开发语言·c++
@我漫长的孤独流浪6 小时前
数据结构测试模拟题(4)
数据结构·c++·算法