]> git.pond.sub.org Git - empserver/commitdiff
Add performance statistics to path finder
authorMarkus Armbruster <armbru@pond.sub.org>
Mon, 21 Feb 2011 21:30:41 +0000 (22:30 +0100)
committerMarkus Armbruster <armbru@pond.sub.org>
Tue, 12 Apr 2011 19:51:31 +0000 (21:51 +0200)
New function path_find_print_stats() prints a few numbers of interest
when compiled with PATH_FIND_STATS defined.

include/path.h
src/lib/common/pathfind.c
src/lib/update/finish.c

index 3b0cc495e1223c973284b7be0a75c9e0becf9499..15ae099d66229a8ec4678e470df1fa2fce69b166 100644 (file)
@@ -73,6 +73,11 @@ extern void path_find_from(coord, coord, natid, int);
 extern double path_find_to(coord, coord);
 extern double path_find(coord, coord, coord, coord, natid, int);
 extern size_t path_find_route(char *, size_t, coord, coord, coord, coord);
+#ifdef PATH_FIND_STATS
+extern void path_find_print_stats(void);
+#else
+#define path_find_print_stats() ((void)0)
+#endif
 
 /* src/lib/common/path.c */
 extern char *BestDistPath(char *, struct sctstr *, struct sctstr *,
index dd6aa0eb2bae1fb31ad8401ef42e5d668fc09a37..a7f9636182f8779a39e7e3aeaa17a66e4ae7ac7a 100644 (file)
@@ -52,6 +52,8 @@ static char *bufrotate(char *buf, size_t bufsz, size_t i);
 /*
  * Dijkstra's algorithm.  Refer to your graph algorithm textbook for
  * how it works.  Implementation is specialized to hex maps.
+ *
+ * Define PATH_FIND_STATS for performance statistics on stdout.
  */
 
 /*
@@ -112,6 +114,22 @@ static int pf_suid;
 static natid pf_actor;
 static double (*pf_sct_cost)(natid, int);
 
+/*
+ * Performance statistics
+ */
+#ifdef PATH_FIND_STATS
+static unsigned pf_nsearch, pf_nsource, pf_nopen, pf_nclose;
+static unsigned pf_nheap_max, pf_noway;
+static double pf_sumcost;
+#define STAT_INC(v) ((void)((v)++))
+#define STAT_INCBY(v, i) ((void)((v) += i))
+#define STAT_HIMARK(v, h) ((void)((v) < (h) ? (v) = (h) : (h)))
+#else  /* !PATH_FIND_STATS */
+#define STAT_INC(v) ((void)0)
+#define STAT_INCBY(v, i) ((void)0)
+#define STAT_HIMARK(v, h) ((void)0)
+#endif /* !PATH_FIND_STATS */
+
 #ifndef NDEBUG                 /* silence "not used" warning */
 /* Is sector with uid UID open?  */
 static int
@@ -224,7 +242,9 @@ pf_open(int uid, coord x, coord y, int dir, double cost)
 {
     int i;
 
+    STAT_INC(pf_nopen);
     i = pf_nheap++;
+    STAT_HIMARK(pf_nheap_max, (unsigned)pf_nheap);
     DPRINTF("pf: open %d,%d %g %c %d\n", x, y, cost, dirch[dir], i);
     assert(pf_is_unvisited(uid));
     pf_map[uid].visit = pf_visit;
@@ -248,6 +268,7 @@ pf_close(void)
 {
     int uid = pf_heap[0].uid;
 
+    STAT_INC(pf_nclose);
     DPRINTF("pf: close %d,%d %d\n", pf_heap[0].x, pf_heap[0].y, pf_nheap);
     assert(pf_is_open(uid));
     if (--pf_nheap) {
@@ -305,6 +326,7 @@ rev_dir(int dir)
 static void
 pf_set_source(coord sx, coord sy, natid actor, double (*cost)(natid, int))
 {
+    STAT_INC(pf_nsource);
     DPRINTF("pf: source %d,%d\n", sx, sy);
     pf_sx = sx;
     pf_sy = sy;
@@ -339,10 +361,12 @@ path_find_to(coord dx, coord dy)
     double cost, c1;
     coord x, y, nx, ny;
 
+    STAT_INC(pf_nsearch);
     DPRINTF("pf: dest %d,%d\n", dx, dy);
     duid = XYOFFSET(dx, dy);
     if (pf_is_closed(duid)) {
        DPRINTF("pf: done old %g\n", pf_map[duid].cost);
+       STAT_INCBY(pf_sumcost, pf_map[duid].cost);
        return pf_map[duid].cost;
     }
 
@@ -373,8 +397,11 @@ path_find_to(coord dx, coord dy)
     }
 
     DPRINTF("pf: done new %g\n", !pf_nheap ? -1.0 : pf_map[duid].cost);
-    if (!pf_nheap)
+    if (!pf_nheap) {
+       STAT_INC(pf_noway);
        return -1.0;
+    }
+    STAT_INCBY(pf_sumcost, pf_map[duid].cost);
     return pf_map[duid].cost;
 }
 
@@ -449,6 +476,18 @@ bufrotate(char *buf, size_t bufsz, size_t i)
     return buf;
 }
 
+#ifdef PATH_FIND_STATS
+void
+path_find_print_stats(void)
+{
+    printf("pathfind %u searches, %u sources, %u opened, %u closed,"
+          " %u heap max, %zu bytes, %u noway, %g avg cost\n",
+          pf_nsearch, pf_nsource, pf_nopen, pf_nclose,
+          pf_nheap_max,
+          (WORLD_SZ() * (sizeof(*pf_map) + sizeof(*pf_heap))),
+          pf_noway, pf_nsearch ? pf_sumcost / pf_nsearch : 0.0);
+}
+#endif
 
 /*
  * Empire interface glue
index 8fc8af924e8220afc4799acf16d80934a2a64087..c502ae6493eab6b981ce5951e42be624daaa9dd1 100644 (file)
@@ -130,4 +130,5 @@ assemble_dist_paths(double *import_cost)
                                   sp->sct_x, sp->sct_y,
                                   dist->sct_own, MOB_MOVE);
     }
+    path_find_print_stats();
 }