diff src/main/java/jp/ac/u_ryukyu/ie/cr/shoshi/jungle/transaction/IndexJungleTreeEditor.java @ 149:feb2346ace19

refactor ParentIndex
author one
date Sat, 22 Nov 2014 12:08:35 +0900
parents 371b6ddb78f2
children d9fbddf77bf6
line wrap: on
line diff
--- a/src/main/java/jp/ac/u_ryukyu/ie/cr/shoshi/jungle/transaction/IndexJungleTreeEditor.java	Fri Nov 21 12:46:36 2014 +0900
+++ b/src/main/java/jp/ac/u_ryukyu/ie/cr/shoshi/jungle/transaction/IndexJungleTreeEditor.java	Sat Nov 22 12:08:35 2014 +0900
@@ -1,13 +1,16 @@
 package jp.ac.u_ryukyu.ie.cr.shoshi.jungle.transaction;
 
 import java.nio.ByteBuffer;
+import java.util.Iterator;
 
+import fj.P2;
 import fj.data.List;
 import fj.data.TreeMap;
 import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.JungleTreeEditor;
 import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.store.NodePath;
 import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.store.impl.IndexTreeEditor;
 import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.store.impl.TreeNode;
+import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.store.impl.TreeNodeChildren;
 import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.store.impl.logger.DefaultTreeOperationLog;
 import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.store.impl.logger.LoggingNode;
 import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.store.impl.logger.OperationLog;
@@ -24,50 +27,59 @@
 import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.util.Either;
 import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.util.Error;
 import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.util.IterableConverter;
-import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.util.Triple;
+import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.util.Pair;
+import jp.ac.u_ryukyu.ie.cr.shoshi.jungle.util.TreeMapOrd;
 import jp.ac.u_ryukyu.ie.cr.tatsuki.jungle.store.index.DefaultIndexEditor;
 import jp.ac.u_ryukyu.ie.cr.tatsuki.jungle.store.index.DeleteChildIndexEditor;
 import jp.ac.u_ryukyu.ie.cr.tatsuki.jungle.store.index.IndexEditor;
