<email@andreas-eberle.com>
<tb@panthema.net>
<http://www.gnu.org/licenses/>
#ifndef EBERLE_PARALLEL_LCP_MERGE_H_
#define EBERLE_PARALLEL_LCP_MERGE_H_
#include <limits>
#include <utility>
#include "../tools/eberle-lcp-losertree.h"
#include "../sequential/eberle-mergesort-lcp.h"
#include "../tools/jobqueue.h"
#include "../tools/stringtools.h"
#include "../tools/debug.h"
#undef DBGX
#define DBGX DBGX_OMP
namespace eberle_parallel_lcp_merge
{
using std::numeric_limits;
using namespace eberle_lcp_utils;
using namespace eberle_mergesort_lcp;
using namespace jobqueue;
using namespace stringtools;
using stringtools::string;
static const bool debug_jobtype_on_creation = false;
static const bool debug_merge_start_message = true;
static string * g_outputBase;
static size_t g_lengthOfLongestJob = 0;
static unsigned g_splittingsExecuted;
static unsigned g_mergeJobsCreated;
static double g_splittingTime;
static const bool USE_WORK_SHARING = true;
static const size_t MERGE_BULK_SIZE = 4 * 1024;
static const size_t SHARE_WORK_THRESHOLD = 4 * MERGE_BULK_SIZE;
struct CopyDataJob : public Job
{
LcpCacheStringPtr input;
string* output;
CopyDataJob(const LcpCacheStringPtr& input, string* output)
: input(input), output(output)
{
g_mergeJobsCreated++;
DBG(debug_jobtype_on_creation,
"CopyDataJob (output: " << (output - g_outputBase) << ", length: " << input.size << ")");
}
virtual bool
run(JobQueue& jobQueue)
{
(void) jobQueue;
input.copyStringsTo(output, input.size);
return true;
}
};
struct BinaryMergeJob : public Job
{
LcpCacheStringPtr input1;
LcpCacheStringPtr input2;
lcp_t firstLcp;
string* output;
BinaryMergeJob(const LcpCacheStringPtr& input1, const LcpCacheStringPtr& input2, lcp_t firstLcp, string* output) :
input1(input1), input2(input2), firstLcp(firstLcp), output(output)
{
g_mergeJobsCreated++;
DBG(debug_jobtype_on_creation,
"BinaryMergeJob (length1: " << input1.size << ", length2: " << input2.size << ", output: " << (output - g_outputBase) << ")");
}
virtual bool
run(JobQueue& jobQueue)
{
(void) jobQueue;
assert(!input1.empty() && !input2.empty());
input1.firstLcp() = firstLcp;
input2.firstLcp() = firstLcp;
input1.firstCached() = input1.firstString()[firstLcp];
input2.firstCached() = input2.firstString()[firstLcp];
eberle_lcp_merge(input1, input2, output);
return true;
}
};
}
#endif