Поиск подстроки в объекте с использованием objectify - PullRequest
10 голосов
/ 10 августа 2011

У меня есть объект с именем lastName со значением "Бенджамин". Есть ли способ объективировать, что если пользователь поставил «Бен» или «Варенье» или «Беня». Я все еще смогу найти эту сущность используя query.filter (). Я должен использовать запрос, так как есть другие критерии поиска, которые я проверяю.

Я видел что-то в «Obgaektify», называемое оператором «начинается с». Но это не работает. Мы ценим любые предложения. Спасибо

Ответы [ 4 ]

12 голосов
/ 10 августа 2011

Нет запросов типа "LIKE" для подстроки, однако с учетом регистра"начинается с" можно смоделировать, используя преимущества операторов > и < для индексов.

// The start string
String searchStr = "Ben";

// emulate a "starts with" query
Query q = new Query("MyEntity")
q.addFilter("name", Query.FilterOperator.GREATER_THAN_OR_EQUAL, searchStr);
q.addFilter("name", Query.FilterOperator.LESS_THAN, searchStr + "\ufffd");

Запрос будет 'искать' свойство name для элементов, начинающихся с "Ben", и меньше чем "Ben\ufffd", где \ufffd - максимально возможный символ Юникода.

2 голосов
/ 10 августа 2011

Не существует стандартного существующего индекса для запросов, подобных содержанию.Кстати, вы всегда можете представить свой собственный.В этом случае вы можете сделать:

  1. add и синтетическое поле типа String[] lastNameIndex
  2. метод добавления, помеченный как @PrePersist, который заполнит поле lastNameIndex всеми доступными комбинациями
  3. Если вы хотите найти объекты, использующие этот индекс, выполните query.filter('lastNameIndex =', val)
0 голосов
/ 27 октября 2015

Я использовал метод токенизации.Вот код на Java:

private String tokenize(String phrase) {
StringBuilder tokens = new StringBuilder();
try {
  for (String word : phrase.split(" ")) {
    if (word.length() < 1) {
      continue;
    }
    int j = 1;
    while (true) {
      for (int i = 0; i < word.length() - j + 1; i++) {
        tokens.append(word.substring(i, i + j)).append(" ");
      }
      if (j == word.length()) {
        break;
      }
      j++;
    }
  }
} catch (Throwable t) {
  t.printStackTrace();
}
return tokens.toString();}

Это позволяет определить индексируемое поле, затем обрабатывать стандартные запросы Ofy и SearchService.

0 голосов
/ 23 февраля 2013

Соединяя ответ Криса и комментарий Ника, вот код для построения фильтра запросов для objectify V4:

public <T> Query<T> fieldStartsWith(Query<T> query, String field, String search){
    query = query.filter(field + " >=", search);
    return query.filter(field + " <", searchStr+"\ufffd");
}
...