summaryrefslogtreecommitdiff
path: root/src/core
diff options
context:
space:
mode:
authorAndreas Stöckel <astoecke@techfak.uni-bielefeld.de>2015-03-03 19:16:30 +0100
committerAndreas Stöckel <andreas@somweyr.de>2015-03-03 19:16:30 +0100
commitb730f4d9cc092f8ab2d7c71853431042d75d5d08 (patch)
tree9922b245fbd33ca5a60b901003e8e9b606bd5699 /src/core
parent2a5e714d1d222cc5e27fc442c56c1a880df573d2 (diff)
parent68c66558cd7c8e64dd0d3b934ccb58603f8b9836 (diff)
Merge branch 'master' of ssh://somweyr.de/var/local/git/ousia
Diffstat (limited to 'src/core')
-rw-r--r--src/core/model/Document.cpp33
-rw-r--r--src/core/model/Document.hpp22
2 files changed, 35 insertions, 20 deletions
diff --git a/src/core/model/Document.cpp b/src/core/model/Document.cpp
index 40c03ac..219e512 100644
--- a/src/core/model/Document.cpp
+++ b/src/core/model/Document.cpp
@@ -327,8 +327,10 @@ void DocumentEntity::addStructureNode(Handle<StructureNode> s, size_t i)
if (par != nullptr) {
if (par->isa(&RttiTypes::StructuredEntity)) {
par.cast<StructuredEntity>()->removeStructureNode(s);
- } else {
+ } else if(par->isa(&RttiTypes::AnnotationEntity)){
par.cast<AnnotationEntity>()->removeStructureNode(s);
+ } else if(par->isa(&RttiTypes::Document)){
+ par.cast<Document>()->setRoot(nullptr);
}
}
s->setParent(subInst);
@@ -463,7 +465,7 @@ static bool matchStartAnchor(Handle<AnnotationClass> desc,
template <typename Iterator>
Rooted<Anchor> DocumentEntity::searchStartAnchorInField(
Handle<AnnotationClass> desc, const std::string &name, Iterator begin,
- Iterator end)
+ Iterator end, std::unordered_set<const DocumentEntity *> &visited)
{
for (Iterator it = begin; it != end; it++) {
Handle<StructureNode> strct = *it;
@@ -478,7 +480,7 @@ Rooted<Anchor> DocumentEntity::searchStartAnchorInField(
// search downwards.
Rooted<Anchor> a =
strct.cast<StructuredEntity>()->searchStartAnchorDownwards(
- desc, name);
+ desc, name, visited);
if (a != nullptr) {
return a;
}
@@ -488,8 +490,12 @@ Rooted<Anchor> DocumentEntity::searchStartAnchorInField(
}
Rooted<Anchor> DocumentEntity::searchStartAnchorDownwards(
- Handle<AnnotationClass> desc, const std::string &name)
+ Handle<AnnotationClass> desc, const std::string &name,
+ std::unordered_set<const DocumentEntity *> &visited)
{
+ if (!visited.insert(this).second) {
+ return nullptr;
+ }
if (fields.empty()) {
return nullptr;
}
@@ -497,13 +503,17 @@ Rooted<Anchor> DocumentEntity::searchStartAnchorDownwards(
NodeVector<StructureNode> children = fields[fields.size() - 1];
// search it from back to front.
return searchStartAnchorInField(desc, name, children.rbegin(),
- children.rend());
+ children.rend(), visited);
}
Rooted<Anchor> DocumentEntity::searchStartAnchorUpwards(
Handle<AnnotationClass> desc, const std::string &name,
- const DocumentEntity *child)
+ const DocumentEntity *child,
+ std::unordered_set<const DocumentEntity *> &visited)
{
+ if (!visited.insert(this).second) {
+ return nullptr;
+ }
if (fields.empty()) {
return nullptr;
}
@@ -519,7 +529,8 @@ Rooted<Anchor> DocumentEntity::searchStartAnchorUpwards(
// to the child.
if (it != children.rend()) {
it++;
- return searchStartAnchorInField(desc, name, it, children.rend());
+ return searchStartAnchorInField(desc, name, it, children.rend(),
+ visited);
}
throw OusiaException("Internal error: Child node not found in parent!");
}
@@ -528,11 +539,13 @@ Rooted<Anchor> DocumentEntity::searchStartAnchor(size_t fieldIdx,
Handle<AnnotationClass> desc,
const std::string &name)
{
+ std::unordered_set<const DocumentEntity *> visited;
+ visited.insert(this);
// get the correct field.
NodeVector<StructureNode> children = fields[fieldIdx];
// search it from back to front.
Rooted<Anchor> a = searchStartAnchorInField(desc, name, children.rbegin(),
- children.rend());
+ children.rend(), visited);
// if we found the Anchor, return it.
if (a != nullptr) {
return a;
@@ -548,11 +561,11 @@ Rooted<Anchor> DocumentEntity::searchStartAnchor(size_t fieldIdx,
if (subInst->getParent()->isa(&RttiTypes::StructuredEntity)) {
return subInst->getParent()
.cast<StructuredEntity>()
- ->searchStartAnchorUpwards(desc, name, this);
+ ->searchStartAnchorUpwards(desc, name, this, visited);
}
if (subInst->getParent()->isa(&RttiTypes::AnnotationEntity)) {
subInst->getParent().cast<AnnotationEntity>()->searchStartAnchorUpwards(
- desc, name, this);
+ desc, name, this, visited);
}
return nullptr;
}
diff --git a/src/core/model/Document.hpp b/src/core/model/Document.hpp
index 8019379..6b2ae47 100644
--- a/src/core/model/Document.hpp
+++ b/src/core/model/Document.hpp
@@ -157,16 +157,18 @@ private:
void invalidateSubInstance();
template <typename Iterator>
- Rooted<Anchor> searchStartAnchorInField(Handle<AnnotationClass> desc,
- const std::string &name,
- Iterator begin, Iterator end);
-
- Rooted<Anchor> searchStartAnchorDownwards(Handle<AnnotationClass> desc,
- const std::string &name);
-
- Rooted<Anchor> searchStartAnchorUpwards(Handle<AnnotationClass> desc,
- const std::string &name,
- const DocumentEntity *child);
+ Rooted<Anchor> searchStartAnchorInField(
+ Handle<AnnotationClass> desc, const std::string &name, Iterator begin,
+ Iterator end, std::unordered_set<const DocumentEntity *> &visited);
+
+ Rooted<Anchor> searchStartAnchorDownwards(
+ Handle<AnnotationClass> desc, const std::string &name,
+ std::unordered_set<const DocumentEntity *> &visited);
+
+ Rooted<Anchor> searchStartAnchorUpwards(
+ Handle<AnnotationClass> desc, const std::string &name,
+ const DocumentEntity *child,
+ std::unordered_set<const DocumentEntity *> &visited);
protected:
bool doValidate(Logger &logger) const;