2015-02-06 4 views
1

이것은 현재 내 머리가 녹고 있지만,해야 할 일이 있습니다. 기본적으로 쿼리는 다음과 같습니다 : 그러니까 기본적으로 내가 사용자와 동일한 작업 ID를 가지고 기록 요구 사항이있는 경우에만 사용자가있는 경우를 선택 모든 레코드를 되찾아있다 할 노력하고있어mysql의 다른 테이블에 레코드가 존재해야하는 경우 레코드가 필요합니다.

SELECT r.* FROM records r 
JOIN users u ON u.job_id = r.job_id 
LEFT JOIN records_requirements rr ON rr.record_id = r.id 
INNER JOIN user_requirements ur on ur.requirement_id = rr.requirement_id 

user_requirements 테이블에 일치하는 레코드가 있습니다. 사용자에게 요구 사항이 없으면 레코드를 선택하지 마십시오.

따라서 동일한 job_id 및 요구 사항이없는 모든 레코드를 얻거나 동일한 job_id를 가지며 사용자에게없는 요구 사항이 없어야합니다. 그것을 테스트하지 않고

+0

요구 사항 ID = 레코드 ID가 같은 것 –

+0

반 결합, 'WHERE blah IS NULL'체크가 필요하다고 생각합니다. – Mihai

+0

WHERE (rr.requirement_id IS NULL 또는 ur.requirement_id IS NOT NULL) '? rr.requirement_ids가 여러 개있는 경우이 방법을 사용할 수 있습니까? 레코드 요구 사항이 많은 경우에도 여전히 한 레코드 만 가져 오려고합니다. – PixMach

답변

1

, 나는 이런 식으로 뭔가 일을해야한다고 생각 :

SELECT DISTINCT r.* 
FROM records r 
INNER JOIN users u ON u.job_id = r.job_id 
LEFT JOIN records_requirements rr ON rr.record_id = r.id 
LEFT JOIN user_requirements ur ON ur.requirement_id = rr.requirement_id 
    AND ur.user_id = u.id 
WHERE 
    (
    (rr.record_id IS NULL) 
     OR 
    (rr.record_id IS NOT NULL AND ur.requirement_id IS NOT NULL) 
) 
    AND u.id = ? 

무엇 더 요구 수 있도록 요구 사항을 기록하기 위해 합류 한 채로하고, 또한 다음 사용자 요구 사항에 합류 남아 그래서 레코드 요구 사항은 있지만 일치하는 사용자 요구 사항은 계속 가져 오지 않습니다.

다음은 null 레코드 요구 사항 또는 레코드 및 사용자 요구 사항을 모두 허용하는 데 사용되는 테스트입니다.

마지막으로 SELECT DISTINCT는 레코드 당 하나의 결과 만 얻을 수 있도록합니다.

편집 : 다음과 같이 SQL Server를 사용하여 빠른 테스트 :

DECLARE @Users TABLE (job_id int) 
DECLARE @Records TABLE (id int, job_id int) 
DECLARE @Records_Requirements TABLE (requirement_id int, record_id int) 
DECLARE @User_Requirements TABLE (requirement_id int) 

INSERT INTO @Users VALUES (1) 

INSERT INTO @Records VALUES (1, 1) 
INSERT INTO @Records VALUES (2, 1) 
INSERT INTO @Records VALUES (3, 1) 

INSERT INTO @Records_Requirements VALUES (1, 1) 
INSERT INTO @Records_Requirements VALUES (2, 2) 

INSERT INTO @User_Requirements VALUES (2) 

SELECT DISTINCT r.* 
FROM @Records r 
INNER JOIN @Users u ON u.job_id = r.job_id 
LEFT JOIN @Records_Requirements rr ON rr.record_id = r.id 
LEFT JOIN @User_Requirements ur on ur.requirement_id = rr.requirement_id 
WHERE (rr.record_id IS NULL) OR (rr.record_id IS NOT NULL AND ur.requirement_id IS NOT NULL) 

결과 : 제가 테스트 데이터에 대한 올바른 생각

id job_id 
2 1 
3 1 

. 아마도 MySQL은 다르게 작동하지만 그렇지 않아야합니다.

+0

실제로 이런 식으로 뭔가를하고 있지만, record_requirement가 없으면 실패합니다. 아마도 LEFT JOIN에 rr.requirement_id가 표시되지 않기 때문입니다. 편집 : record_requirement가 존재하고 사용자 요구 사항이 존재하고 일치하면 레코드를 표시하고 rr.requirement_id가 null 및 ur가 아닌 경우 일치하는 레코드를 표시하지 않습니다. requirement_id는 null이어야합니다. – PixMach

+1

SQL Server를 사용하여 빠른 테스트를 수행했으며 (예상 할 수있는 MySQL이 없습니다) 예상대로 작동하는 것으로 보입니다. 테스트 데이터를 작성하기위한 간단한 스크립트를 제공 할 수 있습니까? (내 SQL 테스트를 내 대답에 붙여 넣을 것입니다.) ... 또는 테스트 데이터와 예상 결과를 제공 할 수 있습니까? – Alan

+0

나는 그것이 작동하지 않는 이유를 알아 내려고 많은 시간을 보냈다. 그 이유는 내가 생각한 것이 아니기 때문에 이유는 ur.requirement_id가 특정 사용자와 연관 될 필요가 없었기 때문이다. 특정 사용자와 일치하는 레코드를 찾는 것이 포함됨) 특정 사용자에게 연결하는 방법을 추가해야했습니다. 'ur.user_id =?'를 사용하는 것은 그것을 망가뜨 렸기 때문에'WHERE ur.user_id =? '를 수행하는 방법을 모른다면 절을 ON 절로 옮겨야했습니다. 또는 ur.user_id is null' 또는 where 절에있는 내용이지만 위험 해 보입니다. – PixMach

관련 문제