+import jp.ac.u_ryukyu.ie.cr.tatsuki.jungle.store.index.ParentIndex;
 
 public class IndexJungleTreeEditor implements JungleTreeEditor {
   private final TransactionManager txManager;
   private final TreeNode root;
+  private final TreeNode oldRoot;
   private final IndexTreeEditor editor;
   private final TreeOperationLog log;
+  private final TreeOperationLog tmpLog;
   private TreeMap<String, TreeMap<String, List<TreeNode>>> index;
-  private TreeMap<TreeNode, TreeNode> parentIndex;
+  private ParentIndex parentIndex;
 
   public TreeMap<String, TreeMap<String, List<TreeNode>>> getIndex() {
     return index;
   }
 
-
-
-  public IndexJungleTreeEditor(TreeNode _root, TransactionManager _txManager, IndexTreeEditor treeEditor,
-      TreeMap<String, TreeMap<String, List<TreeNode>>> index,TreeMap<TreeNode, TreeNode> parentIndex) {
-    this(_root, _txManager, treeEditor, new DefaultTreeOperationLog(), index,parentIndex);
+  public IndexJungleTreeEditor(TreeNode _root, TreeNode oldRoot, TransactionManager _txManager,
+      IndexTreeEditor treeEditor, TreeMap<String, TreeMap<String, List<TreeNode>>> index,
+      ParentIndex parentIndex) {
+    this(_root, oldRoot, _txManager, treeEditor, new DefaultTreeOperationLog(), new DefaultTreeOperationLog(), index, parentIndex);
   }
 
-  public IndexJungleTreeEditor(TreeNode newNode, TransactionManager _txManager, IndexTreeEditor _editor,
-      TreeOperationLog _log, TreeMap<String, TreeMap<String, List<TreeNode>>> index,TreeMap<TreeNode, TreeNode> parentIndex) {
+  public IndexJungleTreeEditor(TreeNode _root, TreeNode oldRoot, TransactionManager _txManager,
+      IndexTreeEditor treeEditor, TreeOperationLog log, TreeMap<String, TreeMap<String, List<TreeNode>>> index,
+      ParentIndex parentIndex) {
+    this(_root, oldRoot, _txManager, treeEditor, log, new DefaultTreeOperationLog(), index, parentIndex);
+  }
+
+  public IndexJungleTreeEditor(TreeNode newNode, TreeNode oldRoot, TransactionManager _txManager,
+      IndexTreeEditor _editor, TreeOperationLog _log, TreeOperationLog tmpLog,
+      TreeMap<String, TreeMap<String, List<TreeNode>>> index, ParentIndex parentIndex) {
     this.root = newNode;
+    this.oldRoot = oldRoot;
     this.txManager = _txManager;
     this.editor = _editor;
     this.log = _log;
     this.index = index;
     this.parentIndex = parentIndex;
+    this.tmpLog = tmpLog;
   }
 
-  
   public Either<Error, IndexJungleTreeEditor> _edit(final NodePath _path, NodeEditor _e, IndexEditor indexEditor) {
-    Either<Error,Triple<LoggingNode, TreeMap<TreeNode, TreeNode>,TreeMap<String,TreeMap<String,List<TreeNode>>>>> either = editor.edit(root, _path, _e, parentIndex, indexEditor);
+    Either<Error, LoggingNode> either = editor.edit(root, _path, _e);
     if (either.isA()) {
       return DefaultEither.newA(either.a());
     }
 
-    LoggingNode newLogging = either.b().getA();
-    TreeMap<TreeNode,TreeNode> newParentIndex = either.b().getB();
-    TreeMap<String,TreeMap<String,List<TreeNode>>> newIndex = either.b().getC();
+    LoggingNode newLogging = either.b();
     OperationLog newLog = newLogging.getOperationLog();
     TreeNode newNode = newLogging.getWrap();
 
@@ -80,8 +92,9 @@
 
     Iterable<TreeOperation> iterable = new IterableConverter<TreeOperation, NodeOperation>(newLog, converter);
     DefaultTreeOperationLog treeOperationLog = new DefaultTreeOperationLog(iterable, newLog.length());
-    TreeOperationLog newTreeOpLog = log.append(treeOperationLog);
-    IndexJungleTreeEditor newIndexTreeEditor = new IndexJungleTreeEditor(newNode, txManager, this.editor,newTreeOpLog, newIndex, newParentIndex);
+    TreeOperationLog newTmpLog = tmpLog.append(treeOperationLog);
+    IndexJungleTreeEditor newIndexTreeEditor = new IndexJungleTreeEditor(newNode, oldRoot, txManager, this.editor, log,
+        newTmpLog, index, parentIndex);
     return DefaultEither.newB(newIndexTreeEditor);
   }
 
@@ -134,17 +147,100 @@
 
   @Override
   public Either<Error, JungleTreeEditor> success() {
-    Either<Error, TransactionManager> either = txManager.commit(root, log, index,parentIndex);
+    ParentIndex newParentIndex = editParentIndex(tmpLog);
+    TreeOperationLog newLog = log.append(tmpLog);
+    Either<Error, TransactionManager> either = txManager.commit(root, newLog, index, newParentIndex);
     if (either.isA()) {
       return DefaultEither.newA(either.a());
     }
 
-    TransactionManager newTxManager = either.b(); 
-    JungleTreeEditor newTreeEditor = new IndexJungleTreeEditor(root, newTxManager, editor, index,parentIndex);
+    TransactionManager newTxManager = either.b();
+    JungleTreeEditor newTreeEditor = new IndexJungleTreeEditor(root, root, newTxManager, editor, index, parentIndex);
 
     return DefaultEither.newB(newTreeEditor);
   }
 
+  private ParentIndex editParentIndex(TreeOperationLog tmpLog) {
+    TreeMap<TreeNode, TreeNode> putParentNodeMap = TreeMap.empty(TreeMapOrd.treeNodeOrd);
+    TreeMap<TreeNode, TreeNode> deleteParentNodeMap = TreeMap.empty(TreeMapOrd.treeNodeOrd);
+    for (TreeOperation log : tmpLog) {
+
+      NodePath targetNodePath = log.getNodePath();
+      putParentNodeMap = getTargetNode(TreeMap.empty(TreeMapOrd.treeNodeOrd), root, targetNodePath);
+      deleteParentNodeMap = getTargetNode(TreeMap.empty(TreeMapOrd.treeNodeOrd), oldRoot, targetNodePath);
+      System.out.println(log.getNodePath().toString());
+    }
+
+    ParentIndex newParentIndex = parentIndex;
+    if (!deleteParentNodeMap.isEmpty())
+      newParentIndex = deleteParentIndex(putParentNodeMap, newParentIndex);
+
+    
+    if (!putParentNodeMap.isEmpty())
+      newParentIndex = putParentIndex(putParentNodeMap,newParentIndex);
+
+    return newParentIndex;
+  }
+
+  private ParentIndex deleteParentIndex(TreeMap<TreeNode, TreeNode> deleteParentNodeMap, ParentIndex editParentIndex) {
+    Iterator<P2<TreeNode, TreeNode>> parentNodeIterator = deleteParentNodeMap.iterator();
+    ParentIndex newParentIndex = editParentIndex;
+
+    for (; parentNodeIterator.hasNext();) {
+      TreeNode parentNode = parentNodeIterator.next()._1();
+      TreeNodeChildren children = parentNode.getChildren();
+      Iterator<TreeNode> childrenIterator = children.iterator();
+
+      for (; childrenIterator.hasNext();) {
+        TreeNode child = childrenIterator.next();
+        newParentIndex = newParentIndex.delete(child);
+      }
+    }
+    return newParentIndex;
+  }
+
+  private ParentIndex putParentIndex(TreeMap<TreeNode, TreeNode> putParentNodeMap,ParentIndex editParentIndex) {
+    Iterator<P2<TreeNode, TreeNode>> parentNodeIterator = putParentNodeMap.iterator();
+    ParentIndex newParentIndex = editParentIndex;
+
+    for (; parentNodeIterator.hasNext();) {
+      TreeNode parentNode = parentNodeIterator.next()._1();
+      TreeNodeChildren children = parentNode.getChildren();
+      Iterator<TreeNode> childrenIterator = children.iterator();
+
+      for (; childrenIterator.hasNext();) {
+        TreeNode child = childrenIterator.next();
+        newParentIndex = newParentIndex.set(child, parentNode);
+      }
+    }
+    return newParentIndex;
+  }
+
+  private TreeMap<TreeNode, TreeNode> getTargetNode(TreeMap<TreeNode, TreeNode> treeNodeMap, TreeNode node,
+      NodePath path) {
+    if (path.size() == 0)
+      return treeNodeMap;
+
+    Pair<Integer, NodePath> pathNode = path.pop();
+
+    if (pathNode.left() == -1) {
+      TreeMap<TreeNode, TreeNode> newTreeNodeMap = treeNodeMap.set(node, node);
+      return getTargetNode(newTreeNodeMap, node, pathNode.right());
+    }
+
+    Either<Error, TreeNode> either = node.getChildren().at(pathNode.left());
+    if (either.isA())
+      return treeNodeMap;
+
+    TreeNode child = either.b();
+    TreeMap<TreeNode, TreeNode> newTreeNodeMap = treeNodeMap.set(child, child);
+    if (pathNode.right().size() == 0)
+      return newTreeNodeMap;
+
+    return getTargetNode(newTreeNodeMap, child, pathNode.right());
+
+  }
+
   @Override
   public String getID() {
     return txManager.getUUID();