Bạn có thể tìm thấy những người bạn chung bằng cách tham gia vào bảng friend_links trên trường friend_id như sau:
SELECT *
FROM friend_links f1 INNER JOIN friend_links f2
ON f1.friend_id = f2.friend_id
WHERE f1.user_id = $person1
AND f2.user_id = $person2
Nhưng hãy nhớ rằng điều này, trong trường hợp xấu nhất, về cơ bản là bình phương số lượng hàng trong bảng friend_links và có thể dễ dàng kích hoạt máy chủ của bạn khi bạn có một số lượng hàng không nhỏ. Một lựa chọn tốt hơn sẽ là sử dụng 2 truy vấn phụ cho mỗi người dùng và sau đó kết hợp các kết quả của những truy vấn đó.
SELECT *
FROM (
SELECT *
FROM friend_links
WHERE user_id = $person1
) p1 INNER JOIN (
SELECT *
FROM friend_links
WHERE user_id = $person1
) p2
ON p1.friend_id = p2.friend_id
Ngoài ra, bạn có thể đơn giản hóa bảng friend_links của mình bằng cách xóa khóa thay thế link_id
và chỉ tạo (user_id,friend_id)
khóa chính vì chúng phải là duy nhất.
Chỉnh sửa:
SELECT f2.user_id, COUNT(*) 'friends_in_common'
FROM friend_links f1 LEFT JOIN friend_links f2
ON f1.friend_id = f2.friend_id
WHERE f1.user_id = $person
GROUP BY f2.user_id
ORDER BY friends_in_common DESC
LIMIT $number
Tôi cũng đang nghĩ rằng user_id
các ràng buộc có thể được di chuyển từ WHERE
mệnh đề trong JOIN
các điều kiện để giảm kích thước của tập dữ liệu được tạo bởi tự nối và ngăn chặn việc sử dụng các truy vấn con như trong ví dụ thứ hai của tôi.