11 std::chrono::seconds
noLimit(0);
17 std::map<std::string, MethodFactory::MethodConstructor> MethodFactory::s_methodsMap;
21 auto itr = s_methodsMap.find(name);
22 if (itr == s_methodsMap.end()) {
23 s_methodsMap.emplace(name, constructor);
31 MethodFactory::MethodPtr MethodFactory::create(
const std::string &name,
unsigned int n,
const std::set<std::string> &Sp,
const std::set<std::string> &Sm,
const std::set<std::string> &S,
const std::set<std::string> &prefixes,
const std::set<char> &alphabet) {
32 auto itr = s_methodsMap.find(name);
33 if (itr == s_methodsMap.end()) {
37 return itr->second(Sp, Sm, S, prefixes, alphabet, n);
41 std::unique_ptr<Method>
constructMethodTrigger(
const std::string &name,
unsigned int n,
const std::set<std::string> &Sp,
const std::set<std::string> &Sm,
const std::set<std::string> &S,
const std::set<std::string> &prefixes,
const std::set<char> &alphabet,
const std::chrono::seconds &timeLimit, std::atomic_bool &stopTrigger,
const bool *stopPointer) {
44 throw std::invalid_argument(
"Unknown method type: " + name);
46 method->setStopTrigger(timeLimit, stopTrigger, stopPointer);
50 std::unique_ptr<Method>
constructMethod(
const std::string &method,
unsigned int n,
const std::set<std::string> &Sp,
const std::set<std::string> &Sm) {
51 std::set<std::string> S =
computeS(Sp, Sm);
55 return std::move(
constructMethod(method, n, Sp, Sm, S, prefixes, alphabet));
58 std::unique_ptr<Method>
constructMethod(
const std::string &method,
unsigned int n,
const std::set<std::string> &Sp,
const std::set<std::string> &Sm,
const std::set<std::string> &S,
const std::set<std::string> &prefixes,
const std::set<char> &alphabet) {
62 std::pair<std::unique_ptr<Method>,
bool>
constructMethod(
const std::string &method,
const std::set<std::string> &Sp,
const std::set<std::string> &Sm,
const std::chrono::seconds &timeLimit,
long double *timeTaken) {
63 std::set<std::string> S =
computeS(Sp, Sm);
67 return constructMethod(method, Sp, Sm, S, prefixes, alphabet, timeLimit, timeTaken);
70 std::pair<std::unique_ptr<Method>,
bool>
constructMethod(
const std::string &method,
const std::set<std::string> &Sp,
const std::set<std::string> &Sm,
const std::set<std::string> &S,
const std::set<std::string> &prefixes,
const std::set<char> &alphabet,
const std::chrono::seconds &timeLimit,
long double *timeTaken) {
71 std::atomic_bool stopTrigger(
false);
74 std::chrono::seconds remainingTime(timeLimit);
76 std::unique_ptr<Method> bestPossible =
nullptr;
79 std::packaged_task<void()> task([&]() {
82 while (cont && !stopTrigger) {
83 std::unique_ptr<Method> toTry =
constructMethodTrigger(method, n, Sp, Sm, S, prefixes, alphabet, remainingTime, stopTrigger, &stopBool);
85 bool success = toTry->solve();
87 *timeTaken += toTry->timeToSolve();
89 remainingTime -= std::chrono::seconds(
int(std::floor(toTry->timeToSolve())));
91 if (remainingTime.count() <= 0) {
92 if (timeLimit == std::chrono::seconds(0)) {
93 remainingTime = std::chrono::seconds(0);
96 remainingTime = std::chrono::seconds(1);
101 bestPossible = std::move(toTry);
108 std::future<void> future = task.get_future();
109 std::thread t(std::move(task));
112 if (timeLimit <= std::chrono::seconds(0)) {
116 return std::make_pair(std::move(bestPossible),
true);
122 std::future_status status = future.wait_for(timeLimit);
123 if (status == std::future_status::ready) {
126 return std::make_pair(std::move(bestPossible),
true);
129 stopTrigger.store(
true);
133 return std::make_pair(std::move(bestPossible),
false);
std::unique_ptr< Method > constructMethodTrigger(const std::string &name, unsigned int n, const std::set< std::string > &Sp, const std::set< std::string > &Sm, const std::set< std::string > &S, const std::set< std::string > &prefixes, const std::set< char > &alphabet, const std::chrono::seconds &timeLimit, std::atomic_bool &stopTrigger, const bool *stopPointer)
The namespace of the library.
std::chrono::seconds noLimit(0)
static MethodPtr create(const std::string &name, unsigned int n, const std::set< std::string > &Sp, const std::set< std::string > &Sm, const std::set< std::string > &S, const std::set< std::string > &prefixes, const std::set< char > &alphabet)
Creates a unique_ptr to a method.
std::set< std::string > computePrefixes(const std::set< std::string > &S)
Computes .
static bool registerMethod(const std::string &name, MethodConstructor const &constructor)
Registers a method.
std::atomic_bool falseStopTrigger(false)
std::unique_ptr< Method > constructMethod(const std::string &name, unsigned int n, const std::set< std::string > &Sp, const std::set< std::string > &Sm)
Computes the alphabet and the prefixes set from Sp and Sm and constructs a method for a fixed number ...
std::unique_ptr< Method > MethodPtr
The type the function create will return.
std::set< std::string > computeS(const std::set< std::string > &Sp, const std::set< std::string > &Sm)
Computes .
std::function< MethodPtr(const std::set< std::string > &Sp, const std::set< std::string > &Sm, const std::set< std::string > &S, const std::set< std::string > &prefixes, const std::set< char > &alphabet, unsigned int n)> MethodConstructor
The type of the constructor the registerMethod must receive.
std::set< char > computeAlphabet(const std::set< std::string > &S)
Computes the alphabet from the words in .