我有一个类,它有一个成员函数,可以打开一个文件,逐行读取并对它做一些事情,然后逐行写入另一个文件。这需要一些时间。
我在一个线程中运行此函数。现在我想显示函数的进度但是从main而不是将代码添加到将显示进度的类函数(printf等)。
这样我可以在windows或linux中运行该类,但在main中为特定操作系统使用不同的进度条代码。
答案 0 :(得分:0)
我赞成@πάνταῥεῖ(你怎么写那个!?)的想法。
首先,我们有一个abstract_sink
结构,它将作为我们所有接收器的接口。
struct abstract_sink {
virtual void on_progress_inc(int progress) = 0;
};
两个示例汇:
struct my_sink : abstract_sink {
void on_progress_inc(int progress) {
std::cout << "The progress: " << progress << "%" << std::endl;
}
};
struct my_another_sink : abstract_sink {
void on_progress_inc(int progress) {
std::cout << "The progress: " << progress << " --- " << std::endl;
}
};
最后将实现一个仿函数(参见:C++ Functors - and their uses),这个仿函数取代了你的成员函数。
template<typename Sink>
struct process_file_functor
{
// Constructor.
process_file_functor(Sink &sink)
{
m_sink = std::make_shared<Sink>(sink);
}
void operator()(std::string infile, std::string outfile)
{
std::fstream inf(infile);
std::fstream out(outfile);
int total_lines = std::count(std::istreambuf_iterator<char>(inf), std::istreambuf_iterator<char>(), '\n');
inf.seekg(0);
int progress = 0;
for (std::string line; std::getline(inf, line); )
{
/*
Here you will do what you have to do and in every iteration
you will compute progress = 100 * lines_processed / total_lines and call...
*/
progress++;
m_sink->on_progress_inc(100 * progress/total_lines); // Here you notify the progress.
}
}
std::shared_ptr<Sink> m_sink;
};
使用示例:
#include <iostream>
#include <fstream>
#include <memory>
#include <string>
#include <thread>
int main(int argc, char *argv[])
{
my_sink ms;
my_another_sink mas;
process_file_functor<my_sink> pfile(ms);
process_file_functor<my_another_sink> pfile1(mas);
std::thread t1(pfile, "data1.txt", "data2.txt");
std::thread t2(pfile1, "data1.txt", "data2.txt");
t1.join();
t2.join();
return 0;
}
重要提示:此代码不涉及并发性,不要将其用于生产只是一种说法。