summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorderat@chromium.org <derat@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2012-09-11 02:48:41 +0000
committerderat@chromium.org <derat@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2012-09-11 02:48:41 +0000
commit3b81314d0b013f2ebcccab76a57aea0df4bfc169 (patch)
treeda7261a067086580e3a44515bad2c87585d1a8e3
parentcfc84156401287b783f439024f61c8a477087362 (diff)
downloadchromium_src-3b81314d0b013f2ebcccab76a57aea0df4bfc169.zip
chromium_src-3b81314d0b013f2ebcccab76a57aea0df4bfc169.tar.gz
chromium_src-3b81314d0b013f2ebcccab76a57aea0df4bfc169.tar.bz2
autocomplete: Add AutocompleteMatch::MergeClassifications()
This just moves a classifications-merging loop from ShortcutsProvider::ClassifyAllMatchesInString() into a utility method. BUG=141877 TEST=none Review URL: https://chromiumcodereview.appspot.com/10911188 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@155919 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r--chrome/browser/autocomplete/autocomplete_match.cc41
-rw-r--r--chrome/browser/autocomplete/autocomplete_match.h6
-rw-r--r--chrome/browser/autocomplete/autocomplete_match_unittest.cc70
-rw-r--r--chrome/browser/autocomplete/shortcuts_provider.cc20
-rw-r--r--chrome/browser/autocomplete/shortcuts_provider_unittest.cc5
5 files changed, 122 insertions, 20 deletions
diff --git a/chrome/browser/autocomplete/autocomplete_match.cc b/chrome/browser/autocomplete/autocomplete_match.cc
index d00ac97..a8b092d 100644
--- a/chrome/browser/autocomplete/autocomplete_match.cc
+++ b/chrome/browser/autocomplete/autocomplete_match.cc
@@ -19,6 +19,16 @@
#include "content/public/common/url_constants.h"
#include "grit/theme_resources.h"
+namespace {
+
+bool IsTrivialClassification(const ACMatchClassifications& classifications) {
+ return classifications.empty() ||
+ ((classifications.size() == 1) &&
+ (classifications.back().style == ACMatchClassification::NONE));
+}
+
+} // namespace
+
// AutocompleteMatch ----------------------------------------------------------
// static
@@ -233,6 +243,37 @@ void AutocompleteMatch::ClassifyLocationInString(
}
// static
+AutocompleteMatch::ACMatchClassifications
+ AutocompleteMatch::MergeClassifications(
+ const ACMatchClassifications& classifications1,
+ const ACMatchClassifications& classifications2) {
+ // We must return the empty vector only if both inputs are truly empty.
+ // The result of merging an empty vector with a single (0, NONE)
+ // classification is the latter one-entry vector.
+ if (IsTrivialClassification(classifications1))
+ return classifications2.empty() ? classifications1 : classifications2;
+ if (IsTrivialClassification(classifications2))
+ return classifications1;
+
+ ACMatchClassifications output;
+ for (ACMatchClassifications::const_iterator i = classifications1.begin(),
+ j = classifications2.begin(); i != classifications1.end();) {
+ AutocompleteMatch::AddLastClassificationIfNecessary(&output,
+ std::max(i->offset, j->offset), i->style | j->style);
+ const size_t next_i_offset = (i + 1) == classifications1.end() ?
+ static_cast<size_t>(-1) : (i + 1)->offset;
+ const size_t next_j_offset = (j + 1) == classifications2.end() ?
+ static_cast<size_t>(-1) : (j + 1)->offset;
+ if (next_i_offset >= next_j_offset)
+ ++j;
+ if (next_j_offset >= next_i_offset)
+ ++i;
+ }
+
+ return output;
+}
+
+// static
std::string AutocompleteMatch::ClassificationsToString(
const ACMatchClassifications& classifications) {
std::string serialized_classifications;
diff --git a/chrome/browser/autocomplete/autocomplete_match.h b/chrome/browser/autocomplete/autocomplete_match.h
index 3296ac4..ca32458 100644
--- a/chrome/browser/autocomplete/autocomplete_match.h
+++ b/chrome/browser/autocomplete/autocomplete_match.h
@@ -144,6 +144,12 @@ struct AutocompleteMatch {
int style,
ACMatchClassifications* classifications);
+ // Returns a new vector of classifications containing the merged contents of
+ // |classifications1| and |classifications2|.
+ static ACMatchClassifications MergeClassifications(
+ const ACMatchClassifications& classifications1,
+ const ACMatchClassifications& classifications2);
+
// Converts classifications to and from a serialized string representation
// (using comma-separated integers to sequentially list positions and styles).
static std::string ClassificationsToString(
diff --git a/chrome/browser/autocomplete/autocomplete_match_unittest.cc b/chrome/browser/autocomplete/autocomplete_match_unittest.cc
index b8fe4ed..1d0e4d2 100644
--- a/chrome/browser/autocomplete/autocomplete_match_unittest.cc
+++ b/chrome/browser/autocomplete/autocomplete_match_unittest.cc
@@ -31,3 +31,73 @@ TEST(AutocompleteMatchTest, MoreRelevant) {
AutocompleteMatch::MoreRelevant(m1, m2));
}
}
+
+TEST(AutocompleteMatchTest, MergeClassifications) {
+ // Merging two empty vectors should result in an empty vector.
+ EXPECT_EQ(std::string(),
+ AutocompleteMatch::ClassificationsToString(
+ AutocompleteMatch::MergeClassifications(
+ AutocompleteMatch::ACMatchClassifications(),
+ AutocompleteMatch::ACMatchClassifications())));
+
+ // If one vector is empty and the other is "trivial" but non-empty (i.e. (0,
+ // NONE)), the non-empty vector should be returned.
+ EXPECT_EQ("0,0",
+ AutocompleteMatch::ClassificationsToString(
+ AutocompleteMatch::MergeClassifications(
+ AutocompleteMatch::ClassificationsFromString("0,0"),
+ AutocompleteMatch::ACMatchClassifications())));
+ EXPECT_EQ("0,0",
+ AutocompleteMatch::ClassificationsToString(
+ AutocompleteMatch::MergeClassifications(
+ AutocompleteMatch::ACMatchClassifications(),
+ AutocompleteMatch::ClassificationsFromString("0,0"))));
+
+ // Ditto if the one-entry vector is non-trivial.
+ EXPECT_EQ("0,1",
+ AutocompleteMatch::ClassificationsToString(
+ AutocompleteMatch::MergeClassifications(
+ AutocompleteMatch::ClassificationsFromString("0,1"),
+ AutocompleteMatch::ACMatchClassifications())));
+ EXPECT_EQ("0,1",
+ AutocompleteMatch::ClassificationsToString(
+ AutocompleteMatch::MergeClassifications(
+ AutocompleteMatch::ACMatchClassifications(),
+ AutocompleteMatch::ClassificationsFromString("0,1"))));
+
+ // Merge an unstyled one-entry vector with a styled one-entry vector.
+ EXPECT_EQ("0,1",
+ AutocompleteMatch::ClassificationsToString(
+ AutocompleteMatch::MergeClassifications(
+ AutocompleteMatch::ClassificationsFromString("0,0"),
+ AutocompleteMatch::ClassificationsFromString("0,1"))));
+
+ // Test simple cases of overlap.
+ EXPECT_EQ("0,3," "1,2",
+ AutocompleteMatch::ClassificationsToString(
+ AutocompleteMatch::MergeClassifications(
+ AutocompleteMatch::ClassificationsFromString("0,1," "1,0"),
+ AutocompleteMatch::ClassificationsFromString("0,2"))));
+ EXPECT_EQ("0,3," "1,2",
+ AutocompleteMatch::ClassificationsToString(
+ AutocompleteMatch::MergeClassifications(
+ AutocompleteMatch::ClassificationsFromString("0,2"),
+ AutocompleteMatch::ClassificationsFromString("0,1," "1,0"))));
+
+ // Test the case where both vectors have classifications at the same
+ // positions.
+ EXPECT_EQ("0,3",
+ AutocompleteMatch::ClassificationsToString(
+ AutocompleteMatch::MergeClassifications(
+ AutocompleteMatch::ClassificationsFromString("0,1," "1,2"),
+ AutocompleteMatch::ClassificationsFromString("0,2," "1,1"))));
+
+ // Test an arbitrary complicated case.
+ EXPECT_EQ("0,2," "1,0," "2,1," "4,3," "5,7," "6,3," "7,7," "15,1," "17,0",
+ AutocompleteMatch::ClassificationsToString(
+ AutocompleteMatch::MergeClassifications(
+ AutocompleteMatch::ClassificationsFromString(
+ "0,0," "2,1," "4,3," "7,7," "10,6," "15,0"),
+ AutocompleteMatch::ClassificationsFromString(
+ "0,2," "1,0," "5,7," "6,1," "17,0"))));
+}
diff --git a/chrome/browser/autocomplete/shortcuts_provider.cc b/chrome/browser/autocomplete/shortcuts_provider.cc
index 5e320e7..0b52176 100644
--- a/chrome/browser/autocomplete/shortcuts_provider.cc
+++ b/chrome/browser/autocomplete/shortcuts_provider.cc
@@ -294,25 +294,7 @@ ACMatchClassifications ShortcutsProvider::ClassifyAllMatchesInString(
last_position = std::max(last_position, next_character);
}
- // Merge match-marking data with original classifications.
- if ((match_class.size() == 1) &&
- (match_class.back().style == ACMatchClassification::NONE))
- return original_class;
- ACMatchClassifications output;
- for (ACMatchClassifications::const_iterator i = original_class.begin(),
- j = match_class.begin(); i != original_class.end();) {
- AutocompleteMatch::AddLastClassificationIfNecessary(&output,
- std::max(i->offset, j->offset), i->style | j->style);
- const size_t next_i_offset = (i + 1) == original_class.end() ?
- static_cast<size_t>(-1) : (i + 1)->offset;
- const size_t next_j_offset = (j + 1) == match_class.end() ?
- static_cast<size_t>(-1) : (j + 1)->offset;
- if (next_i_offset >= next_j_offset)
- ++j;
- if (next_j_offset >= next_i_offset)
- ++i;
- }
- return output;
+ return AutocompleteMatch::MergeClassifications(original_class, match_class);
}
history::ShortcutsBackend::ShortcutMap::const_iterator
diff --git a/chrome/browser/autocomplete/shortcuts_provider_unittest.cc b/chrome/browser/autocomplete/shortcuts_provider_unittest.cc
index 85a6524..740846e 100644
--- a/chrome/browser/autocomplete/shortcuts_provider_unittest.cc
+++ b/chrome/browser/autocomplete/shortcuts_provider_unittest.cc
@@ -506,7 +506,10 @@ TEST_F(ShortcutsProviderTest, ClassifyAllMatchesInString) {
// Extra parens in the next line hack around C++03's "most vexing parse".
class ClassifyTest classify_test5((string16()), ACMatchClassifications());
ACMatchClassifications spans_j = classify_test5.RunTest(ASCIIToUTF16("man"));
- ASSERT_EQ(0U, spans_j.size());
+ ASSERT_EQ(1U, spans_j.size());
+ EXPECT_EQ(0U, spans_j.front().offset);
+ EXPECT_EQ(AutocompleteMatch::ACMatchClassification::NONE,
+ spans_j.front().style);
// Matches which end at beginning of classification merge properly.
matches.clear();