Моя ситуация
Скажем, у меня есть тысячи объектов, которые в этом примере могут быть фильмами.
Я разбираю эти фильмы по-разному, собирая параметры, ключевые слова и статистику по каждому из них. Позвольте называть их ключами. Я также назначаю вес каждому ключу в диапазоне от 0 до 1, в зависимости от частоты, релевантности, силы, оценки и т.д.
В качестве примера, вот несколько клавиш и весов для фильма Armageddon:
"Armageddon"
------------------
disaster 0.8
bruce willis 1.0
metascore 0.2
imdb score 0.4
asteroid 1.0
action 0.8
adventure 0.9
... ...
Там может быть пара тысяч этих ключей и весов, и для ясности здесь есть еще один фильм:
"The Fast and the Furious"
------------------
disaster 0.1
bruce willis 0.0
metascore 0.5
imdb score 0.6
asteroid 0.0
action 0.9
adventure 0.6
... ...
Я называю это отпечатком фильма, и я хочу использовать их для поиска похожих фильмов в моей базе данных.
Я также предполагаю, что можно будет вставить что-то другое, кроме фильма, например, статью или профиль Facebook, и назначить отпечаток пальца, если захочу. Но это не должно повлиять на мой вопрос.
Моя проблема
Итак, я зашел так далеко, но теперь эта часть мне кажется сложной. Я хочу взять отпечаток пальца вверх и превратить его во что-то легко сравнимое и быстрое. Я попытался создать массив, где index 0
= disaster
, 1
= bruce willis
, 2
= metascore
и их значение - вес.
Это выглядит примерно так для моих двух фильмов выше:
[ 0.8 , 1.0 , 0.2 , ... ]
[ 0.1 , 0.0 , 0.5 , ... ]
Который я пробовал сравнивать по-разному, просто умножая:
public double CompareFingerprints(double[] f1, double[] f2)
{
double result = 0;
if (f1.Length == f2.Length)
{
for (int i = 0; i < f1.Length; i++)
{
result += f1[i] * f2[i];
}
}
return result;
}
или сравнения:
public double CompareFingerprints(double[] f1, double[] f2)
{
double result = 0;
if (f1.Length == f2.Length)
{
for (int i = 0; i < f1.Length; i++)
{
result += (1 - Math.Abs(f1[i] - f2[i])) / f1.Length;
}
}
return result;
}
и т.д.
Они вернули очень удовлетворительные результаты, но все они имеют одну общую проблему: они отлично подходят для сравнения двух фильмов, но на самом деле это довольно много времени и кажется очень плохой практикой, когда я хочу сравнить один фильм отпечаток пальца с тысячами отпечатков пальцев, хранящихся в моей базе данных MSSQL. Специально, если он должен работать с такими вещами, как автозаполнение, где я хочу вернуть результаты в доли секунды.
Мой вопрос
Есть ли у меня правильный подход или я изобретаю колесо действительно неэффективным способом? Надеюсь, мой вопрос не будет шире для Stack Overflow, но я сузил его с помощью нескольких мыслей ниже.
Несколько мыслей
- Должен ли мой отпечаток действительно быть массивом весов?
- Должен ли я заглянуть в хэширование моего отпечатка пальца? Это может помочь с хранением отпечатков пальцев, но затрудняет сравнение. Я нашел некоторые подсказки, что это может быть действительный подход, используя чувствительность к местоположению, но математика немного не в моих силах.
- Должен ли я извлекать все тысячи фильмов из SQL и работать с результатом, или есть способ реализовать мое сравнение в SQL-запросе и вернуть только 100 лучших просмотров?
- Является редким представлением данных, чтобы посмотреть на него? (Спасибо Speed8ump)
- Могу ли я применять методы, используемые при сравнении фактических отпечатков пальцев или для OCR?
- Я слышал, что есть программное обеспечение, которое обнаруживает обман на экзамене, обнаруживая сходство в тысячах опубликованных статей и предыдущих тестов. Какой метод они используют?
Ура!