diff --git a/CMakeLists.txt b/CMakeLists.txt index c357051..914be33 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,7 +1,7 @@ cmake_minimum_required(VERSION 3.17) project( arithmo - VERSION 0.0.0 + VERSION 1.0.0 DESCRIPTION "A fast and simple-to-use library for math expressions processing" LANGUAGES C ) diff --git a/README.md b/README.md index 3a1a7cf..1f62021 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # Arithmo > A fast and simple-to-use library for math expressions processing -[![Version: v0.1.0](https://img.shields.io/badge/version-v0.1.0-blue)](https://vstan02.github.io/arithmo) +[![Version: v1.0.0](https://img.shields.io/badge/version-v1.0.0-blue)](https://vstan02.github.io/arithmo) [![License: GPL v3](https://img.shields.io/badge/license-GPL%20v3-blue.svg)](http://www.gnu.org/licenses/gpl-3.0) ## Contents @@ -23,7 +23,7 @@ const char* expression = "(23 - 4) * 3"; artm_calc_t* calc = artm_calc_init(5); // 5 is the approximate number of variables that will be used // Processing a mathematical expression: -artm_result_t result = artm_calc_process(calc, expression); +artm_result_t result = artm_calc_eval(calc, expression); // Saving the token to see exactly where the error is in the expression: const artm_token_t* token = &result.as.token; diff --git a/example/cbk.c b/example/cbk.c new file mode 100644 index 0000000..6ec7eff --- /dev/null +++ b/example/cbk.c @@ -0,0 +1,38 @@ +#include + +#include "arithmo.h" + +static void error_cbk(const artm_result_t*, void*); + +extern int main(void) { + artm_calc_t* calc = artm_calc_init(5); + + const char* expression = "$t = 3 + 5"; + double result = artm_calc_cbk_eval(calc, expression, ARTM_CBK(error_cbk, NULL)); + printf("%s = %g\n", expression, result); + + artm_calc_free(calc); + return 0; +} + +static void error_cbk(const artm_result_t* result, __attribute_maybe_unused__ void* payload) { + const artm_token_t* token = &result->as.token; + switch (result->status) { + case ARTM_NULL_CALC: + printf("[ERROR] NULL_CALC\n"); + break; + case ARTM_NULL_EXPR: + printf("[ERROR] NULL_EXPR\n"); + break; + case ARTM_ALLOC_ERR: + printf("[ERROR] ALLOC_ERR\n"); + break; + case ARTM_INV_TOKEN: + printf("[ERROR] INV_TOKEN -> '%.*s'\n", (int) token->size, token->target); + break; + case ARTM_UNDEF_VAR: + printf("[ERROR] UNDEF_VAR -> '%.*s'\n", (int) token->size, token->target); + break; + default: break; + } +} diff --git a/example/main.c b/example/main.c index 4de9943..747e110 100644 --- a/example/main.c +++ b/example/main.c @@ -1,26 +1,23 @@ #include -#include -#include -#include #include "arithmo.h" -static int process(artm_calc_t* calc, const char* expression); +static int eval(artm_calc_t* calc, const char* expression); extern int main(void) { artm_calc_t* calc = artm_calc_init(5); - process(calc, "$t = 2 + 5"); - process(calc, "t"); - process(calc, "$x = 3 + 5 - 29"); - process(calc, "x"); - process(calc, "t * (y - 1)"); - process(calc, "t * (x - 1)"); + eval(calc, "$t = 2 + 5"); + eval(calc, "t"); + eval(calc, "$x = 3 + 5 - 29"); + eval(calc, "x"); + eval(calc, "t * (y - 1)"); + eval(calc, "t * (x - 1)"); artm_calc_free(calc); return 0; } -static int process(artm_calc_t* calc, const char* expression) { - artm_result_t result = artm_calc_process(calc, expression); +static int eval(artm_calc_t* calc, const char* expression) { + artm_result_t result = artm_calc_eval(calc, expression); const artm_token_t* token = &result.as.token; switch (result.status) { diff --git a/include/arithmo.h b/include/arithmo.h index 15ebbad..7f17047 100644 --- a/include/arithmo.h +++ b/include/arithmo.h @@ -22,9 +22,13 @@ #include +#define ARTM_CBK(_target_, _payload_) \ + ((artm_cbk_t) { .target = (_target_), .payload = (_payload_) }) + typedef struct artm_calc artm_calc_t; typedef struct artm_result artm_result_t; typedef struct artm_token artm_token_t; +typedef struct artm_cbk artm_cbk_t; typedef enum { ARTM_SUCCESS, @@ -48,6 +52,11 @@ struct artm_result { } as; }; +struct artm_cbk { + void (*target)(const artm_result_t*, void*); + void* payload; +}; + /** * @brief Initializes an Arithmo Interpreter object * @param decl_table_size The approximate number of variables that will be used @@ -66,8 +75,17 @@ extern void artm_calc_free(artm_calc_t* calc); * @brief Evaluates the given mathematical expression * @param calc An Arithmo Interpreter object * @param expression The mathematical expression - * @return The evaluation result + * @return The evaluation result structure + */ +extern artm_result_t artm_calc_eval(artm_calc_t* calc, const char* expression); + +/** + * @brief Evaluates the given mathematical expression + * @param calc An Arithmo Interpreter object + * @param expression The mathematical expression + * @param cbk The callback that is called in case of an error + * @return The evaluation result value */ -extern artm_result_t artm_calc_process(artm_calc_t* calc, const char* expression); +extern double artm_calc_cbk_eval(artm_calc_t* calc, const char* expression, artm_cbk_t cbk); #endif // ARITHMO_H diff --git a/src/arithmo.c b/src/arithmo.c index 3bfcb94..2ed4fbd 100644 --- a/src/arithmo.c +++ b/src/arithmo.c @@ -100,7 +100,7 @@ extern void artm_calc_free(artm_calc_t* calc) { } } -extern artm_result_t artm_calc_process(artm_calc_t* calc, const char* expression) { +extern artm_result_t artm_calc_eval(artm_calc_t* calc, const char* expression) { if (calc == NULL) { return ARTM_ERROR(ARTM_NULL_CALC, (token_t) { 0 }); } @@ -123,6 +123,15 @@ extern artm_result_t artm_calc_process(artm_calc_t* calc, const char* expression } } +extern double artm_calc_cbk_eval(artm_calc_t* calc, const char* expression, artm_cbk_t callback) { + artm_result_t result = artm_calc_eval(calc, expression); + if (result.status == ARTM_SUCCESS) + return result.as.value; + + callback.target(&result, callback.payload); + return 0; +} + static artm_result_t parse_decl(artm_calc_t* calc) { ARTM_ADVANCE(calc);