3

私は、ユーザーが自分とほぼ同じアーティストが好きなユーザーを見つけられるようにしたい音楽 Web サイトを作成しています。

「id_user」、「id_artist」の 2 つの列を持つ「like」テーブルがあります。これがどのように機能するかの例です。

User 1 likes:
1, 12
1, 13
1, 14
1, 26
1, 42
1, 44

User 2 likes:
2, 13
2, 14
2, 15
2, 26
2, 42
2, 56

この 2 人のユーザーには、4 人のアーティストが共通しています。これら 2 つの結果セットを比較して、データベース内で最も類似した人物を見つける方法はありますか?

私の最初のアイデアは、「12,13,14,26,42,44」を文字列に連結し、mysql FULLTEXT スコアを使用して異なる文字列を比較することでした。それは機能しませんでした...理由はわかりませんが、mysqlフルテキストはテキストでのみ機能します...数字では機能しません...

どんなアイデアや手がかりも大歓迎です。

4

2 に答える 2

2

このようなもの:

SELECT first_user.id_user, second_user.id_user, COUNT(first_user.id_user) AS total_matches

FROM likes AS first_user

JOIN likes AS second_user
ON second_user.id_artist = first_user.id_artist
AND second_user.id_user != first_user.id_user

GROUP BY first_user.id_user, second_user.id_user

ORDER BY total_matches DESC

LIMIT 1

これはあまり効率的ではないことに注意してください。これを回避する1つの方法は、このクエリの出力を含む「キャッシュテーブル」を作成し、そのLIMIT 1部分を削除することです。関連するインデックスをいくつか追加し、このキャッシュテーブルをクエリします。このテーブルを定期的に更新するようにcronジョブを設定できます。

例:

CREATE TABLE IF NOT EXISTS `likes` (
  `id_user` varchar(50) DEFAULT NULL,
  `id_artist` varchar(50) DEFAULT NULL
) ENGINE=MyISAM DEFAULT CHARSET=latin1;

INSERT INTO `likes` (`id_user`, `id_artist`) VALUES ('8', '39'), ('8', '37'), ('4', '37'), ('8', '24'), ('8', '7'), ('4', '28'), ('8', '28'), ('4', '27'), ('4', '11'), ('8', '49'), ('4', '7'), ('4', '40'), ('4', '29'), ('8', '22'), ('4', '29'), ('8', '11'), ('8', '28'), ('4', '7'), ('4', '31'), ('8', '42'), ('8', '25'), ('4', '25'), ('4', '17'), ('4', '32'), ('4', '46'), ('4', '19'), ('8', '34'), ('3', '32'), ('4', '21')

+---------+---------+---------------+
| id_user | id_user | total_matches |
+---------+---------+---------------+
| 8       | 4       |             7 |
+---------+---------+---------------+
于 2012-04-29T20:14:23.170 に答える
0

テーブルをそれ自体に結合することは可能です。(クエリがあいまいにならないように、テーブルの2つの「コピー」のうち少なくとも1つにエイリアスを指定する必要があります。)

likeしたがって、2人のユーザーがいる場合、テーブルをそれ自体に結合することで、共通の「いいね」を見つけることができます。また、左結合を実行し、結果の数とnullの数の両方をカウントすることで、ユーザー1のいいねの割合をユーザー2が共有していることを確認できます。これは対称操作ではないことに注意してください。一方または両方の数値が0の場合に対処する必要があります。

「データベース内で最も類似した人物を検索する」と言う場合、ユーザーのすべてのペアに対してこれを行うことができますが、ユーザーがいる場合は、 2乗のオーダーの比較nを行う必要があることに注意してください。多くのユーザーがいる場合、これはデータベースにとって非常に多くの作業になる可能性があります。n*(n-1)/2n

于 2012-04-29T20:16:55.027 に答える