diff options
-rw-r--r-- | CMakeLists.txt | 2 | ||||
-rw-r--r-- | src/core/model/Node.cpp | 7 | ||||
-rw-r--r-- | src/core/model/Node.hpp | 11 | ||||
-rw-r--r-- | test/core/model/IndexTest.cpp | 95 |
4 files changed, 109 insertions, 6 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt index 53b8e89..5a494c3 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -124,6 +124,7 @@ ADD_LIBRARY(ousia_core src/core/managed/Manager src/core/model/Document src/core/model/Domain + src/core/model/Index src/core/model/Node src/core/model/Typesystem src/core/parser/Parser @@ -198,6 +199,7 @@ IF(TEST) test/core/managed/VariantObjectTest test/core/model/DomainTest test/core/model/DocumentTest + test/core/model/IndexTest test/core/model/NodeTest test/core/model/TypesystemTest test/core/parser/ParserStackTest diff --git a/src/core/model/Node.cpp b/src/core/model/Node.cpp index fa6a3a2..e149596 100644 --- a/src/core/model/Node.cpp +++ b/src/core/model/Node.cpp @@ -16,6 +16,8 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. */ +#include <core/common/Exceptions.hpp> + #include "Node.hpp" namespace ousia { @@ -90,8 +92,8 @@ int Node::resolve(std::vector<Rooted<Managed>> &res, } std::vector<Rooted<Managed>> Node::resolve(const std::vector<std::string> &path, - Filter filter = nullptr, - void *filterData = nullptr) + Filter filter = nullptr, + void *filterData = nullptr) { std::vector<Rooted<Managed>> res; VisitorSet visited; @@ -102,5 +104,4 @@ std::vector<Rooted<Managed>> Node::resolve(const std::vector<std::string> &path, /* RTTI type registrations */ const Rtti<Node> RttiTypes::Node{"Node"}; - } diff --git a/src/core/model/Node.hpp b/src/core/model/Node.hpp index cca33f7..a637b56 100644 --- a/src/core/model/Node.hpp +++ b/src/core/model/Node.hpp @@ -29,6 +29,8 @@ #include <core/managed/Managed.hpp> #include <core/managed/ManagedContainer.hpp> +#include "Index.hpp" + namespace ousia { /** @@ -292,7 +294,7 @@ public: // TODO: Use a different listener here for updating name maps -template <class T, class Listener = DefaultListener<Handle<T>>> +template <class T, class Listener = Index> class NodeVector : public ManagedGenericList<T, std::vector<Handle<T>>, ListAccessor<Handle<T>>, Listener> { @@ -300,10 +302,11 @@ public: using Base = ManagedGenericList<T, std::vector<Handle<T>>, ListAccessor<Handle<T>>, Listener>; using Base::ManagedGenericList; + + Index& getIndex() { return this->listener;} }; -template <class K, class T, - class Listener = DefaultListener<std::pair<K, Handle<T>>>> +template <class K, class T, class Listener = Index> class NodeMap : public ManagedGenericMap<K, T, std::map<K, Handle<T>>, MapAccessor<std::pair<K, Handle<T>>>, Listener> { @@ -312,6 +315,8 @@ public: ManagedGenericMap<K, T, std::map<K, Handle<T>>, MapAccessor<std::pair<K, Handle<T>>>, Listener>; using Base::ManagedGenericMap; + + Index& getIndex() { return this->listener;} }; namespace RttiTypes { diff --git a/test/core/model/IndexTest.cpp b/test/core/model/IndexTest.cpp new file mode 100644 index 0000000..5bf50db --- /dev/null +++ b/test/core/model/IndexTest.cpp @@ -0,0 +1,95 @@ +/* + Ousía + Copyright (C) 2014, 2015 Benjamin Paaßen, Andreas Stöckel + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see <http://www.gnu.org/licenses/>. +*/ + +#include <gtest/gtest.h> + +#include <iostream> + +#include <core/model/Node.hpp> + +namespace ousia { + +TEST(Index, simple) +{ + Manager mgr{1}; + Rooted<Managed> owner{new Managed(mgr)}; + { + NodeVector<Node> nodes(owner); + Index &idx = nodes.getIndex(); + + Node* n1 = new Node(mgr, "node1"); + Node* n2 = new Node(mgr, "node2"); + Node* n3 = new Node(mgr, "node3"); + + nodes.push_back(n1); + nodes.push_back(n2); + nodes.push_back(n3); + + // Index + ASSERT_EQ(n1, idx.resolve("node1")); + ASSERT_EQ(n2, idx.resolve("node2")); + ASSERT_EQ(n3, idx.resolve("node3")); + ASSERT_EQ(nullptr, idx.resolve("node4")); + + // Rename + n2->setName("node2b"); + ASSERT_EQ(nullptr, idx.resolve("node2")); + ASSERT_EQ(n2, idx.resolve("node2b")); + + // Delete + nodes.erase(nodes.begin() + 1); + ASSERT_EQ(nullptr, idx.resolve("node2b")); + + nodes.erase(nodes.begin() + 0); + ASSERT_EQ(nullptr, idx.resolve("node1")); + + // Another rename + n3->setName("node3b"); + ASSERT_EQ(nullptr, idx.resolve("node3")); + ASSERT_EQ(n3, idx.resolve("node3b")); + } +} + +TEST(Index, shared) +{ + Manager mgr{1}; + Rooted<Managed> owner{new Managed(mgr)}; + Index idx; + { + NodeVector<Node, Index&> nodes1(owner, idx); + NodeVector<Node, Index&> nodes2(owner, idx); + + ASSERT_EQ(&idx, &nodes1.getIndex()); + ASSERT_EQ(&idx, &nodes2.getIndex()); + + Node* n1 = new Node(mgr, "node1"); + Node* n2 = new Node(mgr, "node2"); + Node* n3 = new Node(mgr, "node3"); + + nodes1.push_back(n1); + nodes1.push_back(n2); + nodes2.push_back(n3); + + ASSERT_EQ(n1, idx.resolve("node1")); + ASSERT_EQ(n2, idx.resolve("node2")); + ASSERT_EQ(n3, idx.resolve("node3")); + ASSERT_EQ(nullptr, idx.resolve("node4")); + } +} + +} |