source

행이 있는지 확인하기 위한 두 가지 방법 중 선택(하위 쿼리 수가 더 많은 경우와 왼쪽 조인 수가 더 많은 경우

gigabyte 2022. 10. 19. 21:08
반응형

행이 있는지 확인하기 위한 두 가지 방법 중 선택(하위 쿼리 수가 더 많은 경우와 왼쪽 조인 수가 더 많은 경우

다른 테이블에서 join을 사용하여 하나의 제품 정보를 가져오고 싶습니다.3개의 테이블(review, thread, award)이 더 있는데, 이 제품에 대한 기록이 있는지 확인하고 싶습니다.null이 아닌 값이 있으면 null을 반환하고 그렇지 않으면 null을 반환합니다.향후 이러한 유형의 체크가 쿼리에 추가될 가능성이 있습니다.

레코드가 존재하는지 테스트하기 위해 어떤 쿼리를 사용하시겠습니까?

사용.exists여러 서브쿼리가 있는 경우:

$sql = "SELECT p.product_id,p.name,m.model,m.model_id,b.brand,me.merchant,
         EXISTS(SELECT 1 FROM review WHERE product_id = :id) AS has_review,
         EXISTS(SELECT 1 FROM thread WHERE product_id = :id) AS has_thread,
         EXISTS(SELECT 1 FROM award WHERE product_id = :id) AS has_award
        FROM product p 
        INNER JOIN model m ON m.model_id = p.model_id
        INNER JOIN brand b ON b.brand_id = m.brand_id
        INNER JOIN merchant me ON me.merchant_id = m.merchant_id
        WHERE p.product_id = :id
        LIMIT 1";

$dbh->prepare($sql);

여러 왼쪽 조인 사용:

$sql = "SELECT p.product_id,p.name,m.model,m.model_id,b.brand,me.merchant,
        (t.product_id is not null) AS has_thread,
        (r.product_id is not null) AS has_review,
        (a.product_id is not null) AS has_award
        FROM product p 
        INNER JOIN model m ON m.model_id = p.model_id
        INNER JOIN brand b ON b.brand_id = m.brand_id
        INNER JOIN merchant me ON me.merchant_id = m.merchant_id
        LEFT JOIN review r ON re.product_id = p.product_id
        LEFT JOIN thread t ON t.product_id = p.product_id 
        LEFT JOIN award a ON a.product_id = a.product_id
        WHERE p.product_id = :id
        LIMIT 1";

첫 번째가 훨씬 더 좋다.

성능을 위해 두 버전 모두 인덱스를 사용할 수 있습니다.review(product_id),thread(product_id),그리고.award(product_id).

를 사용하는 이유EXISTS더 나은가요?3개의 테이블에 일치하는 행이 없는 경우 두 버전이 같아야 합니다(마지막 오타를 제외).on절)을 참조해 주세요.그러나 행이 존재하는 경우 두 번째 버전은 해당 행의 데카르트 곱을 생성하여 결과와 성능을 모두 무시합니다.

주의: 저는 다음과 같이 쓰고 싶습니다.EXISTS관련 서브쿼리를 사용하는 절이므로 파라미터는 다음 한 번만 참조됩니다.

     EXISTS (SELECT 1 FROM review r WHERE r.product_id = p.product_id) AS has_review,
     EXISTS (SELECT 1 FROM thread t WHERE t.product_id = p.product_id) AS has_thread,
     EXISTS (SELECT 1 FROM award a WHERE a.product_id = p.product_id) AS has_award,

언급URL : https://stackoverflow.com/questions/34719834/deciding-between-two-methods-to-check-if-a-row-exists-more-subqueries-vs-more-l

반응형