并非原创,但原创文档链接丢失。。
请实现一个简单的文本文件处理程序,要求一个生产者线程负责读入数据,另一个消费者线程池负责处理数据
#include <iostream>
#include <mutex>
#include <queue>
#include <condition_variable>
#include <thread>
#include <functional>
using namespace std;
class LockQue {
public:
void push_back(const string& line) {
{
std::unique_lock<std::mutex> lock(_mutex);
_q.push(line);
}
_push_cv.notify_one();
}
string pop_back() {
{
std::unique_lock<std::mutex> lock(_mutex);
_push_cv.wait(lock, [this]() {
return !_q.empty();
});
auto r = _q.front();
_q.pop();
return r;
}
}
size_t size() const {
return _q.size();
}
private:
std::mutex _mutex;
std::queue<string> _q;
std::condition_variable _push_cv;
};
class ThreadPool {
public:
ThreadPool(size_t numThreads) : stop(false) {
for (size_t i = 0; i < numThreads; ++i) {
threads.emplace_back([this] {
while (true) {
std::function<void()> task;
{
std::unique_lock<std::mutex> lock(this->queueMutex);
this->condition.wait(lock, [this] { return this->stop || !this->tasks.empty(); });
if (this->stop && this->tasks.empty()) {
return;
}
task = std::move(this->tasks.front());
this->tasks.pop();
}
task();
}
});
}
}
~ThreadPool() {
{
std::unique_lock<std::mutex> lock(queueMutex);
stop = true;
}
condition.notify_all();
for (std::thread& thread : threads) {
thread.join();
}
}
template<class F>
void enqueue(F&& f) {
{
std::unique_lock<std::mutex> lock(queueMutex);
tasks.emplace(std::forward<F>(f));
}
condition.notify_one();
}
private:
std::vector<std::thread> threads;
std::queue<std::function<void()>> tasks;
std::mutex queueMutex;
std::condition_variable condition;
bool stop;
};
int main() {
ThreadPool pool(4);
LockQue q;
thread input_thread([&]() {
string s;
while (cin >> s) {
q.push_back(s);
printf("q size:%lu\n", q.size());
}
});
thread out_thread([&]() {
while (true) {
string s = q.pop_back();
pool.enqueue([s] {
cout << s << endl;
});
}
});
input_thread.join();
return 0;
}