参考Qt的QFutureSynchronizer机制同步拷贝文件

Qt同步拷贝文件方法:

QMap< QString, QString > m_Files;
    QMap< QString, QString > m_FileMimetypes;
QHash<QString, QString> ImportEPUB::LoadFolderStructure()
{
    QList<QString> keys = m_Files.keys();
    int num_files = keys.count();
    QFutureSynchronizer<tuple<QString, QString> > sync;

    for (int i = 0; i < num_files; ++i) {
        QString id = keys.at(i);
        sync.addFuture(QtConcurrent::run(
                           this,
                           &ImportEPUB::LoadOneFile,
                           m_Files.value(id),
                           m_FileMimetypes.value(id)));
    }

    sync.waitForFinished();
    QList<QFuture<tuple<QString, QString> > > futures = sync.futures();
    int num_futures = futures.count();
    QHash<QString, QString> updates;

    for (int i = 0; i < num_futures; ++i) {
        tuple< QString, QString > result = futures.at(i).result();
        updates[result.get<0>()] = result.get< 1 >();
    }

    updates.remove(UPDATE_ERROR_STRING);
    return updates;
}


tuple<QString, QString> ImportEPUB::LoadOneFile(const QString &path, const QString &mimetype)
{
    QString fullfilepath = QFileInfo(m_OPFFilePath).absolutePath() + "/" + path;
    
    try {
        Resource &resource = m_Book->GetFolderKeeper().AddContentFileToFolder(fullfilepath, false, mimetype);
        QString newpath = "../" + resource.GetRelativePathToOEBPS();
        return make_tuple(fullfilepath, newpath);
    } catch (FileDoesNotExist &) {
        qDebug() << "FNDE: " << path;
        return make_tuple(UPDATE_ERROR_STRING, UPDATE_ERROR_STRING);
    }
}
以下是使用boost库threadpool模拟使用,比较运行时间

#include <time.h>
#include <iostream>
#include <wx/string.h>
#include <wx/filefn.h>
#include <wx/filename.h>
#include <wx/dir.h>
#include <wx/arrstr.h>
#include <wx/thread.h>
#include <boost/threadpool.hpp>

size_t GetFileNum(const wxString &dir_name, wxArrayString *files)
{
	std::cout << dir_name << std::endl;
	return wxDir::GetAllFiles(dir_name, files, wxEmptyString, wxDIR_FILES);
}

void CopyOneFile(void *data)
{
	static wxMutex access_mutex;
	wxMutexLocker lock(access_mutex);
	wxString source_file = *(wxString*) data;
	const wxString &dest_file = wxString("E:/test/").Append(
			wxFileName(source_file).GetFullName());
	wxCopyFile(source_file, dest_file);
}

void SynchronousCopyFiles(const wxString &dir_name)
{
	wxArrayString files;
	size_t num_files = GetFileNum(dir_name, &files);
//	std::cout << num_files << std::endl;

	clock_t time = clock();
	boost::threadpool::pool thread_pool(num_files);
	for (size_t i = 0; i < num_files; ++i)
	{
		std::cout << files[i] << std::endl;
		thread_pool.schedule(boost::bind(CopyOneFile, &files[i]));
	}
	thread_pool.wait();
	std::cout << "SynchronousCopyFiles: " << clock() - time << std::endl;
}

void CopyFilesOneByOne(const wxString &dir_name)
{
	wxArrayString files;
	size_t num_files = GetFileNum(dir_name, &files);

	clock_t time = clock();
	for (size_t i = 0; i < num_files; ++i)
	{
		std::cout << files[i] << std::endl;
		CopyOneFile(&files[i]);
	}
	std::cout << "CopyFilesOneByOne: " << clock() - time << std::endl;
}

int main()
{
	const wxString dir_name =
			wxT("E:/workspace/help/Sigil_User_Guide_0_7_0/OEBPS/Text/");
	SynchronousCopyFiles(dir_name);
//	CopyFilesOneByOne(dir_name);
	return 0;
}


你可能感兴趣的:(参考Qt的QFutureSynchronizer机制同步拷贝文件)