static void dl_sort_test(void) { printsln((String)__func__); List ac, ex, as; ac = dl_of_string("5, 4, 3, 2, 1"); ex = dl_of_string("1, 2, 3, 4, 5"); as = dl_sort(ac); dl_check_within(as, ex); l_free(ac); l_free(ex); l_free(as); ac = dl_of_string("1, 2, 1, 3, 2"); ex = dl_of_string("1, 1, 2, 2, 3"); as = dl_sort(ac); dl_check_within(as, ex); l_free(ac); l_free(ex); l_free(as); ac = dl_of_string(""); ex = dl_of_string(""); as = dl_sort(ac); dl_check_within(as, ex); l_free(ac); l_free(ex); l_free(as); ac = dl_of_string("-1, -2, -3, -1"); ex = dl_of_string("-3, -2, -1, -1"); as = dl_sort(ac); dl_check_within(as, ex); l_free(ac); l_free(ex); l_free(as); }
bool print_words_to_file_and_screen(list_t *list, int number, char *output){ check(list != NULL, "list was NULL."); check(output != NULL, "output was NULL."); int total_node_count = dl_count(list); int i = 0; char *temp = NULL; int word_count = 0; FILE *output_file = NULL; if(total_node_count != 0){ check(dl_sort(list) == 1, "sort did not complete properly."); } output_file = fopen(output, "w"); check(output_file != NULL, "Could not create file for writing."); for(i = 0; i < total_node_count; i++){ temp = dl_get_back(list); word_count = dl_get_wordcount(list, temp); check(temp != NULL && word_count != 0, "Invalid word or word count. " "temp: '%s', word_count: %d", temp == NULL ? "NULL" : temp, word_count); if(i < number){ printf("%d\t%s\n", word_count, temp); } check(fprintf(output_file, "%d\t%s\n", word_count, temp) > 0, "An error occurred while writing to file."); check(dl_pop_back(list) == 1, "Did not remove back properly."); } fclose(output_file); return 1; error: if(output_file != NULL){ fclose(output_file); } return 0; }
void dl_sort(dl_t dl, size_t el_size, int(*compar)(void *, void *)) { dl_el *el, *first_head, *second_head; dl_s first_list, second_list; void *first_item, *second_item; int i, len; if (dl_length(dl) <= 25) { dl_insertion_sort(dl, el_size, compar); return; } len = dl_length(dl)/2; for (i=0, el=dl->first; i<len; i++) { el = el->next; } first_list.first = dl->first; first_list.last = el->prev; first_list.count = len; first_list.last->next = 0; second_list.first = el; second_list.last = dl->last; second_list.count = dl_length(dl)-len; second_list.first->prev = 0; dl_sort(&first_list, el_size, compar); dl_sort(&second_list, el_size, compar); /* in-place merging */ first_head = first_list.first; second_head = second_list.first; first_item = (void*)(((dl_el*)first_head)+1); second_item = (void*)(((dl_el*)second_head)+1); if (compar(first_item, second_item) <= 0) { dl->first = el = first_head; first_head = first_head->next; } else { dl->first = el = second_head; second_head = second_head->next; } while (1) { first_item = (void*)(((dl_el*)first_head)+1); second_item = (void*)(((dl_el*)second_head)+1); if (compar(first_item, second_item) <= 0) { el->next = first_head; first_head->prev = el; el = first_head; first_head = first_head->next; if (!first_head) { el->next = second_head; second_head->prev = el; dl->last = second_list.last; break; } } else { el->next = second_head; second_head->prev = el; el = second_head; second_head = second_head->next; if (!second_head) { el->next = first_head; first_head->prev = el; dl->last = first_list.last; break; } } } }