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
,可以灵活地包装各种类型的可调用对象,使得任务调度更加通用和方便。