Index: src/Common/Stats/Base.h
===================================================================
--- src/Common/Stats/Base.h	(revision 8e70823920df10bf60abd7a63291bfdbcf88c901)
+++ src/Common/Stats/Base.h	(revision 8e70823920df10bf60abd7a63291bfdbcf88c901)
@@ -0,0 +1,61 @@
+#pragma once
+
+#include <string>
+
+namespace Stats {
+	namespace Base {
+		class TreeImpl {
+		public:
+			struct Top {
+				TreeImpl * head = nullptr;
+				TreeImpl * tail = nullptr;
+
+				void append(TreeImpl * node) {
+					if(!head) { head = node; }
+					else      { tail->next = node;}
+					tail = node;
+				}
+			};
+
+			virtual void print(std::ostream &) = 0;
+
+			const std::string name;
+			TreeImpl(const std::string & name) : name(name) {}
+
+		protected:
+			virtual ~TreeImpl() = default;
+
+			TreeImpl * next = nullptr;
+			Top children;
+
+			template<typename func_t>
+			friend void ForAll(TreeImpl::Top & range, size_t level, func_t func, bool destroy = false);
+		};
+
+		template<typename func_t>
+		inline void ForAll(TreeImpl::Top & range, size_t level, func_t func, bool destroy) {
+			auto it = range.head;
+			while(it) {
+				auto next = it->next;
+				func(it, level);
+				ForAll(it->children, level + 1, func);
+				if(destroy) delete it;
+				it = next;
+			}
+		}
+
+		template<TreeImpl::Top & top>
+		class Tree : public TreeImpl {
+		public:
+			Tree(const std::string & name) : TreeImpl{name} {
+				top.append(this);
+			}
+
+			Tree(const std::string & name, Tree * parent) : TreeImpl{name} {
+				parent->children.append(this);
+			}
+		protected:
+			virtual ~Tree() = default;
+		};
+	}
+}
Index: src/Common/Stats/Counter.cc
===================================================================
--- src/Common/Stats/Counter.cc	(revision 79de2210c8863a3cdcf96bdb85b53eb25fd7baca)
+++ src/Common/Stats/Counter.cc	(revision 8e70823920df10bf60abd7a63291bfdbcf88c901)
@@ -18,39 +18,28 @@
 #include <algorithm>
 #include <cstring>
+#include <functional>
 #include <iomanip>
 
 namespace Stats {
 	namespace Counters {
-
-		template<typename T>
-		void ForAllCounters(BaseCounter::list_t & range, size_t level, T func) {
-			auto it = range.head;
-			while(it) {
-				auto next = it->next;
-				func(it, level);
-				ForAllCounters(it->children, level + 1, func);
-				it = next;
-			}
-		}
-
 		void print() {
-			if(!BaseCounter::top.head) return;
+			if(!top.head) return;
 			size_t nc = 0;
-			ForAllCounters(BaseCounter::top, 0, [&](BaseCounter * node, size_t level) {
-				nc = std::max(nc, (4 * level) + std::strlen(node->name));
+			Base::ForAll(top, 0, [&](Base::TreeImpl * node, size_t level) {
+				nc = std::max(nc, (4 * level) + node->name.size());
 			});
 
-			const char * const title = "Counter Statistic";
+			const std::string & title = "Counter Statistic";
 			size_t nct = nc + 14;
 			std::cerr << std::string(nct, '=') << std::endl;
-			std::cerr << std::string((nct - std::strlen(title)) / 2, ' ');
+			std::cerr << std::string((nct - title.size()) / 2, ' ');
 			std::cerr << title << std::endl;
 			std::cerr << std::string(nct, '-') << std::endl;
 
 
-			ForAllCounters(BaseCounter::top, 0, [&](BaseCounter * node, size_t level) {
+			Base::ForAll(top, 0, [&](Base::TreeImpl * node, size_t level) {
 				std::cerr << std::string(level * 4, ' ');
 				std::cerr << node->name;
-				std::cerr << std::string(nc - ((level * 4) + std::strlen(node->name)), ' ');
+				std::cerr << std::string(nc - ((level * 4) + node->name.size()), ' ');
 				std::cerr << " | ";
 				std::cerr << std::setw(9);
@@ -58,11 +47,10 @@
 				std::cerr << " |";
 				std::cerr << '\n';
-				delete node;
-			});
+			}, true);
 
 			std::cerr << std::string(nct, '-') << std::endl;
 		}
 
-		BaseCounter::list_t BaseCounter::top;
+		Base::TreeImpl::Top top;
 	}
 }
Index: src/Common/Stats/Counter.h
===================================================================
--- src/Common/Stats/Counter.h	(revision 79de2210c8863a3cdcf96bdb85b53eb25fd7baca)
+++ src/Common/Stats/Counter.h	(revision 8e70823920df10bf60abd7a63291bfdbcf88c901)
@@ -18,4 +18,7 @@
 #include <cstdint>
 #include <iostream>
+#include <string>
+
+#include "Common/Stats/Base.h"
 
 namespace Stats {
@@ -23,63 +26,22 @@
 		void print();
 
-		class BaseCounter {
+		extern Base::TreeImpl::Top top;
+
+		class CounterGroup : public Base::Tree<top> {
 		public:
-			BaseCounter(const char * const name) : name(name) {
-				top.append(this);
-			}
+			CounterGroup(const std::string & name ) : Base::Tree<top>(name) {}
+			CounterGroup(const std::string & name, Base::Tree<top> * parent) : Base::Tree<top>(name, parent) {}
 
-			BaseCounter(const char * const name, BaseCounter * parent) : name(name) {
-				parent->children.append(this);
-			}
+			virtual void print(std::ostream & os) override { os << ""; }
 		protected:
-			virtual ~BaseCounter() = default;
-
-			struct list_t {
-				BaseCounter * head = nullptr;
-				BaseCounter * tail = nullptr;
-
-				void append(BaseCounter * node) {
-					if(!head) { head = node; }
-					else      { tail->next = node;}
-					tail = node;
-				}
-			};
-
-		private:
-			virtual void print(std::ostream &) = 0;
-			template<typename T>
-			friend void ForAllCounters(BaseCounter::list_t &, size_t, T );
-			friend void print();
-
-		private:
-			const char * const name;
-
-			BaseCounter * next = nullptr;
-			list_t children;
-
-			static list_t top;
+			virtual ~CounterGroup() = default;
 		};
 
-		class CounterGroup : public BaseCounter {
+		class SimpleCounter : public Base::Tree<top> {
 		public:
-			CounterGroup(const char * const name ) : BaseCounter(name) {}
-			CounterGroup(const char * const name, BaseCounter * parent) : BaseCounter(name, parent) {}
+			SimpleCounter(const std::string & name ) : Base::Tree<top>(name) {}
+			SimpleCounter(const std::string & name, Base::Tree<top> * parent) : Base::Tree<top>(name, parent) {}
 
-		protected:
-			virtual ~CounterGroup() = default;
-
-		private:
-			virtual void print(std::ostream & os) {
-				os << "";
-			}
-			template<typename T>
-			friend void ForAllCounters(BaseCounter::list_t &, size_t, T );
-			friend void print();
-		};
-
-		class SimpleCounter : public BaseCounter {
-		public:
-			SimpleCounter(const char * const name ) : BaseCounter(name) {}
-			SimpleCounter(const char * const name, BaseCounter * parent) : BaseCounter(name, parent) {}
+			virtual void print(std::ostream & os) override { os << count; }
 
 			inline void operator++(int)          { count++;        }
@@ -89,20 +51,14 @@
 
 		private:
-			virtual void print(std::ostream & os) {
-				os << count;
-			}
-			template<typename T>
-			friend void ForAllCounters(BaseCounter::list_t &, size_t, T );
-			friend void print();
-
 			size_t count = 0;
-
 		};
 
 		template<typename T>
-		class AverageCounter : public BaseCounter {
+		class AverageCounter : public Base::Tree<top> {
 		public:
-			AverageCounter(const char * const name ) : BaseCounter(name), sum{} {}
-			AverageCounter(const char * const name, BaseCounter * parent) : BaseCounter(name, parent), sum{} {}
+			AverageCounter(const std::string & name ) : Base::Tree<top>(name), sum{} {}
+			AverageCounter(const std::string & name, Base::Tree<top> * parent) : Base::Tree<top>(name, parent), sum{} {}
+
+			virtual void print(std::ostream & os) { os << sum / count; }
 
 			inline void push(T value) {
@@ -115,11 +71,4 @@
 
 		private:
-			virtual void print(std::ostream & os) {
-				os << sum / count;
-			}
-			template<typename F>
-			friend void ForAllCounters(BaseCounter::list_t &, size_t, F );
-			friend void print();
-
 			T sum;
 			size_t count = 1;
@@ -127,24 +76,16 @@
 
 		template<typename T>
-		class MaxCounter : public BaseCounter {
+		class MaxCounter : public Base::Tree<top> {
 		public:
-			MaxCounter(const char * const name ) : BaseCounter(name), max{} {}
-			MaxCounter(const char * const name, BaseCounter * parent) : BaseCounter(name, parent), max{} {}
+			MaxCounter(const std::string & name ) : Base::Tree<top>(name), max{} {}
+			MaxCounter(const std::string & name, Base::Tree<top> * parent) : Base::Tree<top>(name, parent), max{} {}
 
-			inline void push(T value) {
-				max = std::max(max, value);
-			}
+			virtual void print(std::ostream & os) { os << max; }
 
+			inline void push(T value) { max = std::max(max, value); }
 		protected:
 			virtual ~MaxCounter() = default;
 
 		private:
-			virtual void print(std::ostream & os) {
-				os << max;
-			}
-			template<typename F>
-			friend void ForAllCounters(BaseCounter::list_t &, size_t, F );
-			friend void print();
-
 			T max;
 		};
