From 2fe995048c5d055ed9439006074170d4e20c9f4f Mon Sep 17 00:00:00 2001 From: Daniel Santos Date: Thu, 17 Mar 2022 07:34:32 +0000 Subject: make numericx_translate() * add numericx_free() and numericx_translate() * functionality in main() to the minimum, to house the numericx_translate() in it Signed-off-by: Daniel Santos --- numericx.c | 175 ++++++++++++++++++++++++++++++++++++++++++++++++------------- 1 file changed, 140 insertions(+), 35 deletions(-) diff --git a/numericx.c b/numericx.c index c3d6b97..695ef4e 100644 --- a/numericx.c +++ b/numericx.c @@ -368,42 +368,82 @@ free_numeral(numeral_ptr* numeral) } } - -/* ||MAIN FUNCTION|| */ +/** + * @brief Free numericx result + * + * Function frees up the result of numericx_translate(), + * after we are done with it + * + * @param string - char pointer to be free + */ +void +numericx_free(char* string) +{ + free(string); +} /** - * @brief Translate number. + * @brief Convert numeral_ptr to string * - * Main function that does the translation of the number. + * Allocates space for string and converts numeral_ptr* to char* + * + * @param numeral - numeral_ptr to be converted to string + * @param result_with_units_on_the_end - define if result has units on the end + * + * @return char pointer to converted string in case of success + * @return NULL in case of no memory */ -int -main(int argc, char* argv[]) +char* +numeral_to_string(numeral_ptr* numeral, bool result_with_units_on_the_end) { - /* argument processing */ - if( !(argc == 2) ) + size_t length = 1; + numeral_ptr* numeral_last = numeral; + + while( !(numeral_last->next == NULL) ) { - fprintf(stderr, "usage: %s \n", PROG_NAME); - exit(EXIT_FAILURE); + ++length; + numeral_last = numeral_last->next; } - /* Numeral System variables from MACROS */ - char* from = malloc( (strlen(FROM_NUMERICALS) + 1) * sizeof(char) ); - char* to = malloc( (strlen(TO_NUMERICALS) + 1) * sizeof(char) ); + char* result = malloc((length + 1) * sizeof(char)); + char* tmp = result; - strcpy(from, FROM_NUMERICALS); - strcpy(to, TO_NUMERICALS); + if( !result_with_units_on_the_end ) + { + for( numeral_ptr* digit = numeral; + !(digit == NULL); digit = digit->next) + { + *tmp = *(digit->symbol); + ++tmp; + } + } + else + { + for( numeral_ptr* digit = numeral_last; + !(digit == NULL); digit = digit->previous) + { + *tmp = *(digit->symbol); + ++tmp; + } + } - /* Number variables to be converted */ - char* number = argv[1]; + *(tmp) = '\0'; + + return result; +} + +/** + */ +char* +numericx_translate(char* from, bool from_units_on_the_end, bool from_first_number_void, bool from_infinite_base, char* to, bool to_units_on_the_end, bool to_first_number_void, bool to_infinite_base, char* number) +{ /* Check if number belongs to it's numerical system */ if( !is_valid_number(from, number) ) { fprintf(stderr, "error: %s: %s.\nValid numerals are: \"%s\"\n", PROG_NAME, strerror(EDOM), from); - free(from); - free(to); - exit(EDOM); + return NULL; } /* _first and _last variables */ @@ -413,7 +453,7 @@ main(int argc, char* argv[]) char* to_first = to; char* to_last = to + (strlen(to) - 1); - if( FROM_UNITS_ON_THE_END ) + if( from_units_on_the_end ) { reverse_string(number); } @@ -422,7 +462,7 @@ main(int argc, char* argv[]) numeral_ptr* counting = NULL; numeral_ptr* result = NULL; - if( FROM_INFINITE_BASE ) + if( from_infinite_base ) counting = numeral_infinity(from_first, strlen(number)); else counting = numeral_infinity(from_first, 1); @@ -430,36 +470,34 @@ main(int argc, char* argv[]) result = numeral_infinity(to_first, 1); /* first number void */ - if( !(FROM_FIRST_NUMBER_VOID && TO_FIRST_NUMBER_VOID) ) + if( !(from_first_number_void && to_first_number_void) ) { - if( FROM_FIRST_NUMBER_VOID ) + if( from_first_number_void ) { if( strlen(number) == 1 && *number == *from_first ) { - free(from); - free(to); free_numeral(counting); free_numeral(result); fprintf(stderr, "error: %s: unrepresentable void number\n", PROG_NAME); - exit(EXIT_FAILURE); + return NULL; } decrement_number_string(number, from_first, from_last, from_first); } - if( TO_FIRST_NUMBER_VOID ) + if( to_first_number_void ) increment(result, to_first, to_last, to_first); } /* minor optimization for the cycle below */ char* to_second = NULL; - if( TO_INFINITE_BASE ) + if( to_infinite_base ) to_second = to_first + 1; /* increments until it finishes */ while( !is_the_same(counting, number) ) { - if( TO_INFINITE_BASE ) + if( to_infinite_base ) increment(result, to_first, to_last, to_second); else increment(result, to_first, to_last, to_first); @@ -467,15 +505,82 @@ main(int argc, char* argv[]) increment(counting, from_first, from_last, from_first); } - /* print */ - print_numeral(result); - printf("\n"); + /* result to string (result_string) */ + char* result_string = numeral_to_string(result, to_units_on_the_end); /* free memory */ - free(from); - free(to); free_numeral(counting); free_numeral(result); + return result_string; +} + +/* ||MAIN FUNCTION|| */ + +/** + * @brief Translate number. + * + * Main function that does the translation of the number. + */ +int +main(int argc, char* argv[]) +{ + /* argument processing */ + if( !(argc == 2) ) + { + fprintf(stderr, "usage: %s \n", PROG_NAME); + exit(EXIT_FAILURE); + } + + /* Number variables to be converted */ + char* number = argv[1]; + + /* Arguments for translation */ + char* from = malloc( (strlen(FROM_NUMERICALS) + 1) * sizeof(char) ); + char* to = malloc( (strlen(TO_NUMERICALS) + 1) * sizeof(char) ); + + strcpy(from, FROM_NUMERICALS); + strcpy(to, TO_NUMERICALS); + + bool to_units_on_the_end = TO_UNITS_ON_THE_END; + bool from_units_on_the_end = FROM_UNITS_ON_THE_END; + bool to_first_number_void = TO_FIRST_NUMBER_VOID; + bool from_first_number_void = FROM_FIRST_NUMBER_VOID; + bool to_infinite_base = TO_INFINITE_BASE; + bool from_infinite_base = FROM_INFINITE_BASE; + + /* Check if number belongs to it's numerical system */ + if( !is_valid_number(from, number) ) + { + fprintf(stderr, "error: %s: %s.\nValid numerals are: \"%s\"\n", + PROG_NAME, strerror(EDOM), from); + free(from); + free(to); + exit(EDOM); + } + + /* Translation */ + char* result = numericx_translate( + from, from_units_on_the_end, from_first_number_void, from_infinite_base, + to, to_units_on_the_end, to_first_number_void, to_infinite_base, + number); + + /* Test for translation failure */ + if( result == NULL ) + { + fprintf(stderr, "error: %s: Invalid translation\n", PROG_NAME); + free(from); + free(to); + return EXIT_FAILURE; + } + + /* Print */ + printf("%s\n", result); + + /* Free */ + free(from); + free(to); + numericx_free(result); + return EXIT_SUCCESS; } -- cgit 1.4.1-2-gfad0 { color: #555555 } /* Name.Decorator */ .highlight .ne { color: #bb0066; font-weight: bold } /* Name.Exception */ .highlight .nf { color: #0066bb; font-weight: bold } /* Name.Function */ .highlight .nl { color: #336699; font-style: italic } /* Name.Label */ .highlight .nn { color: #bb0066; font-weight: bold } /* Name.Namespace */ .highlight .py { color: #336699; font-weight: bold } /* Name.Property */ .highlight .nt { color: #bb0066; font-weight: bold } /* Name.Tag */ .highlight .nv { color: #336699 } /* Name.Variable */ .highlight .ow { color: #008800 } /* Operator.Word */ .highlight .w { color: #bbbbbb } /* Text.Whitespace */ .highlight .mb { color: #0000DD; font-weight: bold } /* Literal.Number.Bin */ .highlight .mf { color: #0000DD; font-weight: bold } /* Literal.Number.Float */ .highlight .mh { color: #0000DD; font-weight: bold } /* Literal.Number.Hex */ .highlight .mi { color: #0000DD; font-weight: bold } /* Literal.Number.Integer */ .highlight .mo { color: #0000DD; font-weight: bold } /* Literal.Number.Oct */ .highlight .sa { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Affix */ .highlight .sb { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Backtick */ .highlight .sc { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Char */ .highlight .dl { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Delimiter */ .highlight .sd { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Doc */ .highlight .s2 { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Double */ .highlight .se { color: #0044dd; background-color: #fff0f0 } /* Literal.String.Escape */ .highlight .sh { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Heredoc */ .highlight .si { color: #3333bb; background-color: #fff0f0 } /* Literal.String.Interpol */ .highlight .sx { color: #22bb22; background-color: #f0fff0 } /* Literal.String.Other */ .highlight .sr { color: #008800; background-color: #fff0ff } /* Literal.String.Regex */ .highlight .s1 { color: #dd2200; background-color: #fff0f0 } /* Literal.String.Single */ .highlight .ss { color: #aa6600; background-color: #fff0f0 } /* Literal.String.Symbol */ .highlight .bp { color: #003388 } /* Name.Builtin.Pseudo */ .highlight .fm { color: #0066bb; font-weight: bold } /* Name.Function.Magic */ .highlight .vc { color: #336699 } /* Name.Variable.Class */ .highlight .vg { color: #dd7700 } /* Name.Variable.Global */ .highlight .vi { color: #3333bb } /* Name.Variable.Instance */ .highlight .vm { color: #336699 } /* Name.Variable.Magic */ .highlight .il { color: #0000DD; font-weight: bold } /* Literal.Number.Integer.Long */
5