diff options
Diffstat (limited to 'java/src/com/android/inputmethod/latin/personalization')
7 files changed, 108 insertions, 73 deletions
diff --git a/java/src/com/android/inputmethod/latin/personalization/UserHistoryDictionary.java b/java/src/com/android/inputmethod/latin/personalization/DynamicPredictionDictionaryBase.java index c76dea0bb..9d041f4eb 100644 --- a/java/src/com/android/inputmethod/latin/personalization/UserHistoryDictionary.java +++ b/java/src/com/android/inputmethod/latin/personalization/DynamicPredictionDictionaryBase.java @@ -1,5 +1,5 @@ /* - * Copyright (C) 2010 The Android Open Source Project + * 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. @@ -24,7 +24,6 @@ import android.util.Log; import com.android.inputmethod.annotations.UsedForTesting; import com.android.inputmethod.keyboard.ProximityInfo; import com.android.inputmethod.latin.Constants; -import com.android.inputmethod.latin.Dictionary; import com.android.inputmethod.latin.ExpandableDictionary; import com.android.inputmethod.latin.LatinImeLogger; import com.android.inputmethod.latin.SuggestedWords.SuggestedWordInfo; @@ -47,16 +46,17 @@ import java.util.ArrayList; import java.util.concurrent.locks.ReentrantLock; /** - * Locally gathers stats about the words user types and various other signals like auto-correction - * cancellation or manual picks. This allows the keyboard to adapt to the typist over time. + * This class is a base class of a dictionary for the personalized prediction language model. */ -public class UserHistoryDictionary extends ExpandableDictionary { - private static final String TAG = UserHistoryDictionary.class.getSimpleName(); - private static final String NAME = UserHistoryDictionary.class.getSimpleName(); +public abstract class DynamicPredictionDictionaryBase extends ExpandableDictionary { + public static void registerUpdateListener(PersonalizationDictionaryUpdateListener listener) { + // TODO: Implement + } + + private static final String TAG = DynamicPredictionDictionaryBase.class.getSimpleName(); public static final boolean DBG_SAVE_RESTORE = false; - public static final boolean DBG_STRESS_TEST = false; - public static final boolean DBG_ALWAYS_WRITE = false; - public static final boolean PROFILE_SAVE_RESTORE = LatinImeLogger.sDBG; + private static final boolean DBG_STRESS_TEST = false; + private static final boolean PROFILE_SAVE_RESTORE = LatinImeLogger.sDBG; private static final FormatOptions VERSION3 = new FormatOptions(3, true /* supportsDynamicUpdate */); @@ -65,14 +65,7 @@ public class UserHistoryDictionary extends ExpandableDictionary { private static final int FREQUENCY_FOR_TYPED = 2; /** Maximum number of pairs. Pruning will start when databases goes above this number. */ - public static final int MAX_HISTORY_BIGRAMS = 10000; - - /** - * When it hits maximum bigram pair, it will delete until you are left with - * only (sMaxHistoryBigrams - sDeleteHistoryBigrams) pairs. - * Do not keep this number small to avoid deleting too often. - */ - public static final int DELETE_HISTORY_BIGRAMS = 1000; + private static final int MAX_HISTORY_BIGRAMS = 10000; /** Locale for which this user history dictionary is storing words */ private final String mLocale; @@ -85,9 +78,9 @@ public class UserHistoryDictionary extends ExpandableDictionary { // Should always be false except when we use this class for test @UsedForTesting boolean isTest = false; - /* package */ UserHistoryDictionary(final Context context, final String locale, - final SharedPreferences sp) { - super(context, Dictionary.TYPE_USER_HISTORY); + /* package */ DynamicPredictionDictionaryBase(final Context context, final String locale, + final SharedPreferences sp, final String dictionaryType) { + super(context, dictionaryType); mLocale = locale; mPrefs = sp; if (mLocale != null && mLocale.length() > 1) { @@ -102,8 +95,8 @@ public class UserHistoryDictionary extends ExpandableDictionary { // Also, the database is written to somewhat frequently, so it needs to be kept alive // throughout the life of the process. // mOpenHelper.close(); - // Ignore close because we cache UserHistoryDictionary for each language. See getInstance() - // above. + // Ignore close because we cache PersonalizationPredictionDictionary for each language. + // See getInstance() above. // super.close(); } @@ -184,7 +177,7 @@ public class UserHistoryDictionary extends ExpandableDictionary { } @Override - public void loadDictionaryAsync() { + public final void loadDictionaryAsync() { // This must be run on non-main thread mBigramListLock.lock(); try { @@ -194,48 +187,47 @@ public class UserHistoryDictionary extends ExpandableDictionary { } } - private int profTotal; - private void loadDictionaryAsyncLocked() { + final int[] profTotalCount = { 0 }; + final String locale = getLocale(); if (DBG_STRESS_TEST) { try { - Log.w(TAG, "Start stress in loading: " + mLocale); + Log.w(TAG, "Start stress in loading: " + locale); Thread.sleep(15000); Log.w(TAG, "End stress in loading"); } catch (InterruptedException e) { } } - final long last = Settings.readLastUserHistoryWriteTime(mPrefs, mLocale); + final long last = Settings.readLastUserHistoryWriteTime(mPrefs, locale); final boolean initializing = last == 0; final long now = System.currentTimeMillis(); - profTotal = 0; - final String fileName = NAME + "." + mLocale + ".dict"; + final String fileName = getDictionaryFileName(); final ExpandableDictionary dictionary = this; final OnAddWordListener listener = new OnAddWordListener() { @Override public void setUnigram(final String word, final String shortcutTarget, final int frequency) { - profTotal++; if (DBG_SAVE_RESTORE) { Log.d(TAG, "load unigram: " + word + "," + frequency); } dictionary.addWord(word, shortcutTarget, frequency); - mBigramList.addBigram(null, word, (byte)frequency); + ++profTotalCount[0]; + addToBigramListLocked(null, word, (byte)frequency); } @Override public void setBigram(final String word1, final String word2, final int frequency) { if (word1.length() < Constants.DICTIONARY_MAX_WORD_LENGTH && word2.length() < Constants.DICTIONARY_MAX_WORD_LENGTH) { - profTotal++; if (DBG_SAVE_RESTORE) { Log.d(TAG, "load bigram: " + word1 + "," + word2 + "," + frequency); } + ++profTotalCount[0]; dictionary.setBigramAndGetFrequency( word1, word2, initializing ? new ForgettingCurveParams(true) : new ForgettingCurveParams(frequency, now, last)); } - mBigramList.addBigram(word1, word2, (byte)frequency); + addToBigramListLocked(word1, word2, (byte)frequency); } }; @@ -264,11 +256,21 @@ public class UserHistoryDictionary extends ExpandableDictionary { if (PROFILE_SAVE_RESTORE) { final long diff = System.currentTimeMillis() - now; Log.d(TAG, "PROF: Load UserHistoryDictionary: " - + mLocale + ", " + diff + "ms. load " + profTotal + "entries."); + + locale + ", " + diff + "ms. load " + profTotalCount[0] + "entries."); } } } + protected abstract String getDictionaryFileName(); + + protected String getLocale() { + return mLocale; + } + + private void addToBigramListLocked(String word0, String word1, byte fcValue) { + mBigramList.addBigram(word0, word1, fcValue); + } + /** * Async task to write pending words to the binarydicts. */ @@ -277,16 +279,16 @@ public class UserHistoryDictionary extends ExpandableDictionary { private final UserHistoryDictionaryBigramList mBigramList; private final boolean mAddLevel0Bigrams; private final String mLocale; - private final UserHistoryDictionary mUserHistoryDictionary; + private final DynamicPredictionDictionaryBase mDynamicPredictionDictionary; private final SharedPreferences mPrefs; private final Context mContext; public UpdateBinaryTask(final UserHistoryDictionaryBigramList pendingWrites, - final String locale, final UserHistoryDictionary dict, + final String locale, final DynamicPredictionDictionaryBase dict, final SharedPreferences prefs, final Context context) { mBigramList = pendingWrites; mLocale = locale; - mUserHistoryDictionary = dict; + mDynamicPredictionDictionary = dict; mPrefs = prefs; mContext = context; mAddLevel0Bigrams = mBigramList.size() <= MAX_HISTORY_BIGRAMS; @@ -294,19 +296,19 @@ public class UserHistoryDictionary extends ExpandableDictionary { @Override protected Void doInBackground(final Void... v) { - if (mUserHistoryDictionary.isTest) { + if (mDynamicPredictionDictionary.isTest) { // If isTest == true, wait until the lock is released. - mUserHistoryDictionary.mBigramListLock.lock(); + mDynamicPredictionDictionary.mBigramListLock.lock(); try { doWriteTaskLocked(); } finally { - mUserHistoryDictionary.mBigramListLock.unlock(); + mDynamicPredictionDictionary.mBigramListLock.unlock(); } - } else if (mUserHistoryDictionary.mBigramListLock.tryLock()) { + } else if (mDynamicPredictionDictionary.mBigramListLock.tryLock()) { try { doWriteTaskLocked(); } finally { - mUserHistoryDictionary.mBigramListLock.unlock(); + mDynamicPredictionDictionary.mBigramListLock.unlock(); } } return null; @@ -324,7 +326,8 @@ public class UserHistoryDictionary extends ExpandableDictionary { } final long now = PROFILE_SAVE_RESTORE ? System.currentTimeMillis() : 0; - final String fileName = NAME + "." + mLocale + ".dict"; + final String fileName = + mDynamicPredictionDictionary.getDictionaryFileName(); final File file = new File(mContext.getFilesDir(), fileName); FileOutputStream out = null; @@ -360,7 +363,8 @@ public class UserHistoryDictionary extends ExpandableDictionary { freq = FREQUENCY_FOR_TYPED; final byte prevFc = mBigramList.getBigrams(word1).get(word2); } else { // bigram - final NextWord nw = mUserHistoryDictionary.getBigramWord(word1, word2); + final NextWord nw = + mDynamicPredictionDictionary.getBigramWord(word1, word2); if (nw != null) { final ForgettingCurveParams fcp = nw.getFcParams(); final byte prevFc = mBigramList.getBigrams(word1).get(word2); diff --git a/java/src/com/android/inputmethod/latin/personalization/PersonalizationDicitonary.java b/java/src/com/android/inputmethod/latin/personalization/PersonalizationDictionary.java index d3e2dfec9..19554d639 100644 --- a/java/src/com/android/inputmethod/latin/personalization/PersonalizationDicitonary.java +++ b/java/src/com/android/inputmethod/latin/personalization/PersonalizationDictionary.java @@ -24,7 +24,7 @@ import android.content.Context; /** * This class is a dictionary for the personalized language model that uses binary dictionary. */ -public class PersonalizationDicitonary extends ExpandableBinaryDictionary { +public class PersonalizationDictionary extends ExpandableBinaryDictionary { private static final String NAME = "personalization"; public static void registerUpdateListener(PersonalizationDictionaryUpdateListener listener) { @@ -35,7 +35,7 @@ public class PersonalizationDicitonary extends ExpandableBinaryDictionary { private final String mLocale; // Singleton - private PersonalizationDicitonary(final Context context, final String locale) { + private PersonalizationDictionary(final Context context, final String locale) { super(context, getFilenameWithLocale(NAME, locale), Dictionary.TYPE_PERSONALIZATION); mLocale = locale; } diff --git a/java/src/com/android/inputmethod/latin/personalization/PersonalizationDictionaryHelper.java b/java/src/com/android/inputmethod/latin/personalization/PersonalizationDictionaryHelper.java index e09e834bf..f5dae99ef 100644 --- a/java/src/com/android/inputmethod/latin/personalization/PersonalizationDictionaryHelper.java +++ b/java/src/com/android/inputmethod/latin/personalization/PersonalizationDictionaryHelper.java @@ -29,15 +29,16 @@ public class PersonalizationDictionaryHelper { private static final String TAG = PersonalizationDictionaryHelper.class.getSimpleName(); private static final boolean DEBUG = false; - private static final ConcurrentHashMap<String, SoftReference<UserHistoryDictionary>> + private static final ConcurrentHashMap<String, SoftReference<UserHistoryPredictionDictionary>> sLangDictCache = CollectionUtils.newConcurrentHashMap(); - public static UserHistoryDictionary getUserHistoryDictionary( + public static UserHistoryPredictionDictionary getUserHistoryPredictionDictionary( final Context context, final String locale, final SharedPreferences sp) { synchronized (sLangDictCache) { if (sLangDictCache.containsKey(locale)) { - final SoftReference<UserHistoryDictionary> ref = sLangDictCache.get(locale); - final UserHistoryDictionary dict = ref == null ? null : ref.get(); + final SoftReference<UserHistoryPredictionDictionary> ref = + sLangDictCache.get(locale); + final UserHistoryPredictionDictionary dict = ref == null ? null : ref.get(); if (dict != null) { if (DEBUG) { Log.w(TAG, "Use cached UserHistoryDictionary for " + locale); @@ -45,8 +46,9 @@ public class PersonalizationDictionaryHelper { return dict; } } - final UserHistoryDictionary dict = new UserHistoryDictionary(context, locale, sp); - sLangDictCache.put(locale, new SoftReference<UserHistoryDictionary>(dict)); + final UserHistoryPredictionDictionary dict = + new UserHistoryPredictionDictionary(context, locale, sp); + sLangDictCache.put(locale, new SoftReference<UserHistoryPredictionDictionary>(dict)); return dict; } } diff --git a/java/src/com/android/inputmethod/latin/personalization/PersonalizationDictionaryUpdateListener.java b/java/src/com/android/inputmethod/latin/personalization/PersonalizationDictionaryUpdateListener.java index 2ec0dc00c..c78e5a95b 100644 --- a/java/src/com/android/inputmethod/latin/personalization/PersonalizationDictionaryUpdateListener.java +++ b/java/src/com/android/inputmethod/latin/personalization/PersonalizationDictionaryUpdateListener.java @@ -16,6 +16,6 @@ package com.android.inputmethod.latin.personalization; -public class PersonalizationDictionaryUpdateListener { +public interface PersonalizationDictionaryUpdateListener { // TODO: Implement } diff --git a/java/src/com/android/inputmethod/latin/personalization/PersonalizationPredictionDictionary.java b/java/src/com/android/inputmethod/latin/personalization/PersonalizationPredictionDictionary.java new file mode 100644 index 000000000..955bd2762 --- /dev/null +++ b/java/src/com/android/inputmethod/latin/personalization/PersonalizationPredictionDictionary.java @@ -0,0 +1,36 @@ +/* + * 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. + */ + +package com.android.inputmethod.latin.personalization; + +import com.android.inputmethod.latin.Dictionary; + +import android.content.Context; +import android.content.SharedPreferences; + +public class PersonalizationPredictionDictionary extends DynamicPredictionDictionaryBase { + private static final String NAME = PersonalizationPredictionDictionary.class.getSimpleName(); + + /* package */ PersonalizationPredictionDictionary(final Context context, final String locale, + final SharedPreferences sp) { + super(context, locale, sp, Dictionary.TYPE_PERSONALIZATION_PREDICTION_IN_JAVA); + } + + @Override + protected String getDictionaryFileName() { + return NAME + "." + getLocale() + ".dict"; + } +} diff --git a/java/src/com/android/inputmethod/latin/personalization/UserHistoryDictionaryBigramList.java b/java/src/com/android/inputmethod/latin/personalization/UserHistoryDictionaryBigramList.java index b93630a18..f21db25a6 100644 --- a/java/src/com/android/inputmethod/latin/personalization/UserHistoryDictionaryBigramList.java +++ b/java/src/com/android/inputmethod/latin/personalization/UserHistoryDictionaryBigramList.java @@ -53,7 +53,7 @@ public final class UserHistoryDictionaryBigramList { * Called when loaded from the SQL DB. */ public void addBigram(String word1, String word2, byte fcValue) { - if (UserHistoryDictionary.DBG_SAVE_RESTORE) { + if (UserHistoryPredictionDictionary.DBG_SAVE_RESTORE) { Log.d(TAG, "--- add bigram: " + word1 + ", " + word2 + ", " + fcValue); } final HashMap<String, Byte> map; @@ -73,7 +73,7 @@ public final class UserHistoryDictionaryBigramList { * Called when inserted to the SQL DB. */ public void updateBigram(String word1, String word2, byte fcValue) { - if (UserHistoryDictionary.DBG_SAVE_RESTORE) { + if (UserHistoryPredictionDictionary.DBG_SAVE_RESTORE) { Log.d(TAG, "--- update bigram: " + word1 + ", " + word2 + ", " + fcValue); } final HashMap<String, Byte> map; diff --git a/java/src/com/android/inputmethod/latin/personalization/PersonalizationPredictionDicitonary.java b/java/src/com/android/inputmethod/latin/personalization/UserHistoryPredictionDictionary.java index 3e7772584..d11784454 100644 --- a/java/src/com/android/inputmethod/latin/personalization/PersonalizationPredictionDicitonary.java +++ b/java/src/com/android/inputmethod/latin/personalization/UserHistoryPredictionDictionary.java @@ -17,30 +17,23 @@ package com.android.inputmethod.latin.personalization; import com.android.inputmethod.latin.Dictionary; -import com.android.inputmethod.latin.ExpandableDictionary; import android.content.Context; import android.content.SharedPreferences; /** - * This class is a dictionary for the personalized prediction language model implemented in Java. + * Locally gathers stats about the words user types and various other signals like auto-correction + * cancellation or manual picks. This allows the keyboard to adapt to the typist over time. */ -public class PersonalizationPredictionDicitonary extends ExpandableDictionary { - public static void registerUpdateListener(PersonalizationDictionaryUpdateListener listener) { - // TODO: Implement - } - - /** Locale for which this user history dictionary is storing words */ - private final String mLocale; - private final SharedPreferences mPrefs; - - // Singleton - private PersonalizationPredictionDicitonary(final Context context, final String locale, +public class UserHistoryPredictionDictionary extends DynamicPredictionDictionaryBase { + private static final String NAME = UserHistoryPredictionDictionary.class.getSimpleName(); + /* package */ UserHistoryPredictionDictionary(final Context context, final String locale, final SharedPreferences sp) { - super(context, Dictionary.TYPE_PERSONALIZATION_PREDICTION_IN_JAVA); - mLocale = locale; - mPrefs = sp; + super(context, locale, sp, Dictionary.TYPE_USER_HISTORY); } - // TODO: Implement + @Override + protected String getDictionaryFileName() { + return NAME + "." + getLocale() + ".dict"; + } } |