From 475ee86d70921638c700bc0934441c7fe2c905d1 Mon Sep 17 00:00:00 2001 From: =?utf8?q?J=C3=A9r=C3=B4me=20Benoit?= Date: Tue, 14 Mar 2017 22:21:44 +0100 Subject: [PATCH] TP 13 exo1: Implement all the required features. MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit Signed-off-by: Jérôme Benoit --- TP_13/exo1/Makefile | 2 +- TP_13/exo1/lib/array.c | 13 +++++-- TP_13/exo1/lib/array.h | 2 +- TP_13/exo1/lib/io.c | 86 ++++++++++++++++++++++++++++++++++++++---- TP_13/exo1/lib/io.h | 8 +++- TP_13/exo1/lib/sort.c | 2 +- TP_13/exo1/lib/utils.c | 10 +++++ TP_13/exo1/lib/utils.h | 2 + TP_13/exo1/src/main.c | 36 ++++++++++++++---- 9 files changed, 139 insertions(+), 22 deletions(-) diff --git a/TP_13/exo1/Makefile b/TP_13/exo1/Makefile index 791c7d4..fd95878 100644 --- a/TP_13/exo1/Makefile +++ b/TP_13/exo1/Makefile @@ -50,7 +50,7 @@ OPTI_FLAG = -O3 endif # Putting header files in the source directory is not the purpose of this INCLUDES variable -INCLUDES := $(INCLUDES) -I$(SRC_PATH) -I$(LIBRARY_PATH) +INCLUDES := $(INCLUDES) -I$(LIBRARY_PATH) CFLAGS := $(CFLAGS) $(WARN_FLAGS) $(STD_FLAG) $(OPTI_FLAG) $(DEBUG_FLAG) $(INCLUDES) LIBCFLAGS := -fPIC $(CFLAGS) LDFLAGS := $(LDFLAGS) $(STRIP_FLAG) diff --git a/TP_13/exo1/lib/array.c b/TP_13/exo1/lib/array.c index d2e6182..ec612c1 100644 --- a/TP_13/exo1/lib/array.c +++ b/TP_13/exo1/lib/array.c @@ -1,4 +1,5 @@ #include +#include #include "array.h" @@ -21,17 +22,23 @@ void free_tab(int tab[]) { static void copy_tab(int src_tab[], int dest_tab[], unsigned src_tab_size, unsigned index_offset) { /* FIXME: I think it's worth doing some sanity checks on the array size: * dest_tab_size >= src_tab_size */ + if (src_tab == NULL || dest_tab == NULL) { + printf("please ensure you have created both arrays beforehand\n"); + return; + } for (unsigned i = 0; i < src_tab_size; i++) { dest_tab[i + index_offset] = src_tab[i]; } } -int* concat_tab(int tab1[], unsigned tab_size1, int tab2[], unsigned tab_size2, int tab_dest[]) { - int* rt = create_tab(tab_dest, tab_size1 + tab_size2); +/* one must free the two source tabs in case they will be unused after to concatenation */ +int* concat_tab(int tab1[], unsigned tab_size1, int tab2[], unsigned tab_size2) { + int* tab_dest = NULL; + tab_dest = create_tab(tab_dest, tab_size1 + tab_size2); copy_tab(tab1, tab_dest, tab_size1, 0); copy_tab(tab2, tab_dest, tab_size2, tab_size1); - return rt; + return tab_dest; } int* resize_tab(int tab[], unsigned new_tab_size) { diff --git a/TP_13/exo1/lib/array.h b/TP_13/exo1/lib/array.h index 18596b2..efdb488 100644 --- a/TP_13/exo1/lib/array.h +++ b/TP_13/exo1/lib/array.h @@ -5,7 +5,7 @@ int* create_tab(int tab[], unsigned tab_size); void free_tab(int tab[]); -int* concat_tab(int tab1[], unsigned tab_size1, int tab2[], unsigned tab_size2, int tab_dest[]); +int* concat_tab(int tab1[], unsigned tab_size1, int tab2[], unsigned tab_size2); int* resize_tab(int tab[], unsigned tab_size); int count_tab_element(int tab[], unsigned tab_size, int element); void sort_tab(int tab[], unsigned tab_size, criteria_cb criteria); diff --git a/TP_13/exo1/lib/io.c b/TP_13/exo1/lib/io.c index 1217750..989e746 100644 --- a/TP_13/exo1/lib/io.c +++ b/TP_13/exo1/lib/io.c @@ -1,7 +1,9 @@ #include +#include #include "io.h" #include "array.h" +#include "utils.h" int prompt_value(const char* msg, int* result) { puts(msg); @@ -15,21 +17,89 @@ int* prompt_array(int array[], unsigned* size) { for (unsigned i = 0; i < *size; i++) { errno += prompt_value("Valeur?", &array[i]); } - if (errno == 0) { - return array; - } else { - return NULL; + /* error might have occured */ + handle_prompt_error(errno); + return array; +} + +void display_choice_menu() { + printf("\n=== Menu ===\n\n"); + printf("1) Saisir puis concatener un autre tableau.\n"); + printf("2) Trier le tableau.\n"); + printf("3) Afficher le tableau.\n"); + printf("4) Compter le nombre d'occurence d'un entier dans le tableau.\n"); + printf("5) Quitter.\n"); +} + +int* do_concat(int array[], unsigned* size) { + int* tab_to_concat = NULL; + unsigned tab_to_concat_size = 0; + printf("\n=== Saisie d'un tableau ===\n\n"); + tab_to_concat = prompt_array(tab_to_concat, &tab_to_concat_size); + int* tab_concat = concat_tab(array, *size, tab_to_concat, tab_to_concat_size); + *size += tab_to_concat_size; + free_tab(array); + free_tab(tab_to_concat); + return tab_concat; +} + +void do_sort(int array[], unsigned size) { + int errno = 0; + int choice = 0; + bool done = false; + criteria_cb criteria; + + printf("\n=== Menu de tri ===\n\n"); + printf("1) Croissant.\n"); + printf("2) Decroissant.\n"); + printf("3) Croissant pairs en premier.\n"); + printf("4) Croissant impairs en premier.\n"); + do { + errno = prompt_value("Choix?", &choice); + handle_prompt_error(errno); + done = true; + if (1 > choice || 4 < choice) { + printf("\nFaire un choix compris entre 1 et 4\n"); + done = false; + } + } while (!done); + switch (choice) { + case 1: + criteria = ascending; + break; + case 2: + criteria = descending; + break; + case 3: + criteria = ascending_and_even; + break; + case 4: + criteria = ascending_and_odd; + break; + default: + criteria = ascending; + break; } + sort_tab(array, size, criteria); +} + +void do_count(int array[], unsigned size) { + int errno = 0; + int search_value = 0; + + errno = prompt_value("\nValeur a chercher?", &search_value); + handle_prompt_error(errno); + printf("La valeur %d est presente %d fois dans le tableau\n", search_value, count_tab_element(array, size, search_value)); } -void display_array(int* array, int size) { +void display_array(int array[], unsigned size) { if (array != NULL) { - printf("--array begin--\n"); - for (int i = 0; i < size; i++) { + printf("\n--array begin--\n"); + for (unsigned i = 0; i < size; i++) { printf("value in array at index[%d]=%d\n", i, array[i]); } printf("--array end--\n"); } else { - printf("--array NULL--\n"); + printf("\n--array NULL--\n"); } } diff --git a/TP_13/exo1/lib/io.h b/TP_13/exo1/lib/io.h index 21a33e0..13f14e0 100644 --- a/TP_13/exo1/lib/io.h +++ b/TP_13/exo1/lib/io.h @@ -4,6 +4,12 @@ int prompt_value(const char* msg, int* result); int* prompt_array(int array[], unsigned* size); -void display_array(int* array, int size); +void display_choice_menu(); + +int* do_concat(int array[], unsigned* size); +void do_sort(int array[], unsigned size); +void do_count(int array[], unsigned size); + +void display_array(int array[], unsigned size); #endif /* IO_H */ diff --git a/TP_13/exo1/lib/sort.c b/TP_13/exo1/lib/sort.c index f8917ea..01a742f 100644 --- a/TP_13/exo1/lib/sort.c +++ b/TP_13/exo1/lib/sort.c @@ -30,7 +30,7 @@ static bool sort_first(int* array, unsigned length, criteria_cb criteria) { return rt; } -/* this function is awaited in the array.c file */ +/* the feature of this function is awaited in the array.c file */ void sort_bubble_array(int* array, unsigned length, criteria_cb criteria) { bool rt; do { diff --git a/TP_13/exo1/lib/utils.c b/TP_13/exo1/lib/utils.c index 04a20e4..fbd7e01 100644 --- a/TP_13/exo1/lib/utils.c +++ b/TP_13/exo1/lib/utils.c @@ -1,3 +1,5 @@ +#include + #include "utils.h" void swap_int(int* v1, int* v2) { @@ -11,3 +13,11 @@ void swap_ptr(void* v1, void* v2) { v1 = v2; v2 = tmp; } + +void handle_prompt_error(int errno) { + if (errno != 0) { + printf("\nMerci de saisir un nombre entier, exiting\n"); + /* it's somewhat violent but better than looping forever */ + exit(EXIT_FAILURE); + } +} diff --git a/TP_13/exo1/lib/utils.h b/TP_13/exo1/lib/utils.h index 03f1226..fe3fa08 100644 --- a/TP_13/exo1/lib/utils.h +++ b/TP_13/exo1/lib/utils.h @@ -6,4 +6,6 @@ void swap_int(int* v1, int* v2); void swap_ptr(void* v1, void* v2); +void handle_prompt_error(int errno); + #endif /* UTILS_H */ diff --git a/TP_13/exo1/src/main.c b/TP_13/exo1/src/main.c index ea4abc3..e747218 100644 --- a/TP_13/exo1/src/main.c +++ b/TP_13/exo1/src/main.c @@ -8,16 +8,38 @@ int main() { int* tab = NULL; unsigned tab_size = 0; + int errno = 0; + int choice = 0; + printf("=== Saisie initiale ===\n\n"); tab = prompt_array(tab, &tab_size); - printf("%d\n", tab_size); - - display_array(tab, tab_size); - - sort_tab(tab, tab_size, ascending_and_odd); - - display_array(tab, tab_size); + do { + display_choice_menu(); + errno = prompt_value("Choix?", &choice); + handle_prompt_error(errno); + if (1 > choice || 5 < choice) { + printf("\nFaire un choix compris entre 1 et 5\n"); + continue; + } + switch (choice) { + case 1: + tab = do_concat(tab, &tab_size); + break; + case 2: + do_sort(tab, tab_size); + break; + case 3: + display_array(tab, tab_size); + break; + case 4: + do_count(tab, tab_size); + break; + default: + /* do nothing, unused code path */ + break; + } + } while (choice != 5); free_tab(tab); exit(EXIT_SUCCESS); -- 2.34.1