Я новый пользователь SQL и мне нужна ваша помощь! Я делаю анализ реляционного графа на основе базы данных SQL, которая является единственным ресурсом, который я могу использовать и у которого возникают проблемы с сохранением определенного типа отношений между двумя людьми .
У меня есть эта таблица:
+---------+----------------+--------+----------------+-----------+
| left_id | left_rel | common | right_rel | right_id |
+---------+----------------+--------+----------------+-----------+
| Tom | graduated_from | MIT | worked_in | Jerry |
| Tom | graduated_from | MIT | graduated_from | Lee |
| Lee | graduated_from | MIT | graduated_from | Tom |
| Tom | graduated_from | MIT | graduated_from | Jerry |
+---------+----------------+--------+----------------+-----------+
Мне нужна таблица, в которой идентичные отношения между двумя людьми сведены к одной единственной связи. Итак, отношения, в которых Том и Ли закончили Массачусетский технологический институт, имеют две записи, я хочу отбросить эти дубликаты. Я могу принять Тома как Left_id или Right_id, , только если его id и rel сопоставлены .
Надеюсь, этот фрагмент кода создания таблицы сэкономит вам время.
CREATE TABLE tmp (
left_id varchar(20)
, left_rel varchar(50)
, common varchar(50)
, right_rel varchar(50)
, right_id varchar(20)
);
INSERT INTO tmp VALUES ("Tom", "graduated_from", "MIT", "worked_in", "Jerry");
INSERT INTO tmp VALUES ("Tom", "graduated_from", "MIT", "graduated_from", "Lee");
INSERT INTO tmp VALUES ("Lee", "graduated_from", "MIT", "graduated_from", "Tom");
INSERT INTO tmp VALUES ("Tom", "graduated_from", "MIT", "graduated_from", "Jerry");
То, что я пробовал до сих пор
CREATE TEMPORARY TABLE tmp1
AS
SELECT
greatest(CONCAT_WS(':', left_id, left_rel), CONCAT_WS(':', right_id, right_rel)) AS Left_Part
, Common
, least(CONCAT_WS(':', left_id, left_rel), CONCAT_WS(':', right_id, right_rel)) AS Right_Part
FROM tmp
;
CREATE TEMPORARY TABLE tmp2
AS
SELECT
T1.Left_Part
, T1.Common
, T1.Right_Part
FROM ( SELECT
*
, ROW_NUMBER() OVER(DISTRIBUTE BY Left_Part, Right_Part) AS rn
FROM tmp1
) T1
WHERE T1.rn = 1
;
CREATE TEMPORARY TABLE result
AS
SELECT
SPLIT(Left_Part,':')[0] as left_id
, SPLIT(Left_Part,':')[1] as left_rel
, Common
, SPLIT(Right_Part,':')[0] as right_id
, SPLIT(Right_Part,':')[1] as right_rel
FROM tmp2
;
дает результат
+---------+----------------+--------+----------------+-----------+
| left_id | left_rel | common | right_rel | right_id |
+---------+----------------+--------+----------------+-----------+
| Tom | graduated_from | MIT | worked_in | Jerry |
| Tom | graduated_from | MIT | graduated_from | Lee |
| Tom | graduated_from | MIT | graduated_from | Jerry |
+---------+----------------+--------+----------------+-----------+