Mysql
 sql >> база данни >  >> RDS >> Mysql

Сравняване на модел с mysql между две колони на таблици

Два въпроса - описанията стандартни ли са (описанията не се променят) или се въвеждат от потребител? Ако са стандартни, добавете колона, която е цяло число, и направете сравнение с тази колона.

Ако е въведено от потребителя, работата ви е по-сложна, защото търсите нещо, което е по-неясно търсене. Използвах алгоритъм за двуграмово търсене, за да класирам сходството между два низа, но това не може да се направи директно в mySQL.

Вместо размито търсене можете да използвате LIKE, но ефективността му е ограничена до извършване на сканиране на таблици, ако в крайна сметка поставите „%“ в началото на термина за търсене. Освен това означава, че можете да получите съвпадение на избраната от вас част от подниза, което означава, че трябва да знаете подниза предварително.

Ще се радвам да разясня повече, след като разбера какво се опитвате да направите.

РЕДАКТИРАНЕ1:Добре, като се има предвид вашата разработка, ще трябва да направите търсене в размит стил, както споменах. Използвам двуграмов метод, който включва вземане на всеки запис, направен от потребителя, и разделянето му на части от 2 или 3 знака. След това съхранявам всяка от тези части в друга таблица, като всеки запис се връща към действителното описание.

Пример:

Описание1:„Бързо бягане напред“Описание 2:„Кратко бягане напред“

Ако разделите всеки на 2 символни части - 'A', 'f', 'fa', 'as','st'.....

След това можете да сравните броя на 2 символни парчета, които съответстват на двата низа и да получите "резултат", който ще означава точност или сходство между двата.

Като се има предвид, че не знам какъв език за разработка използвате, ще пропусна внедряването, но това е нещо, което ще трябва да се направи не изрично в mySQL.

Или мързеливата алтернатива би била да използвате услуга за търсене в облак като Amazon, която ще осигури търсене въз основа на термини, които сте й дали... не съм сигурен дали ви позволяват непрекъснато да добавяте нови описания, които да обмислите, и в зависимост от вашето приложение, може да бъде малко скъпо (IMHO).

R

За друга публикация на SO относно внедряването на bigram - вижте това SO bigram / размито търсене

--- Актуализация на разработката на питащия---

Първо, предполагам, че сте прочели теорията на връзките, които предоставих.. второ, ще се опитам да го запазя възможно най-зависим от DB, тъй като не се нуждае от mySQL (въпреки че го използвам и работи повече от добре)

Добре, така че методът на bigram работи добре при създаване/сравняване на масиви в паметта само ако възможните съвпадения са относително малки, в противен случай той страда от производителността на сканиране на таблица като mysql таблица без индекси доста бързо. Така че ще използвате силните страни на базата данни, за да Ви помогнем да направим индексирането.

Това, от което се нуждаете, е една таблица, която да съдържа въведените от потребителя „термини“ или текст, който искате да сравните. Най-простата форма е таблица с две колони, едната е уникално цяло число с автоматично нарастване, което ще бъде индексирано, ще извикаме hd_id по-долу, втората е varchar(255), ако низовете са доста кратки, или TEXT, ако могат get long - можете да го кръстите както искате.

След това ще трябва да направите друга таблица, която има поне ТРИ колони - една за референтната колона обратно към автоматично увеличаващата се колона на другата таблица (ще наречем това hd_id по-долу), втората ще бъде varchar() на да речем най-много 5 символа (това ще съдържа вашите парчета биграма), които ще наречем „биграма“ по-долу, а третата колона с автоматично нарастване, наречена b_id по-долу. Тази таблица ще съдържа всички биграми за запис на всеки потребител и ще се свърже с общия запис. Ще искате да индексирате колоната varchar сама по себе си (или първа по ред в съставен индекс).

Сега всеки път, когато потребител въведе термин, който искате да търсите, трябва да въведете термина в първата таблица, след това да го разчлените на биграми и да въведете всяка част във втората таблица, като използвате препратката обратно към общия термин в първата таблица за завършване на връзката. По този начин вие правите дисекцията в PHP, но оставяте mySQL или друга база данни да направи оптимизацията на индекса вместо вас. Може да помогне във фазата на биграмата да съхраните броя на биграмите, направени в таблица 1 за фазата на изчисление. По-долу е даден код на PHP, за да ви даде представа как да създавате биграми:

// split the string into len-character segments and store seperately in array slots
function get_bigrams($theString,$len)   
{
   $s=strtolower($theString);
   $v=array();
   $slength=strlen($s)-($len-1);     // we stop short of $len-1 so we don't make short chunks as we run out of characters

   for($m=0;$m<$slength;$m++)
   {
      $v[]=substr($s,$m,$len);
   }
   return $v;
}    

Не се притеснявайте за интервалите в низовете - те всъщност са много полезни, ако мислите за размито търсене.

Така че получавате биграмите, въвеждате ги в таблица, свързана с общия текст в таблица 1 чрез и индексирана колона...и сега какво?

Сега всеки път, когато търсите термин като „Моят любим термин за търсене“ – можете да използвате функцията php, за да го превърнете в масив от биграми. След това използвате това, за да създадете частта IN (..) на SQL оператор на вашата биграмна таблица(2). По-долу е даден пример:

select count(b_id) as matches,a.hd_id,description, from table2 a
inner join table1 b on (a.hd_id=b.hd_id)
where bigram in (" . $sqlstr . ")
group by hd_id order by matches desc limit X

Оставих $sqlstr като препратка към PHP низ - можете сами да конструирате това като списък, разделен със запетая, от функцията bigram, като използвате implode или каквото и да е в масива, върнат от get_bigrams или параметризирате, ако желаете.

Ако е направено правилно, заявката по-горе връща най-близките съвпадащи размити думи за търсене в зависимост от дължината на биграмата, която сте избрали. Избраната от вас дължина има относителна ефективност въз основа на очакваната от вас дължина на общите низове за търсене.

И накрая - заявката по-горе, просто дава ранг на размито съвпадение. Можете да си поиграете и да подобрите, като сравнявате не само съвпаденията, но съвпаденията спрямо общия брой биграми, което ще помогне за премахване на пристрастията на дългите низове за търсене в сравнение с късите низове. Спрях до тук, защото в този момент става много по-специфично за приложението.

Надявам се това да помогне!

R




  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. pymssql.OperationalError:съобщение за грешка в DB-Lib 20009, сериозност 9

  2. Мога ли да използвам pt-online-schema-change за промяна на първичен ключ?

  3. Инструкция за вмъкване, която проверява за дублиране преди вмъкване

  4. Django група по дати и стойности SUM

  5. MySQL - ИЗБЕРЕТЕ само 2 реда от всяка "група"