diff --git a/src/lib/diff/record-content-mutator.hpp b/src/lib/diff/record-content-mutator.hpp index 5ede5259f..5f672e557 100644 --- a/src/lib/diff/record-content-mutator.hpp +++ b/src/lib/diff/record-content-mutator.hpp @@ -57,19 +57,54 @@ namespace diff{ /** @internal helper for DiffApplicationStrategy */ template - class RecordContentMutator + struct RecordContentMutator : boost::noncopyable { - public: - explicit + using Iter = typename STO::iterator; + + STO attribs; + STO children; + Iter pos; + RecordContentMutator() + : attribs() + , children() + , pos(attribs.begin()) + { } + + + bool + empty() const { - swap (attribs_, target_.attribs()); - swap (children_, target_.children()); - - // heuristics for storage pre-allocation - target_.attribs().reserve (attribs_.size() * 120 / 100); - target_.children().reserve (children_.size() * 120 / 100); + return attribs.empty() + && children.empty(); + } + + bool + currIsAttrib() const + { + UNIMPLEMENTED ("determine current scope"); + } + + bool + currIsChild() const + { + UNIMPLEMENTED ("determine current scope"); + } + + Iter end() { return children.end(); } + Iter end() const { return children.end(); } + + RecordContentMutator& + operator++() + { + UNIMPLEMENTED ("iteration"); + } + + void + resetPos() + { + pos = attribs.begin(); } }; diff --git a/src/lib/diff/record.hpp b/src/lib/diff/record.hpp index fbeaf0eef..457068ca7 100644 --- a/src/lib/diff/record.hpp +++ b/src/lib/diff/record.hpp @@ -92,6 +92,8 @@ #include "lib/itertools.hpp" #include "lib/util.hpp" +#include "lib/diff/record-content-mutator.hpp" + #include #include @@ -239,6 +241,8 @@ namespace diff{ */ class Mutator; + using ContentMutator = RecordContentMutator; + /** * copy-initialise (or convert) from the given Mutator instance. @@ -453,7 +457,12 @@ namespace diff{ Storage& attribs() { return record_.attribs_; } Storage& children() { return record_.children_; } - + void + swapContent (ContentMutator& alteredContent) + { + std::swap (record_.attribs_, alteredContent.attribs); + std::swap (record_.children_, alteredContent.children); + } /* === extension point for building specific value types === */ /* diff --git a/tests/library/diff/generic-record-update-test.cpp b/tests/library/diff/generic-record-update-test.cpp index 92154774f..2767982a8 100644 --- a/tests/library/diff/generic-record-update-test.cpp +++ b/tests/library/diff/generic-record-update-test.cpp @@ -107,24 +107,27 @@ namespace test{ mut.setType("🌰"); std::cout << string(subject) << std::endl; - CHECK (!isnil (mut)); - RecS::ContentMutator content = mut.swapContent(); + RecS::ContentMutator content; - CHECK ( isnil (mut)); + CHECK (!isnil (mut)); + CHECK ( isnil (content)); + mut.swapContent(content); CHECK (!isnil (content)); + CHECK ( isnil (mut)); + CHECK (content.pos == content.attribs.begin()); CHECK (content.currIsAttrib()); CHECK (!content.currIsChild()); CHECK ("b = β" == *content.pos); - void* rawElm = &attribs[0]; + void* rawElm = &content.attribs[0]; swap (content.attribs[0], content.attribs[1]); CHECK ("a = α" == *content.pos); - CHECK (rawElm == content.pos); + CHECK (rawElm == & *content.pos); ++content; CHECK ("b = β" == *content.pos); - CHECK (rawElm != content.pos); + CHECK (rawElm != &*content.pos); CHECK (content.currIsAttrib()); CHECK (!content.currIsChild()); @@ -148,18 +151,18 @@ namespace test{ VERIFY_ERROR (ITER_EXHAUST, ++content); content.resetPos(); - CHECK (rawElm == content.pos); + CHECK (rawElm == & *content.pos); ++content; CHECK ("b = β" == *content.pos); CHECK ( isnil (mut)); CHECK (!isnil (content)); - mut.swapContent(); + mut.swapContent(content); CHECK ( isnil (content)); CHECK (!isnil (mut)); mut.replace(subject); - CHECK (Seq({"a = α", "b = β", "γ", "δ", "ε"}) == contents(a)); + CHECK (Seq({"a = α", "b = β", "γ", "δ", "ε"}) == contents(subject)); std::cout << string(subject) << std::endl; } };