diff --git a/autotests/CMakeLists.txt b/autotests/CMakeLists.txt --- a/autotests/CMakeLists.txt +++ b/autotests/CMakeLists.txt @@ -13,6 +13,12 @@ LINK_LIBRARIES Qt5::Test NAME_PREFIX "kpat-" ) +ecm_add_test( + golf_solver_wins.cpp + TEST_NAME GolfSolveTest + LINK_LIBRARIES Qt5::Test + NAME_PREFIX "kpat-" +) ecm_add_test( solve_by_name.cpp TEST_NAME SolveByVariantName @@ -31,6 +37,7 @@ "../patpile.cpp" "../pileutils.cpp" "../renderer.cpp" + "../settings.cpp" solver_format.cpp TEST_NAME SolverFormatTest LINK_LIBRARIES Qt5::Test kcardgame diff --git a/autotests/golf_solver_wins.cpp b/autotests/golf_solver_wins.cpp new file mode 100644 --- /dev/null +++ b/autotests/golf_solver_wins.cpp @@ -0,0 +1,47 @@ +/* Copyright (c) 2019 Shlomi Fish + * + * Permission is hereby granted, free of charge, to any person + * obtaining a copy of this software and associated documentation + * files (the "Software"), to deal in the Software without + * restriction, including without limitation the rights to use, + * copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following + * conditions: + * + * The above copyright notice and this permission notice shall be + * included in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES + * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ +#include +#include +#include + +class TestSolver: public QObject +{ + Q_OBJECT +private slots: + void runSolver(); +}; + +void TestSolver::runSolver() +{ + QProcess kpat; + kpat.start(QStringLiteral("../bin/kpat"), QStringList() << QStringLiteral("--start") << "1" << QStringLiteral("--end") << "3" << QStringLiteral("--solve") << QStringLiteral("Golf")); + QCOMPARE(kpat.waitForFinished(), true); + QCOMPARE(kpat.exitStatus(), QProcess::NormalExit); + QCOMPARE(kpat.exitCode(), 0); + auto bytes = kpat.readAllStandardOutput(); + QCOMPARE(QRegularExpression("\\n2 won \\(").match(QString(bytes)).hasMatch(), true); +} + +QTEST_MAIN(TestSolver) +#include "golf_solver_wins.moc" diff --git a/golf.cpp b/golf.cpp --- a/golf.cpp +++ b/golf.cpp @@ -40,6 +40,7 @@ #include "speeds.h" #include "patsolve/golfsolver.h" #include "pileutils.h" +#include "settings.h" #include @@ -88,7 +89,9 @@ } setActions(DealerScene::Hint | DealerScene::Demo | DealerScene::Draw); - setSolver( new GolfSolver( this ) ); + auto solver = new GolfSolver( this ); + solver->default_max_positions = Settings::golfSolverIterationsLimit(); + setSolver( solver ); connect( this, &KCardScene::cardClicked, this, &DealerScene::tryAutomaticMove ); } diff --git a/kpat.kcfg b/kpat.kcfg --- a/kpat.kcfg +++ b/kpat.kcfg @@ -29,5 +29,8 @@ 0 + + 1000000 + diff --git a/patsolve/golfsolver.h b/patsolve/golfsolver.h --- a/patsolve/golfsolver.h +++ b/patsolve/golfsolver.h @@ -29,6 +29,7 @@ { public: explicit GolfSolver(const Golf *dealer); + int default_max_positions; #ifdef WITH_BH_SOLVER black_hole_solver_instance_t *solver_instance; diff --git a/patsolve/golfsolver.cpp b/patsolve/golfsolver.cpp --- a/patsolve/golfsolver.cpp +++ b/patsolve/golfsolver.cpp @@ -20,8 +20,7 @@ #include "../golf.h" #include "../kpat_debug.h" -const int CHUNKSIZE = 100; -const long int MAX_ITERS_LIMIT = 1000000; +const int CHUNKSIZE = 10000; #define BHS__GOLF__NUM_COLUMNS 7 #define BHS__GOLF__MAX_NUM_CARDS_IN_COL 5 @@ -212,6 +211,10 @@ : Solver() { deal = dealer; + // Set default_max_positions to an initial + // value so it will not accidentally be used uninitialized. + // Note: it will be overrided by the Settings anyhow. + default_max_positions = 100000; #ifdef WITH_BH_SOLVER solver_instance = NULL; solver_ret = BLACK_HOLE_SOLVER__OUT_OF_ITERS; @@ -231,7 +234,7 @@ SolverInterface::ExitStatus GolfSolver::patsolve( int _max_positions ) { int current_iters_count = 0; - max_positions = (_max_positions < 0) ? MAX_ITERS_LIMIT : _max_positions; + max_positions = (_max_positions < 0) ? default_max_positions : _max_positions; init(); if (solver_instance) @@ -276,7 +279,7 @@ ( (solver_ret == BLACK_HOLE_SOLVER__OUT_OF_ITERS) ) && - (current_iters_count < MAX_ITERS_LIMIT) + (current_iters_count < max_positions) ) { current_iters_count += CHUNKSIZE;