Как эффективно удалить строки из таблицы на основе текстового поиска?

0

Нечетный вопрос к фразе, но немного легче объяснить в структуре таблицы. Два стола:

CREATE TABLE 'posts' (
  'id' bigint(20) AUTO_INCREMENT,
  'text' mediumtext,
  PRIMARY KEY ('id')
);

CREATE TABLE 'dictionary' (
  'id' bigint(20) AUTO_INCREMENT,
  'term' varchar(255),
  'definition' varchar(255),
  PRIMARY KEY ('id'),
  UNIQUE KEY 'ix_term' ('term')
);

Таблица posts содержит большие проходы произвольного текста. Таблица dictionary поддерживает отображение терминов (то есть отдельных слов, которые могут встречаться в тексте) и их определения (более широкое значение).

Пример некоторых данных по posts:

+----+-----------+
| id | text      |
+----+-----------+
|  1 | foo       |
|  2 | bar       |
|  3 | foo bar   |
|  4 | foobarbaz |
+----+-----------+

Пример некоторых данных dictionary:

+----+------+--------------------------+
| id | term | definition               |
+----+------+--------------------------+
|  1 | foo  | A foo is a foo.          |
|  2 | bar  | A bar is a bar.          |
|  3 | baz  | A baz is something else. |
|  4 | quux | Who knows.               |
+----+------+--------------------------+

В данных примера есть запись словаря для термина quux, который не отображается в тексте любых сообщений. Я хотел бы удалить такие неиспользуемые строки из таблицы словаря, но из-за компоновки схемы, похоже, не особенно эффективный способ сделать это.

Лучшее, что я смог собрать, - это:

DELETE 'dictionary' FROM 'dictionary'
LEFT JOIN 'posts' ON 'posts'.'text' LIKE CONCAT('%', 'dictionary'.'term', '%')
WHERE 'posts'.'id' IS NULL;

... и это sloooow. Мне интересно, есть ли более эффективный способ построения условия JOIN или лучший способ сделать LIKE %...% или совсем другой подход к поиску posts.text который будет работать быстрее.

(В стороне, я признаю, что наличие многого числа, которое связывает posts с соответствующими строками dictionary было бы гораздо более эффективным способом поддерживать и искать эти данные, но код приложения - это то, что он есть.)

Теги:
left-join

1 ответ

1

Создать таблицу как select (CTAS) должна работать быстрее, чем удалить с помощью соединения.

  1. CTAS where exists:

CREATE TABLE dictionary_new AS выберите * из dictionary где существует (выберите 1 из posts где posts. text LIKE CONCAT ('%', dictionary term, '%'))

;

  1. Удалить исходный стол

    drop table dictionary;

  2. Переименовать таблицу

    RENAME TABLE dictionary_new TO dictionary;

4.Создать ограничения

ALTER TABLE  'dictionary' ADD PRIMARY KEY(id);
ALTER TABLE  'dictionary' ADD UNIQUE KEY 'ix_term' ('term')

Ещё вопросы

Сообщество Overcoder
Наверх
Меню