diff --git a/README.md b/README.md index 1a1544d..a67a289 100644 --- a/README.md +++ b/README.md @@ -101,6 +101,98 @@ Which will put the library's header files and the application `/in ## Usage +TLDR; +``` +ROOT Command Line Interface + + +root_cli [OPTIONS] SUBCOMMAND + + +OPTIONS: + -h, --help Print this help message and exit + -v, --verbose Enable verbose output + --wcli, --write-to-cli + Write results to command line + --wcsv, --write-to-csv TEXT + Path for writing results to CSV file + --ocsvsep, --output-csv-sep CHAR [,] + Separator character for CSV output + --wdat, --write-to-dat TEXT + Path for writing results to DAT file + --wgnuplot, --write-to-gnuplot TEXT + Path for writing results to Gnuplot file + --ofmode, --output-file-mode CHAR:{a,o} [o] + Append or overwrite output file: 'a' for append, 'o' for + overwrite + +SUBCOMMANDS: + csv Use CSV input + dat Use DAT input + cli Use CLI input +``` + +Assuming that `root_cli` is on your `PATH`, the program can be executed with: + +``` +root_cli +# or use the full install/build path of the executable: /path/to/root_cli +``` + +In order to print out more information about the arguments and the subcommands: + +``` +root_cli +``` + +Every additional needed function must be added together with the function to find the root of. +Here's a list of examples of possible execution syntax: + +- CLI input, CLI output, Newton-Raphson method to find the root of x^2-4, starting from initial guess 1 (default tolerance and maximum iterations): + + ``` + root_cli --wcli cli --function "x^2-4" newton --initial 1.0 --derivative "2*x" + ``` + +- DAT input file called input.dat with first row not being header and " " separating different values, .dat file output called output.dat, Bisection method to find the root of x^3-1, with initial interval [-2,2], verbose output (given tolerance and maximum iterations): + + ``` + root_cli --verbose --wdat output dat input + ``` + + where input.dat is: + + ``` + function = x^3-1 + method = bisection + initial = -1 + tolerance = 1e-5 + max-iterations = 100 + derivative = 2*x + ``` + +- CSV input file called input.csv with first row which is a header and "," separating different values, .csv file ouput +called output.csv, Fixed Point Method to find the root of cos(x), with +initial guess 0.5, fixed point function cos(x): + + ``` + root_cli --wcsv output --ocsvsep , csv input --sep , --header + ``` + + where input.csv is: + + ``` + function,method,initial,tolerance,max_iterations,g-function + 'cos(x)',fixed_point,0.5,1e-5,100,'cos(x)' + ``` + +- CLI input, .dat output file called output.dat and moreover a GNU Plot is created from it as output.png. Chords method to solve +the equation x^3-8 starting from the two initial points 1 and 3: + + ``` + root_cli --wdat output --wgnuplot output cli --function x^3-8 chords --x0 --x1 3 + ``` + The installed CLI application can simply be used by: ``` diff --git a/ROOT/ROOT/reader.cpp b/ROOT/ROOT/reader.cpp index 2c92bae..80ff684 100644 --- a/ROOT/ROOT/reader.cpp +++ b/ROOT/ROOT/reader.cpp @@ -107,10 +107,10 @@ std::unique_ptr ReaderBase::make_config_from_map( } int max_iter = 100; - auto it_max = config_map.find("max_iterations"); + auto it_max = config_map.find("max-iterations"); if (it_max != config_map.end()) { if (!parseInt(it_max->second, max_iter)) { - std::cerr << "\033[31mmake_config_from_map: invalid max_iterations: " << it_max->second << "\033[0m\n"; + std::cerr << "\033[31mmake_config_from_map: invalid max-iterations: " << it_max->second << "\033[0m\n"; std::exit(EXIT_FAILURE); } } @@ -202,14 +202,14 @@ std::unique_ptr ReaderBase::make_config_from_map( case Method::FIXED_POINT: { auto it_x0 = config_map.find("initial"); - auto it_g = config_map.find("function_g"); + auto it_g = config_map.find("g-function"); if (it_x0 == config_map.end() || it_g == config_map.end()) { - std::cerr << "\033[31mmake_config_from_map: fixed_point requires initial and function_g\033[0m\n"; + std::cerr << "\033[31mmake_config_from_map: fixed_point requires initial and g-function\033[0m\n"; std::exit(EXIT_FAILURE); } double initial = 0.0; - auto function_g = FunctionParserBase::parseFunction(it_g->second); - return std::make_unique(tolerance, max_iter, aitken, function, initial, function_g, + auto g_function = FunctionParserBase::parseFunction(it_g->second); + return std::make_unique(tolerance, max_iter, aitken, function, initial, g_function, verbose); } } // switch @@ -312,8 +312,8 @@ std::unique_ptr ReaderCSV::read(CLI::App* app, bool verbose) { } } else { // positional mapping documented here: - std::vector posnames = {"method", "tolerance", "max_iterations", "aitken", "function", - "derivative", "interval_a", "interval_b", "function_g", "initial", + std::vector posnames = {"method", "tolerance", "max-iterations", "aitken", "function", + "derivative", "interval_a", "interval_b", "function-g", "initial", "x0", "x1"}; for (size_t i = 0; i < values.size() && i < posnames.size(); ++i) { config_map[posnames[i]] = values[i]; @@ -383,7 +383,7 @@ std::unique_ptr ReaderCLI::read(CLI::App* app, bool verbose) { if (verbose) { std::cout << "ReaderCLI: read configuration\n"; std::cout << " tolerance = " << app->get_option("--tolerance")->as() << "\n"; - std::cout << " max_iterations = " << app->get_option("--max-iterations")->as() << "\n"; + std::cout << " max-iterations = " << app->get_option("--max-iterations")->as() << "\n"; std::cout << " aitken = " << (app->get_option("--aitken")->as() ? "true" : "false") << "\n"; std::cout << " function = " << app->get_option("--function")->as() << "\n"; std::cout << " verbose = " << (verbose ? "true" : "false") << "\n"; @@ -423,7 +423,7 @@ std::unique_ptr ReaderCLI::read(CLI::App* app, bool verbose) { app->get_subcommand("fixed_point")->get_option("--g-function")->as()), verbose); if (verbose) { - std::cout << " g_function = " + std::cout << " g-function = " << app->get_subcommand("fixed_point")->get_option("--g-function")->as() << "\n"; std::cout << " initial = " << app->get_subcommand("fixed_point")->get_option("--initial")->as() << "\n";