Contacts dictionary rebuilds only when contact names have changed.

Bug: 6396600
Change-Id: Iad693ec4bab6351793d624e5c5b0a9f5c12a60e3
diff --git a/native/jni/src/bigram_dictionary.cpp b/native/jni/src/bigram_dictionary.cpp
index 0703108..7ed4dc4 100644
--- a/native/jni/src/bigram_dictionary.cpp
+++ b/native/jni/src/bigram_dictionary.cpp
@@ -128,7 +128,7 @@
                 ++bigramCount;
             }
         }
-    } while (0 != (UnigramDictionary::FLAG_ATTRIBUTE_HAS_NEXT & bigramFlags));
+    } while (UnigramDictionary::FLAG_ATTRIBUTE_HAS_NEXT & bigramFlags);
     return bigramCount;
 }
 
@@ -189,5 +189,25 @@
     return false;
 }
 
+bool BigramDictionary::isValidBigram(const int32_t *word1, int length1, const int32_t *word2,
+        int length2) {
+    const uint8_t* const root = DICT;
+    int pos = getBigramListPositionForWord(word1, length1);
+    // getBigramListPositionForWord returns 0 if this word isn't in the dictionary or has no bigrams
+    if (0 == pos) return false;
+    int nextWordPos = BinaryFormat::getTerminalPosition(root, word2, length2);
+    if (NOT_VALID_WORD == nextWordPos) return false;
+    int bigramFlags;
+    do {
+        bigramFlags = BinaryFormat::getFlagsAndForwardPointer(root, &pos);
+        const int bigramPos = BinaryFormat::getAttributeAddressAndForwardPointer(root, bigramFlags,
+                &pos);
+        if (bigramPos == nextWordPos) {
+            return true;
+        }
+    } while (UnigramDictionary::FLAG_ATTRIBUTE_HAS_NEXT & bigramFlags);
+    return false;
+}
+
 // TODO: Move functions related to bigram to here
 } // namespace latinime