2012-03-24 3 views
0

MySQL을 사용하여 동의어 검색 기능을 만들어야합니다. 나는 그것이 이런 식으로 작업 할동의어 목록 : 사용 요청

NAMES_TABLE   SYNONYMS_TABLE 
------------   -------------- 
ID | NAME    ID_1 | ID_2 
---+--------   ------+------- 
1 | NAME_A    1 | 2 
2 | NAME_B    2 | 1 
3 | NAME_C    1 | 3 
4 | NAME_D    3 | 1 
5 | NAME_E    4 | 5 
         5 | 4 

: 다음에있는 형태로 단어를 입력하면 그 인덱스는 동의어 테이블에있는 경우, 해당 나에게 모든 단어를 전송 여기

는 테이블 구조 , ID_1 또는 ID_2.

하지만 요청을하기 위해 알아낼 수 없습니다 ...

도움 주셔서 감사합니다.

답변

1

한 방향은 : ID_1는 이름, ID_2는 동의어입니다 :

select 
    sn.NAME 
from 
    NAMES_TABLE n 
    inner join SYNONYMS_TABLE s on s.ID_1 = n.ID 
    inner join NAMES_TABLE sn on sn.ID2 = s.ID_2 
where 
    n.NAME = :NAME 

두 방향 : 다른 동의어 동안 ID_1 또는 ID_2 중 하나가, 이름을 포함 할 수 있습니다.

select 
    sn1.NAME 
from 
    NAMES_TABLE n1 
    inner join SYNONYMS_TABLE s1 on s1.ID_1 = n1.ID 
    inner join NAMES_TABLE sn1 on sn1.ID = s1.ID_2 
where 
    n1.NAME = :NAME 
union 
select 
    sn2.NAME 
from 
    NAMES_TABLE n2 
    inner join SYNONYMS_TABLE s2 on s2.ID_2 = n2.ID 
    inner join NAMES_TABLE sn2 on sn2.ID = s2.ID_1 
where 
    n2.NAME = :NAME 

참고 ID_2와 ID_1은 두 번째 쿼리의 두 번째 부분에서 반대입니다.

필요한 데이터는 데이터에 따라 다릅니다. '차선'을 '도로'의 동의어로 사용하고 다른 방향으로는 사용하지 않으려면 첫 번째 방법을 사용해야합니다. 그러나이 경우에 당신은 양방향 동의어 두 번 추가되어야 함을 기억해야 할 것이다, 그래서 당신은 얻을 것이다 :

NAMES_TABLE   SYNONYMS_TABLE 
------------   -------------- 
ID | NAME    ID_1 | ID_2 
---+--------   ------+------- 
1 | Road    1 | 3 
2 | Lane    3 | 1 
3 | Street   2 | 1 

이제 도로 및 거리 서로의 동의어이지만, 레인 동안 도로의 동의어입니다 , 도로는 차선이 아닙니다. ID_1과 ID_2를 바꿔서 이중 레코드를 입력 할 위험이 있지만 그 행동을 원하지 않는다면 두 번째 레코드를 사용하는 것이 좋습니다. ID_2가 항상 같거나 낮은 ID_1보다 항상 높은지 확인하여이를 방지 할 수 있어야합니다.

+0

정확하게 필요한 부분입니다. 요청 및 명확한 추가 설명에 감사드립니다. – mlh

1

이 JOIN에 가까운 뭔가가 잘 작동합니다. 두 이름 행 (원본과 동의어)을 확인하려는 때문에

SELECT n1.NAME 
FROM NAMES_TABLE n1 
JOIN SYNONYMS_TABLE s1 
    ON s1.ID_1 = n1.ID 
JOIN NAMES_TABLE n2 
    ON s1.ID_2 = n2.ID 
WHERE n2.NAME = ? 

, 당신은 SYNONYMS_TABLE를 통해 자체 테이블 NAMES_TABLE에 가입해야합니다.