#include "array.h"
#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

array::array(int numberofcounters)
{
	assert(numberofcounters >= 1);

	counters = NULL;
	ncounters = numberofcounters;
	strings = NULL;
	nin = 0;
}

array::~array()
{
	if (counters)
		free(counters);

	if (strings)
		free(strings);
}

void array::setcounter(int index, int subindex, int value)
{
	counters[(index * ncounters) + subindex] = value;
}

int array::addcounter(int index, int subindex, int value)
{
	return counters[(index * ncounters) + subindex] += value;
}

int array::getcounter(int index, int subindex)
{
	return counters[(index * ncounters) + subindex];
}

int array::addstring(char *string, int defvalue)
{
	int loop;

	for(loop=0; loop<nin; loop++)
	{
		if (strcasecmp(strings[loop], string) == 0)
		{
			(void)addcounter(loop, 0, 1);
			return loop;
		}
	}

	int index = addelement(string);
	setcounter(index, 0, defvalue);

	return index;
}

int array::addelement(char *string)
{
	strings = (char **)realloc(strings, sizeof(char *) * (nin + 1));
	if (!strings)
	{
		fprintf(stderr, "realloc problem\n");
		exit(1);
	}
	counters = (long int *)realloc(counters, sizeof(long int) * ncounters * (nin + 1));
	if (!counters)
	{
		fprintf(stderr, "realloc problem\n");
		exit(1);
	}

	strings[nin] = strdup(string);
	for(int loop=0; loop<ncounters; loop++)
		setcounter(nin, loop, 0);

	nin++;

	return nin-1;
}

void array::sort(int subindex)
{
	assert(subindex < ncounters);

	do_sort(subindex, 0, nin);
}

void array::do_sort(int subindex, int start, int end)
{
	for(int loop=start; loop<(end-1); loop++)
	{
		for(int loop2=loop+1; loop2<end; loop2++)
		{
			if (getcounter(loop, subindex) < getcounter(loop2, subindex))
			{
				swap_entry(loop, loop2);
			}
			else if (getcounter(loop, subindex) == getcounter(loop2, subindex) && ncounters > 1)
			{
				int dummy = (subindex + 1) % ncounters;
				if (getcounter(loop, dummy) < getcounter(loop2, dummy))
					swap_entry(loop, loop2);
			}
		}
	}
}

void array::swap_entry(int index1, int index2)
{
	char *dummy = strings[index1];
	strings[index1] = strings[index2];
	strings[index2] = dummy;

	for(int loop=0; loop<ncounters; loop++)
	{
		int dummy = getcounter(index1, loop);
		setcounter(index1, loop, getcounter(index2, loop));
		setcounter(index2, loop, dummy);
	}
}


syntax highlighted by Code2HTML, v. 0.9.1