Index: third_party/android_prediction/suggest/policyimpl/dictionary/structure/pt_common/dynamic_pt_gc_event_listeners.cpp |
diff --git a/third_party/android_prediction/suggest/policyimpl/dictionary/structure/pt_common/dynamic_pt_gc_event_listeners.cpp b/third_party/android_prediction/suggest/policyimpl/dictionary/structure/pt_common/dynamic_pt_gc_event_listeners.cpp |
new file mode 100644 |
index 0000000000000000000000000000000000000000..ba13b800fc9f60f9345be97e534a0eca605cefae |
--- /dev/null |
+++ b/third_party/android_prediction/suggest/policyimpl/dictionary/structure/pt_common/dynamic_pt_gc_event_listeners.cpp |
@@ -0,0 +1,144 @@ |
+/* |
+ * Copyright (C) 2013 The Android Open Source Project |
+ * |
+ * Licensed under the Apache License, Version 2.0 (the "License"); |
+ * you may not use this file except in compliance with the License. |
+ * You may obtain a copy of the License at |
+ * |
+ * http://www.apache.org/licenses/LICENSE-2.0 |
+ * |
+ * Unless required by applicable law or agreed to in writing, software |
+ * distributed under the License is distributed on an "AS IS" BASIS, |
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
+ * See the License for the specific language governing permissions and |
+ * limitations under the License. |
+ */ |
+ |
+#include "third_party/android_prediction/suggest/policyimpl/dictionary/structure/pt_common/dynamic_pt_gc_event_listeners.h" |
+ |
+#include "third_party/android_prediction/suggest/core/policy/dictionary_header_structure_policy.h" |
+#include "third_party/android_prediction/suggest/policyimpl/dictionary/structure/pt_common/dynamic_pt_writing_utils.h" |
+#include "third_party/android_prediction/suggest/policyimpl/dictionary/structure/pt_common/pt_node_params.h" |
+#include "third_party/android_prediction/suggest/policyimpl/dictionary/structure/pt_common/pt_node_writer.h" |
+ |
+namespace latinime { |
+ |
+bool DynamicPtGcEventListeners |
+ ::TraversePolicyToUpdateUnigramProbabilityAndMarkUselessPtNodesAsDeleted |
+ ::onVisitingPtNode(const PtNodeParams *const ptNodeParams) { |
+ // PtNode is useless when the PtNode is not a terminal and doesn't have any not useless |
+ // children. |
+ bool isUselessPtNode = !ptNodeParams->isTerminal(); |
+ if (ptNodeParams->isTerminal() && !ptNodeParams->representsNonWordInfo()) { |
+ bool needsToKeepPtNode = true; |
+ if (!mPtNodeWriter->updatePtNodeProbabilityAndGetNeedsToKeepPtNodeAfterGC( |
+ ptNodeParams, &needsToKeepPtNode)) { |
+ AKLOGE("Cannot update PtNode probability or get needs to keep PtNode after GC."); |
+ return false; |
+ } |
+ if (!needsToKeepPtNode) { |
+ isUselessPtNode = true; |
+ } |
+ } |
+ if (mChildrenValue > 0) { |
+ isUselessPtNode = false; |
+ } else if (ptNodeParams->isTerminal()) { |
+ // Remove children as all children are useless. |
+ if (!mPtNodeWriter->updateChildrenPosition(ptNodeParams, |
+ NOT_A_DICT_POS /* newChildrenPosition */)) { |
+ return false; |
+ } |
+ } |
+ if (isUselessPtNode) { |
+ // Current PtNode is no longer needed. Mark it as deleted. |
+ if (!mPtNodeWriter->markPtNodeAsDeleted(ptNodeParams)) { |
+ return false; |
+ } |
+ } else { |
+ mValueStack.back() += 1; |
+ if (ptNodeParams->isTerminal() && !ptNodeParams->representsNonWordInfo()) { |
+ mValidUnigramCount += 1; |
+ } |
+ } |
+ return true; |
+} |
+ |
+bool DynamicPtGcEventListeners::TraversePolicyToUpdateBigramProbability |
+ ::onVisitingPtNode(const PtNodeParams *const ptNodeParams) { |
+ if (!ptNodeParams->isDeleted()) { |
+ int bigramEntryCount = 0; |
+ if (!mPtNodeWriter->updateAllBigramEntriesAndDeleteUselessEntries(ptNodeParams, |
+ &bigramEntryCount)) { |
+ return false; |
+ } |
+ mValidBigramEntryCount += bigramEntryCount; |
+ } |
+ return true; |
+} |
+ |
+// Writes dummy PtNode array size when the head of PtNode array is read. |
+bool DynamicPtGcEventListeners::TraversePolicyToPlaceAndWriteValidPtNodesToBuffer |
+ ::onDescend(const int ptNodeArrayPos) { |
+ mValidPtNodeCount = 0; |
+ int writingPos = mBufferToWrite->getTailPosition(); |
+ mDictPositionRelocationMap->mPtNodeArrayPositionRelocationMap.insert( |
+ PtNodeWriter::PtNodeArrayPositionRelocationMap::value_type(ptNodeArrayPos, writingPos)); |
+ // Writes dummy PtNode array size because arrays can have a forward link or needles PtNodes. |
+ // This field will be updated later in onReadingPtNodeArrayTail() with actual PtNode count. |
+ mPtNodeArraySizeFieldPos = writingPos; |
+ return DynamicPtWritingUtils::writePtNodeArraySizeAndAdvancePosition( |
+ mBufferToWrite, 0 /* arraySize */, &writingPos); |
+} |
+ |
+// Write PtNode array terminal and actual PtNode array size. |
+bool DynamicPtGcEventListeners::TraversePolicyToPlaceAndWriteValidPtNodesToBuffer |
+ ::onReadingPtNodeArrayTail() { |
+ int writingPos = mBufferToWrite->getTailPosition(); |
+ // Write PtNode array terminal. |
+ if (!DynamicPtWritingUtils::writeForwardLinkPositionAndAdvancePosition( |
+ mBufferToWrite, NOT_A_DICT_POS /* forwardLinkPos */, &writingPos)) { |
+ return false; |
+ } |
+ // Write actual PtNode array size. |
+ if (!DynamicPtWritingUtils::writePtNodeArraySizeAndAdvancePosition( |
+ mBufferToWrite, mValidPtNodeCount, &mPtNodeArraySizeFieldPos)) { |
+ return false; |
+ } |
+ return true; |
+} |
+ |
+// Write valid PtNode to buffer and memorize mapping from the old position to the new position. |
+bool DynamicPtGcEventListeners::TraversePolicyToPlaceAndWriteValidPtNodesToBuffer |
+ ::onVisitingPtNode(const PtNodeParams *const ptNodeParams) { |
+ if (ptNodeParams->isDeleted()) { |
+ // Current PtNode is not written in new buffer because it has been deleted. |
+ mDictPositionRelocationMap->mPtNodePositionRelocationMap.insert( |
+ PtNodeWriter::PtNodePositionRelocationMap::value_type( |
+ ptNodeParams->getHeadPos(), NOT_A_DICT_POS)); |
+ return true; |
+ } |
+ int writingPos = mBufferToWrite->getTailPosition(); |
+ mDictPositionRelocationMap->mPtNodePositionRelocationMap.insert( |
+ PtNodeWriter::PtNodePositionRelocationMap::value_type( |
+ ptNodeParams->getHeadPos(), writingPos)); |
+ mValidPtNodeCount++; |
+ // Writes current PtNode. |
+ return mPtNodeWriter->writePtNodeAndAdvancePosition(ptNodeParams, &writingPos); |
+} |
+ |
+bool DynamicPtGcEventListeners::TraversePolicyToUpdateAllPositionFields |
+ ::onVisitingPtNode(const PtNodeParams *const ptNodeParams) { |
+ // Updates parent position. |
+ int bigramCount = 0; |
+ if (!mPtNodeWriter->updateAllPositionFields(ptNodeParams, mDictPositionRelocationMap, |
+ &bigramCount)) { |
+ return false; |
+ } |
+ mBigramCount += bigramCount; |
+ if (ptNodeParams->isTerminal()) { |
+ mUnigramCount++; |
+ } |
+ return true; |
+} |
+ |
+} // namespace latinime |