/*
 * Bubble sort a list of 10 strings
 *
 * We want the strings to persist in memory, that is why we use a 'const char*'.
 *
 */
#include <iostream>
#include <cstring>


#define LIST_SIZE 10
#define USE_PTR 1

#define VERBOSE 0

void sort( const char** A, const int size );
#if !USE_PTR
void order( const char* &a, const char* &b );
#else
void orderptr( const char* *a, const char* *b );
#endif


int main() {
	const char* list[LIST_SIZE] = { 
		"b", 
		"cccccccccc", 
		"aaabcd", 
		"axefsaf", 
		"poqkud", 
		"6xnj439yu", 
		"nullieksj", 
		"bell", 
		"uuisdjk",
		"aaaaaaa", 
	};

	// Print the original
	std::cout << "Original: ";

	for( int i = 0; i < LIST_SIZE ; i++ )
	{
		if ( i != 0 )
		{
			std::cout << ", ";
		}

		std::cout << list[i];
	}
	std::cout << std::endl;

	// sort it
	sort( list, LIST_SIZE );

	// Print it
	std::cout << "Sorted: ";
	for( int i = 0; i < LIST_SIZE ; i++ )
	{
		if ( i != 0 )
		{
			std::cout << ", ";
		}

		std::cout << list[i];
	}
	std::cout << std::endl;

	return 0;
}

void sort( const char** A, const int size ) {
	for ( int i = 0 ; i < size ; i++ ) {
		for ( int j = 0 ; j < size - 1 ; j++ ) {
			#if VERBOSE
				std::cout << "SORT: " << A[i] << ", " << A[j]<< std::endl;
			#endif

			#if !USE_PTR
			order( A[ i ], A[ j ] );
			#else
			orderptr( &A[ i ], &A[ j ] );
			#endif
		}
	}
}

#if !USE_PTR
void order( const char* &a, const char* &b ) {
	#if VERBOSE
	std::cout << "Order: " << a << ", " << b << std::endl;
	#endif
	if ( strcmp( a, b ) > 0 ) {
		#if VERBOSE
		std::cout << "Ordering OK" << std::endl;
		#endif
		return;
	}
	#if VERBOSE
	std::cout << "Ordering ToDo" << std::endl;
	#endif

	const char* tmp = a;
	a = b;
	b = tmp;
}
#else
void orderptr( const char* *a, const char* *b ) {
	#if VERBOSE
	std::cout << "Order: " << a << std::endl;
	#endif
	// b is greater or equal to a, do nothing
	if ( strcmp(*a, *b) > 0) {
		#if VERBOSE
		std::cout << "Ordering OK" << std::endl;
		#endif
		return;
	}
	#if VERBOSE
	std::cout << "Ordering ToDo" << std::endl;
	#endif

	const char* tmp = *a;
	*a = *b;
	*b = tmp;
}
#endif
