2012-09-04 2 views
1
SELECT cf.FK_collection, c.collectionName, 
    uf.FK_userMe, uf.FK_userYou, 
    u.userId, u.username 
FROM userFollows as uf 
INNER JOIN collectionFollows as cf ON uf.FK_userMe = cf.FK_user 
INNER JOIN collections as c ON cf.FK_collection = c.collectionId 
INNER JOIN users as u ON uf.FK_userYou = u.userId 
WHERE uf.FK_userMe = 2 

안녕 얘들 아.MySQL - 여러 레코드 수정

나는이 쿼리를 만들려고 노력하고 있으며 원하는대로 여러 행을 반환하기 때문에 물론 원하는대로 처리하지 않을 수 있습니다. 설명해 드리겠습니다.

사이트에서 사용자 작업을 표시하기 위해 collectionFollows 및 userFollows를 모두 가져 오려고합니다. 하지만 이렇게하면 userFollows에서 여러 행이 나옵니다. 사용자가 1을 따르는 경우에도 마찬가지입니다. 이는 여러 collectionFollows를 따르기 때문에 발생합니다. 내 결과를 보여줄 때

그래서 다음과 같이 반환합니다

John is following 'webdesign' 
John is following 'Lisa' 
John is following 'programming' 
John is following 'Lisa' 
내가 여러 쿼리를 만들거나 하위 쿼리를 사용하는 경우 내가 알고 싶습니다

? 가장 좋은 방법은 무엇입니까? 그러면 쿼리를 어떻게 작성합니까?

+1

질문에 수십억 번 묻는 질문을 알고 있다면 적어도 100 만 건의 대답을 발견 했어야합니다. – GolezTrol

+0

@GolezTrol 내가이 질문을 작성하지 않았 더라면. 나는 또한 다른 질문에서 말하지 않은 모범 사례를 묻고있다. – skolind

+0

좋아. 가장 좋은 방법은 먼저 작동하는 쿼리를 작성한 다음 (사용자가 수행하지 않는) 쿼리를 최적화 한 후에 수행하는 것입니다. 나는이 질문에 답하려고 노력했다. – GolezTrol

답변

3

실제로 두 개의 매우 관련없는 검색어를 결합하고 있습니다. 저는 그것들을 별도의 쿼리로 유지할 것입니다. 원하는 경우 UNION ALL을 사용하여 이러한 쿼리를 결합 할 수 있습니다. 이렇게하면 항목의 유형에 관계없이 따라 다니는 항목의 이름 목록 만 나타납니다. 원하는 경우 지정할 수도 있습니다.

SELECT 
    cf.user, 
    cf.FK_collection as followItem, 
    c.collectionName as followName, 
    'collection' as followType 
FROM collectionFollows as cf 
INNER JOIN collections as c ON cf.FK_collection = c.collectionId 
WHERE cf.user = 2 
UNION ALL 
SELECT 
    uf.FK_userMe, 
    u.userId, 
    u.username 
    'user' as followType 
FROM userFollows as uf 
INNER JOIN users as u ON uf.FK_userYou = u.userId 
WHERE uf.FK_userMe = 2 

또 다른 대안은 PHP에서 고유 한 값을 필터링하는 것이지만 쿼리를 수행하더라도 실패합니다. 내부 조인 때문에 사용자가 다른 사용자를 따르거나 콜렉션 만 따르는 경우에는 결과가 표시되지 않습니다. 결과를 얻으려면 적어도 둘 중 하나가 필요합니다. INNER JOIN을 LEFT JOIN으로 변경할 수 있지만, 필터를 두 번 필터링하고 NULL 값을 필터링하려면 쿼리를 후 처리해야합니다.

UNION ALL은 빠릅니다. 처리 과정없이 두 개의 쿼리 결과를 함께 저장합니다. 이것은 UNION과 다르다. UNION은 DISTINCT와 같이 double을 필터링한다. 이 경우 사용자가 컬렉션이나 다른 사용자를 한 번만 추적 할 수 있다고 가정하기 때문에 필요하지 않습니다. 따라서 이러한 쿼리는 중복 레코드를 반환하지 않습니다. 이것이 사실이라면 UNION ALL은 UNION보다 빠르며 빠를 것입니다.

UNION ALL 외에도 두 가지 별도의 쿼리가 적합합니다.

+0

답장을 보내 주셔서 감사합니다. 감사! – skolind

+0

이것은 완벽합니다. 고마워. 매우 유용한 답변입니다! 이제는 UNION에 대한 모든 내용과 작동 방식을 읽으므로 귀하의 대답을 복사하여 붙여 넣는 것이 아닙니다. 감사! – skolind

+0

'UNION ALL '이 아니라'UNION ALL '입니다. 그들은 다르다! :) – GolezTrol