changeset 275:68fd7fba64ef

Added sorting possibility, cleaned up output.
author Matti Hamalainen <ccr@tnsp.org>
date Sat, 16 Jun 2007 12:09:09 +0000
parents cc2ebbd38ba6
children 69b29ecdc6fb
files mapstats.c
diffstat 1 files changed, 113 insertions(+), 12 deletions(-) [+]
line wrap: on
line diff
--- a/mapstats.c	Sat Jun 16 10:54:02 2007 +0000
+++ b/mapstats.c	Sat Jun 16 12:09:09 2007 +0000
@@ -6,13 +6,29 @@
 #include "maputils.h"
 #include "th_args.h"
 #include "th_string.h"
+#include <string.h>
 
+typedef int (*compareFunc)(const void *, const void *);
+
+enum {
+	SORT_NONE,
+	SORT_NAME,
+	SORT_SYMBOL,
+	SORT_AMOUNT
+};
 
 char	*srcFilename = NULL,
 	*destFilename = NULL;
 
 BOOL	optUseOldFormat = FALSE,
-	optInputIsDiff = FALSE;
+	optInputIsDiff = FALSE,
+	optSortBy = SORT_NONE;
+
+
+typedef struct {
+	ulint_t	n;
+	int piece;
+} statpiece_t;
 
 	
 /* Arguments
@@ -24,6 +40,7 @@
 	{ 3, 'd', "input-diff",	"Input is a diff", OPT_NONE },
 	{ 4, 'O', "old-format",	"Input using old symbols/colors", OPT_NONE },
 	{ 5, 'o', "output",	"Output filename", OPT_ARGREQ },
+	{ 6, 's', "sort",	"Sort (by name,symbol,amount)", OPT_ARGREQ },
 };
 
 const int optListN = (sizeof(optList) / sizeof(optarg_t));
@@ -67,6 +84,21 @@
 		THMSG(2, "Output file set to '%s'.\n", destFilename);
 		break;
 	
+	case 6:
+		if (!strncmp(optArg, "n", 1))
+			optSortBy = SORT_NAME;
+		else if (!strncmp(optArg, "s", 1))
+			optSortBy = SORT_SYMBOL;
+		else if (!strncmp(optArg, "a", 1))
+			optSortBy = SORT_AMOUNT;
+		else {
+			THERR("Unknown sorting method name '%s'!\n", optArg);
+			exit(1);
+		}
+		
+		THMSG(2, "Sorting via method %d\n", optSortBy);
+		break;
+	
 	default:
 		THERR("Unknown option '%s'.\n", currArg);
 		return FALSE;
@@ -89,18 +121,54 @@
 }
 
 
+int compareByName(const void *p1, const void *p2)
+{
+	statpiece_t *vp1 = (statpiece_t *) p1, *vp2 = (statpiece_t *) p2;
+
+	if (optUseOldFormat)
+		return strcmp(mapPieces[vp1->piece].oldDesc, mapPieces[vp2->piece].oldDesc);
+	else
+		return strcmp(mapPieces[vp1->piece].desc, mapPieces[vp2->piece].desc);
+}
+
+
+int compareBySymbol(const void *p1, const void *p2)
+{
+	statpiece_t *vp1 = (statpiece_t *) p1, *vp2 = (statpiece_t *) p2;
+
+	if (optUseOldFormat)
+		return strcmp(mapPieces[vp1->piece].oldDesc, mapPieces[vp2->piece].oldDesc);
+	else
+		return strcmp(mapPieces[vp1->piece].desc, mapPieces[vp2->piece].desc);
+}
+
+
+int compareByAmount(const void *p1, const void *p2)
+{
+	statpiece_t *vp1 = (statpiece_t *) p1, *vp2 = (statpiece_t *) p2;
+
+	if (vp1->n < vp2->n)
+		return -1;
+	else if (vp1->n > vp2->n)
+		return 1;
+	else
+		return 0;
+}
+
+
 /* Main program
  */
 int main(int argc, char *argv[])
 {
 	FILE *outFile;
 	mapblock_t *map;
-	int x, y;
+	int i, x, y;
 	char *d;
-	ulint_t statTotal, statUnknown, statPieces[nmapPieces];
+	ulint_t statTotal, statUnknown;
+	statpiece_t statPieces[nmapPieces];
 
 	/* Initialize */
-	th_init("mapstats", "ASCII map statistics generator", "0.1", NULL, NULL);
+	th_init("mapstats", "ASCII map statistics generator", "0.2", NULL, NULL);
 	th_verbosityLevel = 1;
 	
 	/* Parse arguments */
@@ -125,7 +193,10 @@
 	THMSG(1, "Analyzing %dx%d area ...\n",
 		map->w, map->h);
 	
-	th_memset(statPieces, 0, sizeof(statPieces));
+	for (i = 0; i < nmapPieces; i++) {
+		statPieces[i].n = 0;
+		statPieces[i].piece = i;
+	}
 	statTotal = statUnknown = 0;
 	
 	d = map->d;
@@ -133,7 +204,7 @@
 	for (x = 0; x < map->w; x++) {
 		int c;
 		if ((c = mcGet(*d, optUseOldFormat)) >= 0) {
-			statPieces[c]++;
+			statPieces[c].n++;
 		} else {
 			statUnknown++;
 		}
@@ -141,6 +212,23 @@
 		d++;
 	}
 	
+	/* Sort results, if needed */
+	if (optSortBy != SORT_NONE) {
+		compareFunc tmpFunc;
+		
+		THMSG(2, "Sorting results ...\n");
+		switch (optSortBy) {
+		case SORT_NAME: tmpFunc = compareByName; break;
+		case SORT_SYMBOL: tmpFunc = compareBySymbol; break;
+		case SORT_AMOUNT: tmpFunc = compareByAmount; break;
+		default:
+			THERR("Internal error, no sort function for sort type %d.\n", optSortBy);
+			exit(2);
+			break;
+		}
+		qsort(statPieces, nmapPieces, sizeof(statpiece_t), tmpFunc);
+	}
+	
 	/* Open output file */
 	if (destFilename == NULL)
 		outFile = stdout;
@@ -150,12 +238,25 @@
 		exit(1);
 	}
 	
-	for (x = 0; x < nmapPieces; x++) {
-		fprintf(outFile, " %-20s [%c]: %6ld (%1.3f%%)\n",
-			mapPieces[x].desc,
-			mapPieces[x].symbol,
-			statPieces[x],
-			(statPieces[x] * 100.0f / statTotal));
+	for (i = 0; i < nmapPieces; i++) {
+		int p = statPieces[i].piece;
+		char *desc, symbol;
+		
+		if (optUseOldFormat) {
+			desc = mapPieces[p].oldDesc;
+			symbol = mapPieces[p].oldSymbol;
+		} else {
+			desc = mapPieces[p].desc;
+			symbol = mapPieces[p].symbol;
+		}
+		
+		if (symbol >= 0) {
+			fprintf(outFile, " %-20s [%c]: %6ld (%1.3f%%)\n",
+			desc,
+			symbol,
+			statPieces[i].n,
+			(statPieces[i].n * 100.0f / statTotal));
+		}
 	}
 	
 	fprintf(outFile, " %ld total, %ld unknown.\n",