sql >> Base de Datos >  >> RDS >> Mysql

¿Cuál es la mejor manera de implementar una búsqueda de subcadena en SQL?

Mira mi presentación Búsqueda práctica de texto completo en MySQL .

Comparé:

Hoy lo que usaría es Apache Solr , que pone a Lucene en un servicio con un montón de funciones y herramientas adicionales.

Re tu comentario:Ajá, está bien, no. Ninguna de las capacidades de búsqueda de texto completo que mencioné ayudará, ya que todas asumen algún tipo de límite de palabras

La otra forma de encontrar eficientemente subcadenas arbitrarias es el N-gram Acercarse. Básicamente, cree un índice de todas las secuencias posibles de N letras y señale las cadenas donde ocurre cada secuencia respectiva. Normalmente, esto se hace con N=3, o un trigram , porque es un punto de compromiso entre hacer coincidir subcadenas más largas y mantener el índice en un tamaño manejable.

No conozco ninguna base de datos SQL que admita la indexación de N-gram de forma transparente, pero puede configurarla usted mismo usando un índice invertido :

create table trigrams (
  trigram char(3) primary key
);

create table trigram_matches (
  trigram char(3),
  document_id int,
  primary key (trigram, document_id),
  foreign key (trigram) references trigrams(trigram),
  foreign key (document_id) references mytable(document_id)
);

Ahora complétalo de la manera difícil:

insert into trigram_matches
  select t.trigram, d.document_id
  from trigrams t join mytable d
    on d.textcolumn like concat('%', t.trigram, '%');

¡Por supuesto que esto llevará bastante tiempo! Pero una vez hecho, puedes buscar mucho más rápido:

select d.*
from mytable d join trigram_matches t
  on t.document_id = d.document_id
where t.trigram = 'abc'

Por supuesto, podría estar buscando patrones de más de tres caracteres, pero el índice invertido todavía ayuda a acotar mucho la búsqueda:

select d.*
from mytable d join trigram_matches t
  on t.document_id = d.document_id
where t.trigram = 'abc'
  and d.textcolumn like '%abcdef%';