Skip to content

Instantly share code, notes, and snippets.

@zmackie
Last active February 25, 2017 21:39
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save zmackie/b936908dc2b74814a904b542efd60cd2 to your computer and use it in GitHub Desktop.
Save zmackie/b936908dc2b74814a904b542efd60cd2 to your computer and use it in GitHub Desktop.
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
void die(const char *message)
{
if (errno) {
perror(message);
} else {
printf("ERROR: %s\n", message);
}
exit(1);
}
void swap(int *a, int *b)
{
int temp = *a;
*a = *b;
*b = temp;
}
typedef int (*compare_cb) (int a, int b);
typedef int *(*sort_func) (int *numbers, int count, compare_cb cmp);
int *bubble_sort(int *numbers, int count, compare_cb cmp)
{
int *target = malloc(count * sizeof(int));
if (!target)
die("Memory error");
memcpy(target, numbers, count * sizeof(int));
for (int i = 0; i < count; i++) {
for (int j = 0; j < count - 1; j++) {
if (cmp(target[j], target[j + 1]) > 0) {
swap(&target[j], &target[j + 1]);
}
}
}
return target;
}
int partition(int target[], int low, int high)
{
int i;
int p_index;
int firsthigh;
int cur;
int below_p;
p_index = high;
int p_value = target[p_index];
firsthigh = low;
for (i = low; i < high; i++) {
cur = target[i];
below_p = cur < p_value;
if (below_p) {
swap(&target[i], &target[firsthigh]);
firsthigh ++;
}
}
swap(&target[p_index], &target[firsthigh]);
return(firsthigh);
}
void quicksort(int *target, int low, int high)
{
int partition_index;
// Base case
int inbounds = (high - low) > 0;
if (inbounds) {
partition_index = partition(target, low, high);
quicksort(target, low, partition_index-1);
quicksort(target, partition_index+1, high);
}
}
int *do_quick_sort(int *numbers, int count, compare_cb cmp)
{
int *target = malloc(count * sizeof(int));
if (!target)
die("Memory error");
memcpy(target, numbers, count * sizeof(int));
quicksort(target, 0, count-1);
return target;
}
int sorted_order(int a, int b)
{
int a_larger = (a > b); // 1 or 0
int b_larger = (a < b); //1 or 0
return a_larger - b_larger; // 1-0, 0-1, 0
}
int reverse_sorted(int a, int b)
{
int a_larger = (a > b); // 1 or 0
int b_larger = (a < b); //1 or 0
// 0-1, 1-0, 0 (but the reverse of above for a given test
return b_larger - a_larger ;
}
int strang_order(int a, int b)
{
if (a == 0 || b == 0) {
return 0;
} else {
return a % b;
}
}
void test_sorting(int *numbers, int count, sort_func sort, compare_cb cmp)
{
int i = 0;
int *sorted = sort(numbers, count, cmp);
if (!sorted)
die("Failed to sort as requested");
for (i = 0; i < count; i++) {
printf("%d\n", sorted[i]);
}
printf("\n");
free(sorted);
}
int main(int argc, char const* argv[])
{
if (argc < 2) die("USAGE: ex18 4 3 1 5 6");
int count = argc - 1;
int i = 0;
const char **inputs = argv + 1;
int *numbers = malloc(count * sizeof(int));
if (!numbers) die("Memory error");
for (i = 0; i < count; i++) {
numbers[i] = atoi(inputs[i]);
}
printf("BubbleSort:\n");
test_sorting(numbers, count, bubble_sort, sorted_order);
test_sorting(numbers, count, bubble_sort, reverse_sorted);
test_sorting(numbers, count, bubble_sort, strang_order);
printf("Quicksort\n");
test_sorting(numbers, count, do_quick_sort, sorted_order);
test_sorting(numbers, count, do_quick_sort, reverse_sorted);
test_sorting(numbers, count, do_quick_sort, strang_order);
free(numbers);
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment