Selaa lähdekoodia

Converting tests to GoogleMock.
- Create dummy library to gain profiling data.

Sam Jaffe 7 vuotta sitten
vanhempi
commit
7a4c179fac
5 muutettua tiedostoa jossa 421 lisäystä ja 188 poistoa
  1. 0 117
      trie.t.h
  2. 257 71
      trie.xcodeproj/project.pbxproj
  3. 11 0
      trie_dummy.cpp
  4. 129 0
      trie_test.cpp
  5. 24 0
      trie_test/Info.plist

+ 0 - 117
trie.t.h

@@ -1,117 +0,0 @@
-//
-//  trie.t.h
-//  trie
-//
-//  Created by Sam Jaffe on 6/16/17.
-//
-
-#pragma once
-
-#include <cxxtest/TestSuite.h>
-
-#include "trie.hpp"
-
-class trie_TestSuite : public CxxTest::TestSuite {
-private:
-  trie<int, int> data;
-  
-  void setUp() override {
-    data.clear();
-    data = 1;
-    data[0] = 5;
-    data[{0,1}] = 4;
-    data[{0,1,0}] = 3;
-    data[{0,1,2}] = 6;
-    data[{0,2,0}] = 7;
-    data[1] = 2;
-    data[{1,1}] = 8;
-    data[{1,1,0}] = 9;
-  }
-  
-  template <typename Iter, typename R>
-  static void container_equals(Iter l_it, R const & rhs) {
-    decltype(l_it) l_end{};
-    auto r_it = std::begin(rhs), r_end = std::end(rhs);
-    auto l_size = std::distance(l_it, l_end), r_size = std::distance(r_it, r_end);
-    TS_ASSERT_EQUALS(l_size, r_size);
-    for ( ; l_it != l_end && r_it != r_end; ++l_it, ++r_it ) {
-      TS_ASSERT_EQUALS(*l_it, *r_it);
-    }
-  }
-public:
-  // Parent, Left -> Right
-  void testIterationIsPreOrder() {
-    int const expected[] = { 1, 5, 4, 3, 6, 0, 7, 2, 8, 9 };
-    container_equals(data.begin(), expected);
-  }
-  
-  // Parent, Right -> Left
-  void testPostIterationIsPostOrder() {
-    int const expected[] = { 1, 2, 8, 9, 5, 0, 7, 4, 6, 3 };
-    auto it = trie<int, int>::const_post_iterator{&data};
-    container_equals(it, expected);
-  }
-
-  // Right -> Left, Parent
-  void testReverseIterationIsInvDepthFirst() {
-    int const expected[] = { 9, 8, 2, 7, 0, 6, 3, 4, 5, 1 };
-    container_equals(data.crbegin(), expected);
-  }
-
-  void testCopyCtorIsDeepCopy() {
-    trie<int, int> copy{data};
-    TS_ASSERT_EQUALS(data, copy);
-    copy[{0, 1}] = -1;
-    TS_ASSERT_DIFFERS(data, copy);
-  }
-  
-  void testEqualsConsidersPaths() {
-    trie<int, int> t1, t2;
-    t1[1] = 1;
-    t2[2] = 1;
-    TS_ASSERT_DIFFERS(t1, t2);
-  }
-  
-  void testInsertNewElementOutputsTrue() {
-    trie<int, int> test;
-    auto pair = test.insert(1, 2);
-    TS_ASSERT_EQUALS(*pair.first, 2);
-    TS_ASSERT(pair.second);
-  }
-
-  void testEmplaceNewElementOutputsTrue() {
-    trie<int, int> test;
-    auto pair = test.emplace(1, 2);
-    TS_ASSERT_EQUALS(*pair.first, 2);
-    TS_ASSERT(pair.second);
-  }
-
-  void testInsertArrayOfElementCreatesAllEntries() {
-    trie<int, int> test;
-    auto pair = test.insert({1, 1, 1}, 2);
-    TS_ASSERT_EQUALS(*pair.first, 2);
-    TS_ASSERT(pair.second);
-    TS_ASSERT_EQUALS(test[1][1][1].value(), 2);
-  }
-
-  void testInsertNotDestructive() {
-    trie<int, int> test;
-    auto pair = test.insert(1, 2);
-    pair = test.insert(1, 0);
-    TS_ASSERT_EQUALS(*pair.first, 2);
-    TS_ASSERT(!pair.second);
-  }
-  
-  void testCanLocateElement() {
-    TS_ASSERT_EQUALS(*data.find({0, 1, 2}), 6);
-  }
-
-  void testFindAbsentElementReturnsEnd() {
-    TS_ASSERT_EQUALS(data.find({0, 3, 2}), data.end());
-  }
-  
-  void testEraseDropsEntireBranch() {
-    data.erase(0);
-    TS_ASSERT_EQUALS(data.find(0), data.end());
-  }
-};

+ 257 - 71
trie.xcodeproj/project.pbxproj

@@ -7,32 +7,83 @@
 	objects = {
 
 /* Begin PBXBuildFile section */
-		CD46DF461EF3FDCE0092D121 /* trie_tc.cpp in Sources */ = {isa = PBXBuildFile; fileRef = CD46DF441EF3FDCE0092D121 /* trie_tc.cpp */; };
+		CD0C596320C2DC3200454F82 /* GoogleMock.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = CD0C594D20C2DBE700454F82 /* GoogleMock.framework */; };
+		CD0C596420C2DC3800454F82 /* trie_test.cpp in Sources */ = {isa = PBXBuildFile; fileRef = CD0C595420C2DBFB00454F82 /* trie_test.cpp */; };
+		CD0C596D20C2E9DE00454F82 /* trie_impl.hpp in Headers */ = {isa = PBXBuildFile; fileRef = CD46DF481EF47C520092D121 /* trie_impl.hpp */; };
+		CD0C596E20C2E9E300454F82 /* trie.hpp in Headers */ = {isa = PBXBuildFile; fileRef = CD46DF451EF3FDCE0092D121 /* trie.hpp */; };
+		CD0C596F20C2E9E300454F82 /* trie_iterator.hpp in Headers */ = {isa = PBXBuildFile; fileRef = CD46DF4A1EF497E30092D121 /* trie_iterator.hpp */; };
+		CD0C597420C2EA7300454F82 /* trie_dummy.cpp in Sources */ = {isa = PBXBuildFile; fileRef = CD0C597320C2EA7300454F82 /* trie_dummy.cpp */; };
+		CD0C597920C2EAFA00454F82 /* libtrie.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = CD0C596920C2E9CE00454F82 /* libtrie.dylib */; };
 /* End PBXBuildFile section */
 
-/* Begin PBXCopyFilesBuildPhase section */
-		CD46DF351EF3FD540092D121 /* CopyFiles */ = {
-			isa = PBXCopyFilesBuildPhase;
-			buildActionMask = 2147483647;
-			dstPath = /usr/share/man/man1/;
-			dstSubfolderSpec = 0;
-			files = (
-			);
-			runOnlyForDeploymentPostprocessing = 1;
+/* Begin PBXContainerItemProxy section */
+		CD0C594C20C2DBE700454F82 /* PBXContainerItemProxy */ = {
+			isa = PBXContainerItemProxy;
+			containerPortal = CD0C594520C2DBE700454F82 /* GoogleMock.xcodeproj */;
+			proxyType = 2;
+			remoteGlobalIDString = 05818F861A685AEA0072A469;
+			remoteInfo = GoogleMock;
+		};
+		CD0C594E20C2DBE700454F82 /* PBXContainerItemProxy */ = {
+			isa = PBXContainerItemProxy;
+			containerPortal = CD0C594520C2DBE700454F82 /* GoogleMock.xcodeproj */;
+			proxyType = 2;
+			remoteGlobalIDString = 05E96ABD1A68600C00204102;
+			remoteInfo = gmock;
+		};
+		CD0C595020C2DBE700454F82 /* PBXContainerItemProxy */ = {
+			isa = PBXContainerItemProxy;
+			containerPortal = CD0C594520C2DBE700454F82 /* GoogleMock.xcodeproj */;
+			proxyType = 2;
+			remoteGlobalIDString = 05E96B1F1A68634900204102;
+			remoteInfo = gtest;
+		};
+		CD0C595220C2DBE700454F82 /* PBXContainerItemProxy */ = {
+			isa = PBXContainerItemProxy;
+			containerPortal = CD0C594520C2DBE700454F82 /* GoogleMock.xcodeproj */;
+			proxyType = 2;
+			remoteGlobalIDString = 05818F901A685AEA0072A469;
+			remoteInfo = GoogleMockTests;
+		};
+		CD0C596120C2DC2D00454F82 /* PBXContainerItemProxy */ = {
+			isa = PBXContainerItemProxy;
+			containerPortal = CD0C594520C2DBE700454F82 /* GoogleMock.xcodeproj */;
+			proxyType = 1;
+			remoteGlobalIDString = 05818F851A685AEA0072A469;
+			remoteInfo = GoogleMock;
 		};
-/* End PBXCopyFilesBuildPhase section */
+		CD0C597020C2EA1400454F82 /* PBXContainerItemProxy */ = {
+			isa = PBXContainerItemProxy;
+			containerPortal = CD46DF2F1EF3FD540092D121 /* Project object */;
+			proxyType = 1;
+			remoteGlobalIDString = CD0C596820C2E9CE00454F82;
+			remoteInfo = trie;
+		};
+/* End PBXContainerItemProxy section */
 
 /* Begin PBXFileReference section */
-		CD46DF371EF3FD540092D121 /* trie_tc */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = trie_tc; sourceTree = BUILT_PRODUCTS_DIR; };
-		CD46DF441EF3FDCE0092D121 /* trie_tc.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = trie_tc.cpp; sourceTree = "<group>"; };
+		CD0C594520C2DBE700454F82 /* GoogleMock.xcodeproj */ = {isa = PBXFileReference; lastKnownFileType = "wrapper.pb-project"; name = GoogleMock.xcodeproj; path = "../../../gmock-xcode-master/GoogleMock.xcodeproj"; sourceTree = "<group>"; };
+		CD0C595420C2DBFB00454F82 /* trie_test.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = trie_test.cpp; sourceTree = "<group>"; };
+		CD0C595920C2DC1D00454F82 /* trie_test.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = trie_test.xctest; sourceTree = BUILT_PRODUCTS_DIR; };
+		CD0C595D20C2DC1D00454F82 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; name = Info.plist; path = trie_test/Info.plist; sourceTree = "<group>"; };
+		CD0C596920C2E9CE00454F82 /* libtrie.dylib */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.dylib"; includeInIndex = 0; path = libtrie.dylib; sourceTree = BUILT_PRODUCTS_DIR; };
+		CD0C597320C2EA7300454F82 /* trie_dummy.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = trie_dummy.cpp; sourceTree = "<group>"; };
 		CD46DF451EF3FDCE0092D121 /* trie.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = trie.hpp; sourceTree = "<group>"; };
-		CD46DF471EF3FDDD0092D121 /* trie.t.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = trie.t.h; sourceTree = "<group>"; };
 		CD46DF481EF47C520092D121 /* trie_impl.hpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.h; path = trie_impl.hpp; sourceTree = "<group>"; };
 		CD46DF4A1EF497E30092D121 /* trie_iterator.hpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.h; path = trie_iterator.hpp; sourceTree = "<group>"; };
 /* End PBXFileReference section */
 
 /* Begin PBXFrameworksBuildPhase section */
-		CD46DF341EF3FD540092D121 /* Frameworks */ = {
+		CD0C595620C2DC1D00454F82 /* Frameworks */ = {
+			isa = PBXFrameworksBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+				CD0C597920C2EAFA00454F82 /* libtrie.dylib in Frameworks */,
+				CD0C596320C2DC3200454F82 /* GoogleMock.framework in Frameworks */,
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		CD0C596620C2E9CE00454F82 /* Frameworks */ = {
 			isa = PBXFrameworksBuildPhase;
 			buildActionMask = 2147483647;
 			files = (
@@ -42,9 +93,21 @@
 /* End PBXFrameworksBuildPhase section */
 
 /* Begin PBXGroup section */
+		CD0C594620C2DBE700454F82 /* Products */ = {
+			isa = PBXGroup;
+			children = (
+				CD0C594D20C2DBE700454F82 /* GoogleMock.framework */,
+				CD0C594F20C2DBE700454F82 /* gmock.framework */,
+				CD0C595120C2DBE700454F82 /* gtest.framework */,
+				CD0C595320C2DBE700454F82 /* GoogleMockTests.xctest */,
+			);
+			name = Products;
+			sourceTree = "<group>";
+		};
 		CD46DF2E1EF3FD540092D121 = {
 			isa = PBXGroup;
 			children = (
+				CD0C594520C2DBE700454F82 /* GoogleMock.xcodeproj */,
 				CD46DF421EF3FD6D0092D121 /* src */,
 				CD46DF411EF3FD670092D121 /* test */,
 				CD46DF381EF3FD540092D121 /* Products */,
@@ -54,7 +117,8 @@
 		CD46DF381EF3FD540092D121 /* Products */ = {
 			isa = PBXGroup;
 			children = (
-				CD46DF371EF3FD540092D121 /* trie_tc */,
+				CD0C595920C2DC1D00454F82 /* trie_test.xctest */,
+				CD0C596920C2E9CE00454F82 /* libtrie.dylib */,
 			);
 			name = Products;
 			sourceTree = "<group>";
@@ -62,8 +126,8 @@
 		CD46DF411EF3FD670092D121 /* test */ = {
 			isa = PBXGroup;
 			children = (
-				CD46DF471EF3FDDD0092D121 /* trie.t.h */,
-				CD46DF441EF3FDCE0092D121 /* trie_tc.cpp */,
+				CD0C595420C2DBFB00454F82 /* trie_test.cpp */,
+				CD0C595D20C2DC1D00454F82 /* Info.plist */,
 			);
 			name = test;
 			sourceTree = "<group>";
@@ -74,30 +138,62 @@
 				CD46DF451EF3FDCE0092D121 /* trie.hpp */,
 				CD46DF4A1EF497E30092D121 /* trie_iterator.hpp */,
 				CD46DF481EF47C520092D121 /* trie_impl.hpp */,
+				CD0C597320C2EA7300454F82 /* trie_dummy.cpp */,
 			);
 			name = src;
 			sourceTree = "<group>";
 		};
 /* End PBXGroup section */
 
+/* Begin PBXHeadersBuildPhase section */
+		CD0C596720C2E9CE00454F82 /* Headers */ = {
+			isa = PBXHeadersBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+				CD0C596E20C2E9E300454F82 /* trie.hpp in Headers */,
+				CD0C596D20C2E9DE00454F82 /* trie_impl.hpp in Headers */,
+				CD0C596F20C2E9E300454F82 /* trie_iterator.hpp in Headers */,
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+/* End PBXHeadersBuildPhase section */
+
 /* Begin PBXNativeTarget section */
-		CD46DF361EF3FD540092D121 /* trie_tc */ = {
+		CD0C595820C2DC1D00454F82 /* trie_test */ = {
+			isa = PBXNativeTarget;
+			buildConfigurationList = CD0C595E20C2DC1D00454F82 /* Build configuration list for PBXNativeTarget "trie_test" */;
+			buildPhases = (
+				CD0C595520C2DC1D00454F82 /* Sources */,
+				CD0C595620C2DC1D00454F82 /* Frameworks */,
+				CD0C595720C2DC1D00454F82 /* Resources */,
+			);
+			buildRules = (
+			);
+			dependencies = (
+				CD0C597120C2EA1400454F82 /* PBXTargetDependency */,
+				CD0C596220C2DC2D00454F82 /* PBXTargetDependency */,
+			);
+			name = trie_test;
+			productName = trie_test;
+			productReference = CD0C595920C2DC1D00454F82 /* trie_test.xctest */;
+			productType = "com.apple.product-type.bundle.unit-test";
+		};
+		CD0C596820C2E9CE00454F82 /* trie */ = {
 			isa = PBXNativeTarget;
-			buildConfigurationList = CD46DF3E1EF3FD540092D121 /* Build configuration list for PBXNativeTarget "trie_tc" */;
+			buildConfigurationList = CD0C596A20C2E9CF00454F82 /* Build configuration list for PBXNativeTarget "trie" */;
 			buildPhases = (
-				CD46DF431EF3FD9A0092D121 /* ShellScript */,
-				CD46DF331EF3FD540092D121 /* Sources */,
-				CD46DF341EF3FD540092D121 /* Frameworks */,
-				CD46DF351EF3FD540092D121 /* CopyFiles */,
+				CD0C596520C2E9CE00454F82 /* Sources */,
+				CD0C596620C2E9CE00454F82 /* Frameworks */,
+				CD0C596720C2E9CE00454F82 /* Headers */,
 			);
 			buildRules = (
 			);
 			dependencies = (
 			);
-			name = trie_tc;
+			name = trie;
 			productName = trie;
-			productReference = CD46DF371EF3FD540092D121 /* trie_tc */;
-			productType = "com.apple.product-type.tool";
+			productReference = CD0C596920C2E9CE00454F82 /* libtrie.dylib */;
+			productType = "com.apple.product-type.library.dynamic";
 		};
 /* End PBXNativeTarget section */
 
@@ -108,7 +204,10 @@
 				LastUpgradeCheck = 0720;
 				ORGANIZATIONNAME = "Sam Jaffe";
 				TargetAttributes = {
-					CD46DF361EF3FD540092D121 = {
+					CD0C595820C2DC1D00454F82 = {
+						CreatedOnToolsVersion = 7.2.1;
+					};
+					CD0C596820C2E9CE00454F82 = {
 						CreatedOnToolsVersion = 7.2.1;
 					};
 				};
@@ -123,48 +222,143 @@
 			mainGroup = CD46DF2E1EF3FD540092D121;
 			productRefGroup = CD46DF381EF3FD540092D121 /* Products */;
 			projectDirPath = "";
+			projectReferences = (
+				{
+					ProductGroup = CD0C594620C2DBE700454F82 /* Products */;
+					ProjectRef = CD0C594520C2DBE700454F82 /* GoogleMock.xcodeproj */;
+				},
+			);
 			projectRoot = "";
 			targets = (
-				CD46DF361EF3FD540092D121 /* trie_tc */,
+				CD0C595820C2DC1D00454F82 /* trie_test */,
+				CD0C596820C2E9CE00454F82 /* trie */,
 			);
 		};
 /* End PBXProject section */
 
-/* Begin PBXShellScriptBuildPhase section */
-		CD46DF431EF3FD9A0092D121 /* ShellScript */ = {
-			isa = PBXShellScriptBuildPhase;
+/* Begin PBXReferenceProxy section */
+		CD0C594D20C2DBE700454F82 /* GoogleMock.framework */ = {
+			isa = PBXReferenceProxy;
+			fileType = wrapper.framework;
+			path = GoogleMock.framework;
+			remoteRef = CD0C594C20C2DBE700454F82 /* PBXContainerItemProxy */;
+			sourceTree = BUILT_PRODUCTS_DIR;
+		};
+		CD0C594F20C2DBE700454F82 /* gmock.framework */ = {
+			isa = PBXReferenceProxy;
+			fileType = wrapper.framework;
+			path = gmock.framework;
+			remoteRef = CD0C594E20C2DBE700454F82 /* PBXContainerItemProxy */;
+			sourceTree = BUILT_PRODUCTS_DIR;
+		};
+		CD0C595120C2DBE700454F82 /* gtest.framework */ = {
+			isa = PBXReferenceProxy;
+			fileType = wrapper.framework;
+			path = gtest.framework;
+			remoteRef = CD0C595020C2DBE700454F82 /* PBXContainerItemProxy */;
+			sourceTree = BUILT_PRODUCTS_DIR;
+		};
+		CD0C595320C2DBE700454F82 /* GoogleMockTests.xctest */ = {
+			isa = PBXReferenceProxy;
+			fileType = wrapper.cfbundle;
+			path = GoogleMockTests.xctest;
+			remoteRef = CD0C595220C2DBE700454F82 /* PBXContainerItemProxy */;
+			sourceTree = BUILT_PRODUCTS_DIR;
+		};
+/* End PBXReferenceProxy section */
+
+/* Begin PBXResourcesBuildPhase section */
+		CD0C595720C2DC1D00454F82 /* Resources */ = {
+			isa = PBXResourcesBuildPhase;
 			buildActionMask = 2147483647;
 			files = (
 			);
-			inputPaths = (
-				"$(SRCROOT)/trie.t.h",
-			);
-			outputPaths = (
-				"$(SRCROOT)/trie_tc.cpp",
-			);
 			runOnlyForDeploymentPostprocessing = 0;
-			shellPath = /bin/sh;
-			shellScript = "cxxtestgen --error-printer -o trie_tc.cpp trie.t.h";
 		};
-/* End PBXShellScriptBuildPhase section */
+/* End PBXResourcesBuildPhase section */
 
 /* Begin PBXSourcesBuildPhase section */
-		CD46DF331EF3FD540092D121 /* Sources */ = {
+		CD0C595520C2DC1D00454F82 /* Sources */ = {
 			isa = PBXSourcesBuildPhase;
 			buildActionMask = 2147483647;
 			files = (
-				CD46DF461EF3FDCE0092D121 /* trie_tc.cpp in Sources */,
+				CD0C596420C2DC3800454F82 /* trie_test.cpp in Sources */,
+			);
+			runOnlyForDeploymentPostprocessing = 0;
+		};
+		CD0C596520C2E9CE00454F82 /* Sources */ = {
+			isa = PBXSourcesBuildPhase;
+			buildActionMask = 2147483647;
+			files = (
+				CD0C597420C2EA7300454F82 /* trie_dummy.cpp in Sources */,
 			);
 			runOnlyForDeploymentPostprocessing = 0;
 		};
 /* End PBXSourcesBuildPhase section */
 
+/* Begin PBXTargetDependency section */
+		CD0C596220C2DC2D00454F82 /* PBXTargetDependency */ = {
+			isa = PBXTargetDependency;
+			name = GoogleMock;
+			targetProxy = CD0C596120C2DC2D00454F82 /* PBXContainerItemProxy */;
+		};
+		CD0C597120C2EA1400454F82 /* PBXTargetDependency */ = {
+			isa = PBXTargetDependency;
+			target = CD0C596820C2E9CE00454F82 /* trie */;
+			targetProxy = CD0C597020C2EA1400454F82 /* PBXContainerItemProxy */;
+		};
+/* End PBXTargetDependency section */
+
 /* Begin XCBuildConfiguration section */
+		CD0C595F20C2DC1D00454F82 /* Debug */ = {
+			isa = XCBuildConfiguration;
+			buildSettings = {
+				CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
+				COMBINE_HIDPI_IMAGES = YES;
+				INFOPLIST_FILE = trie_test/Info.plist;
+				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks @loader_path/../Frameworks";
+				PRODUCT_BUNDLE_IDENTIFIER = "leumasjaffe.trie-test";
+				PRODUCT_NAME = "$(TARGET_NAME)";
+			};
+			name = Debug;
+		};
+		CD0C596020C2DC1D00454F82 /* Release */ = {
+			isa = XCBuildConfiguration;
+			buildSettings = {
+				CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
+				COMBINE_HIDPI_IMAGES = YES;
+				INFOPLIST_FILE = trie_test/Info.plist;
+				LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/../Frameworks @loader_path/../Frameworks";
+				PRODUCT_BUNDLE_IDENTIFIER = "leumasjaffe.trie-test";
+				PRODUCT_NAME = "$(TARGET_NAME)";
+			};
+			name = Release;
+		};
+		CD0C596B20C2E9CF00454F82 /* Debug */ = {
+			isa = XCBuildConfiguration;
+			buildSettings = {
+				DYLIB_COMPATIBILITY_VERSION = 1;
+				DYLIB_CURRENT_VERSION = 1;
+				EXECUTABLE_PREFIX = lib;
+				PRODUCT_NAME = "$(TARGET_NAME)";
+			};
+			name = Debug;
+		};
+		CD0C596C20C2E9CF00454F82 /* Release */ = {
+			isa = XCBuildConfiguration;
+			buildSettings = {
+				DYLIB_COMPATIBILITY_VERSION = 1;
+				DYLIB_CURRENT_VERSION = 1;
+				EXECUTABLE_PREFIX = lib;
+				PRODUCT_NAME = "$(TARGET_NAME)";
+			};
+			name = Release;
+		};
 		CD46DF3C1EF3FD540092D121 /* Debug */ = {
 			isa = XCBuildConfiguration;
 			buildSettings = {
 				ALWAYS_SEARCH_USER_PATHS = NO;
-				CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x";
+				CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
@@ -200,6 +394,7 @@
 				MTL_ENABLE_DEBUG_INFO = YES;
 				ONLY_ACTIVE_ARCH = YES;
 				SDKROOT = macosx;
+				USER_HEADER_SEARCH_PATHS = "../ ../../types";
 			};
 			name = Debug;
 		};
@@ -207,7 +402,7 @@
 			isa = XCBuildConfiguration;
 			buildSettings = {
 				ALWAYS_SEARCH_USER_PATHS = NO;
-				CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x";
+				CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
 				CLANG_CXX_LIBRARY = "libc++";
 				CLANG_ENABLE_MODULES = YES;
 				CLANG_ENABLE_OBJC_ARC = YES;
@@ -236,48 +431,39 @@
 				MACOSX_DEPLOYMENT_TARGET = 10.10;
 				MTL_ENABLE_DEBUG_INFO = NO;
 				SDKROOT = macosx;
-			};
-			name = Release;
-		};
-		CD46DF3F1EF3FD540092D121 /* Debug */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
-				HEADER_SEARCH_PATHS = /usr/local/include;
-				PRODUCT_NAME = "$(TARGET_NAME)";
-				USER_HEADER_SEARCH_PATHS = "../../types ../";
-			};
-			name = Debug;
-		};
-		CD46DF401EF3FD540092D121 /* Release */ = {
-			isa = XCBuildConfiguration;
-			buildSettings = {
-				CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
-				HEADER_SEARCH_PATHS = /usr/local/include;
-				PRODUCT_NAME = "$(TARGET_NAME)";
-				USER_HEADER_SEARCH_PATHS = "../../types ../";
+				USER_HEADER_SEARCH_PATHS = "../ ../../types";
 			};
 			name = Release;
 		};
 /* End XCBuildConfiguration section */
 
 /* Begin XCConfigurationList section */
-		CD46DF321EF3FD540092D121 /* Build configuration list for PBXProject "trie" */ = {
+		CD0C595E20C2DC1D00454F82 /* Build configuration list for PBXNativeTarget "trie_test" */ = {
 			isa = XCConfigurationList;
 			buildConfigurations = (
-				CD46DF3C1EF3FD540092D121 /* Debug */,
-				CD46DF3D1EF3FD540092D121 /* Release */,
+				CD0C595F20C2DC1D00454F82 /* Debug */,
+				CD0C596020C2DC1D00454F82 /* Release */,
 			);
 			defaultConfigurationIsVisible = 0;
 			defaultConfigurationName = Release;
 		};
-		CD46DF3E1EF3FD540092D121 /* Build configuration list for PBXNativeTarget "trie_tc" */ = {
+		CD0C596A20C2E9CF00454F82 /* Build configuration list for PBXNativeTarget "trie" */ = {
 			isa = XCConfigurationList;
 			buildConfigurations = (
-				CD46DF3F1EF3FD540092D121 /* Debug */,
-				CD46DF401EF3FD540092D121 /* Release */,
+				CD0C596B20C2E9CF00454F82 /* Debug */,
+				CD0C596C20C2E9CF00454F82 /* Release */,
 			);
 			defaultConfigurationIsVisible = 0;
+			defaultConfigurationName = Release;
+		};
+		CD46DF321EF3FD540092D121 /* Build configuration list for PBXProject "trie" */ = {
+			isa = XCConfigurationList;
+			buildConfigurations = (
+				CD46DF3C1EF3FD540092D121 /* Debug */,
+				CD46DF3D1EF3FD540092D121 /* Release */,
+			);
+			defaultConfigurationIsVisible = 0;
+			defaultConfigurationName = Release;
 		};
 /* End XCConfigurationList section */
 	};

+ 11 - 0
trie_dummy.cpp

@@ -0,0 +1,11 @@
+//
+//  trie_dummy.cpp
+//  trie
+//
+//  Created by Sam Jaffe on 6/2/18.
+//
+
+#include "trie.hpp"
+
+
+template class trie<int, int>;

+ 129 - 0
trie_test.cpp

@@ -0,0 +1,129 @@
+//
+//  trie_test.cpp
+//  trie
+//
+//  Created by Sam Jaffe on 6/2/18.
+//
+
+#include <gtest/gtest.h>
+#include <gmock/gmock.h>
+
+#include "trie.hpp"
+
+using Tree = trie<int, int>;
+
+class TrieTest : public ::testing::Test {
+protected:
+  virtual void SetUp() override;
+  virtual void TearDown() override;
+
+  Tree data;
+};
+
+void TrieTest::SetUp() {
+  data          = 1;
+  data[0      ] = 5;
+  data[{0,1}  ] = 4;
+  data[{0,1,0}] = 3;
+  data[{0,1,2}] = 6;
+  data[{0,2,0}] = 7;
+  data[ 1     ] = 2;
+  data[{1,1}  ] = 8;
+  data[{1,1,0}] = 9;
+}
+
+void TrieTest::TearDown() {
+  data.clear();
+}
+
+template <typename Iter>
+std::vector<int> flatten(Iter it) {
+  decltype(it) end{};
+  std::vector<int> out;
+  out.reserve(size_t(std::distance(it, end)));
+  std::copy(it, end, std::back_inserter(out));
+  return out;
+}
+
+TEST_F(TrieTest, CopyConstructorIsDeep) {
+  Tree copy = data;
+  copy[{0, 1}] += 1;
+  EXPECT_THAT(copy, ::testing::Not(::testing::Eq(data)));
+}
+
+TEST_F(TrieTest, EqualityIsPathSensitive) {
+  Tree t1, t2;
+  t1[1] = 1;
+  t2[2] = 1;
+  EXPECT_THAT(flatten(t1.cbegin()),
+              flatten(t2.cbegin()));
+  EXPECT_THAT(t1, ::testing::Not(::testing::Eq(t2)));
+}
+
+TEST_F(TrieTest, NormalIterationIsPreOrdered) {
+  EXPECT_THAT(flatten(data.cbegin()),
+              std::vector<int>({ 1, 5, 4, 3, 6, 0, 7, 2, 8, 9 }));
+}
+
+TEST_F(TrieTest, PostIteratorUsesPostOrder) {
+  EXPECT_THAT(flatten(Tree::const_post_iterator(&data)),
+              std::vector<int>({ 1, 2, 8, 9, 5, 0, 7, 4, 6, 3 }));
+}
+
+TEST_F(TrieTest, ReverseIterationIsBackwardsPreOrdered) {
+  EXPECT_THAT(flatten(data.crbegin()),
+              std::vector<int>({ 9, 8, 2, 7, 0, 6, 3, 4, 5, 1 }));
+}
+
+TEST_F(TrieTest, InsertingNewElementReturnsSuccess) {
+  Tree example;
+  std::pair<Tree::iterator, bool> rval = example.insert(1, 2);
+  EXPECT_TRUE(rval.second);
+  EXPECT_THAT(*rval.first, 2);
+}
+
+TEST_F(TrieTest, EmplacingNewElementReturnsSuccess) {
+  Tree example;
+  std::pair<Tree::iterator, bool> rval = example.emplace(1, 2);
+  EXPECT_TRUE(rval.second);
+  EXPECT_THAT(*rval.first, 2);
+}
+
+TEST_F(TrieTest, InsertingWithPathWillCreateParents) {
+  Tree example;
+  std::pair<Tree::iterator, bool> rval = example.emplace({1,1,1}, 2);
+  EXPECT_TRUE(rval.second);
+  EXPECT_THAT(*rval.first, 2);
+  EXPECT_THAT(example[1][1][1].value(), 2);
+}
+
+TEST_F(TrieTest, InsertingInAlreadyExistantPathNonDestructive) {
+  Tree example;
+  example.insert(1, 2);
+  std::pair<Tree::iterator, bool> rval = example.insert(1, 0);
+  EXPECT_FALSE(rval.second);
+  EXPECT_THAT(*rval.first, ::testing::Not(0));
+}
+
+TEST_F(TrieTest, EmplacingInAlreadyExistantPathNonDestructive) {
+  Tree example;
+  example.insert(1, 2);
+  std::pair<Tree::iterator, bool> rval = example.emplace(1, 0);
+  EXPECT_FALSE(rval.second);
+  EXPECT_THAT(*rval.first, ::testing::Not(0));
+}
+
+TEST_F(TrieTest, FindWithPathWillReturnIteratorToEntry) {
+  EXPECT_THAT(*data.find({0, 1, 2}), 6);
+}
+
+TEST_F(TrieTest, FindMissingPathWillReturnEnd) {
+  EXPECT_THAT(data.find({0, 3, 2}), data.end());
+}
+
+TEST_F(TrieTest, EraseDropsWholeBranch) {
+  EXPECT_THAT(data.find({0, 1}), ::testing::Not(data.end()));
+  data.erase(0);
+  EXPECT_THAT(data.find({0, 1}), data.end());
+  EXPECT_THAT(data.find(0), data.end());
+}

+ 24 - 0
trie_test/Info.plist

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+	<key>CFBundleDevelopmentRegion</key>
+	<string>en</string>
+	<key>CFBundleExecutable</key>
+	<string>$(EXECUTABLE_NAME)</string>
+	<key>CFBundleIdentifier</key>
+	<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
+	<key>CFBundleInfoDictionaryVersion</key>
+	<string>6.0</string>
+	<key>CFBundleName</key>
+	<string>$(PRODUCT_NAME)</string>
+	<key>CFBundlePackageType</key>
+	<string>BNDL</string>
+	<key>CFBundleShortVersionString</key>
+	<string>1.0</string>
+	<key>CFBundleSignature</key>
+	<string>????</string>
+	<key>CFBundleVersion</key>
+	<string>1</string>
+</dict>
+</plist>