Path: utzoo!utgpu!jarvis.csri.toronto.edu!mailrus!ukma!rayssd!mirror!redsox!campbell From: campbell@redsox.bsw.com (Larry Campbell) Newsgroups: alt.sources Subject: mapstats: uucp map statistics program Message-ID: <1381@redsox.bsw.com> Date: 6 Aug 89 03:44:09 GMT Reply-To: campbell@redsox.bsw.com (Larry Campbell) Organization: The Boston Software Works, Inc. Lines: 166 Here's a little ditty I just whipped up to print interesting statistics about the uucp map. You feed it pathalias output and it tells you, for each of your neighbors, how many paths utilise that neighbor, and what the average hop count is for paths through that neighbor. It's simple, it's fast, and it lints. Too small to warrant a makefile or shar archive, here it is: ------------------------------cut here------------------------------ /* * mapstats * * Compute and print statistics about uucp connectivity. * Reads standard input, which should be in pathalias output format. * * I did this in awk originally. This runs about 100 times faster. * * Copyright (c) 1989 by Larry Campbell (campbell@redsox.bsw.com) * You may make any use of this code you wish, including selling * it, as long as you credit the author. */ #include #include #define NEW(type) ( (type *) malloc(sizeof(type)) ) #define NIL(type) ( (type) 0 ) typedef struct neighbor { char *n_name; unsigned long n_hops; unsigned long n_paths; struct neighbor *n_next; } NEIGHBOR; static NEIGHBOR *nroot; static void do_record(); static void inc_neighbor_count(); static void print_stats(); static void xabort(); static unsigned long total_paths; static unsigned long total_hops; main() { char buf[BUFSIZ]; int n; while (fgets(buf, BUFSIZ, stdin)) { n = strlen(buf); if (buf[n-1] == '\n') buf[n-1] = '\0'; do_record(buf); } print_stats(); return 0; } static void do_record(buf) char *buf; { char *p; char *neighbor; unsigned hop_count; p = strchr(buf, '\t'); if (p == NIL(char *)) xabort("missing tab: %s\n", buf); neighbor = ++p; for (hop_count = 0, p = strchr(p, '!'); p != NIL(char *); p = strchr(p, '!')) { hop_count++; *p++ = '\0'; } if (hop_count == 0) { if (strcmp(neighbor, "%s") == 0) return; xabort("bad hop count: %s\n", buf); } inc_neighbor_count(neighbor, hop_count); total_paths++; total_hops += hop_count; } static void inc_neighbor_count(name, hop_count) char *name; unsigned hop_count; { NEIGHBOR *np; /* Try to find neighbor struct */ for (np = nroot; np != NIL(NEIGHBOR *); np = np->n_next) { if (strcmp(name, np->n_name) == 0) break; } /* Make new one if needed */ if (np == NIL(NEIGHBOR *)) { NEIGHBOR *next, *prev; np = NEW(NEIGHBOR); np->n_name = strdup(name); np->n_paths = 0L; np->n_hops = 0L; np->n_next = NIL(NEIGHBOR *); /* Insert neighbor node in list lexically sorted by name */ next = nroot; prev = NIL(NEIGHBOR *); while (next != NIL(NEIGHBOR *)) { if (strcmp(name, next->n_name) < 0) break; prev = next; next = next->n_next; } if (prev == NIL(NEIGHBOR *)) nroot = np; else np->n_next = next, prev->n_next = np; /* the infamous comma */ } np->n_paths++; np->n_hops += hop_count; } static void print_stats() { NEIGHBOR *np; (void) printf("Neighbor Paths Avg hops\n"); for (np = nroot; np != NIL(NEIGHBOR *); np = np->n_next) { (void) printf("%-12s %5ld %3.1f\n", np->n_name, np->n_paths, np->n_paths == 0L ? 0.0 : (double) np->n_hops / (double) np->n_paths); } (void) printf("Total paths: %5ld\n", total_paths); } /* VARARGS1 */ static void xabort(fmt, a, b, c, d) char *fmt; { (void) fprintf(stderr, fmt, a, b, c, d); exit(1); } -- Larry Campbell The Boston Software Works, Inc. campbell@bsw.com 120 Fulton Street wjh12!redsox!campbell Boston, MA 02146