Lý do của việc sử dụng nối đôi bên trong trong câu lệnh SQL này là gì?


10

Tôi đang xem xét truy vấn SQL kế thừa này. Một chút tôi không thể có được là tại sao nó lại tham gia cùng một bảng hai lần trên cùng một cột. Tôi đang nói về Table1 và Table1 được nối với bí danh "Table1Alias",

SELECT DISTINCT othercolumns,
                Table1Alias.columna
FROM   maintable
       INNER JOIN secondarytable
               ON maintable.id1 = secondarytable.a_id1
       INNER JOIN table1
               ON secondarytable.id2 = table1.id3
       INNER JOIN table1 Table1Alias
               ON secondarytable.id2 = Table1Alias.id3
       INNER JOIN thirdtable
               ON table1.id4 = thirdtable.id5
       INNER JOIN fourthtable
               ON thirdtable.id6 = fourthtable.id7
       INNER JOIN fivetable
               ON thirdtable.id8 = fivetable.id9
       INNER JOIN sixthtable
               ON Table1Alias.columna = sixthtable.id10
       LEFT JOIN seventhtable
              ON thirdtable.id11 = seventhtable.id12
WHERE  LEFT(secondarytable.type123, 2) BETWEEN '01' AND '09'
       AND secondarytable.type456 = 'cate'
       AND table1.type = '0'
       AND Table1Alias.columna = 'conn'

Câu trả lời:


27

Nó có thể giúp viết lại truy vấn như thế này, vì vậy rõ ràng là 2 phép nối là khác nhau , tức là các phép nối là các tập con khác nhau (của cùng một bảng):

FROM   maintable 
       INNER JOIN secondarytable 
               ON maintable.id1 = secondarytable.a_id1 
       INNER JOIN table1 
               ON secondarytable.id2 = table1.id3 
              AND table1.type = '0' 
       INNER JOIN table1 Table1Alias 
               ON secondarytable.id2 = Table1Alias.id3 
              AND Table1Alias.columna = 'conn' 
       INNER JOIN
       ...
WHERE  LEFT(secondarytable.type123, 2) BETWEEN '01' AND '09' 
       AND secondarytable.type456 = 'cate' 

không phải là WHERE được áp dụng SAU các phép nối, tức là tôi sẽ đồng ý nếu các ràng buộc đó là một phần của câu lệnh nối, tức là được kết nối bởi AND, nhưng WHERE trong tất cả kinh nghiệm được áp dụng cho kết quả của phép nối lọc ra các hàng từ bảng tham gia, không ảnh hưởng đến tham gia thực tế.
Frank Hopkins

3
@Darkwing Theo như tôi biết, không quan trọng bạn đặt điều kiện ở đâu, vì đó là công việc của trình tối ưu hóa truy vấn để đưa ra kế hoạch kiểm tra tốt nhất. Tuy nhiên, tốt hơn là đặt chúng bên cạnh tham gia vì nó giúp chúng dễ đọc hơn nhưng đó chỉ là một ý kiến
Toán học

Ngay cả khi điều đó xảy ra SAU khi tham gia, kết quả của các lần tham gia cuối cùng vẫn khác nhau. Và có, các hàng đã tham gia thường được lọc trước khi tham gia vì nó cải thiện hiệu suất.
Gherman

1
Nó cũng tương đương với việc tham gia với một truy vấn con, vd INNER JOIN (SELECT * FROM table1 WHERE type = 0) table1. Điều đó có thể làm cho nó rõ ràng hơn những gì đang xảy ra.
Barmar

3
@Mathatures - cho dù một điều kiện nằm trong ONmệnh đề của phép nối hoặc trong WHEREmệnh đề có thể là vấn đề lớn nếu tham gia là một OUTER JOIN. Nếu một điều kiện thất bại trong ONmệnh đề, hàng chính vẫn được đưa vào (không có hàng ngoài phù hợp); nếu nó thất bại trong WHEREmệnh đề, thì hàng chính được loại trừ khỏi tập kết quả.
RDFozz

8

Nhìn vào wheremệnh đề, hàng được trỏ tới table1yêu cầu cột typephải = '0' và hàng được trỏ tới table1aliasyêu cầu cột columnaphải = 'Conn'.

Có lẽ có nhiều hàng trên table1cho cùng một id3?


2

Không nhìn thấy cấu trúc bảng - cách tiếp cận có thể là sử dụng một chỉ mục không che phủ nhỏ hơn và sau đó tham gia vào bảng trên một chỉ mục bao phủ lớn hơn để có được các hàng còn lại để tránh hoạt động 'Tra cứu khóa' và tránh sửa đổi các chỉ mục hiện có (hoặc nếu bạn không thể sửa đổi các chỉ mục)


2

Bất cứ khi nào một bảng xuất hiện nhiều hơn một lần trong một phép nối phức tạp, thường là do có một thực thể tham gia vào nhiều hơn một mối quan hệ. Đó dường như là trường hợp ở đây, đánh giá bằng câu trả lời mà @Ypercube đã đưa ra.

Các thực thể và mối quan hệ thường được hiểu thông qua ngữ nghĩa của dữ liệu và kết nối với chủ đề cơ bản. Nếu hệ thống di sản của bạn được xây dựng cẩn thận, có lẽ họ đã cẩn thận phân tích vấn đề và xác định cẩn thận từng yếu tố dữ liệu. Họ thậm chí có thể đã xây dựng một mô hình Mối quan hệ thực thể. Tất cả những công việc cẩn thận đó có thể đã bị mất, và bạn bị mắc kẹt trong việc tái cấu trúc nó bằng cách đào sâu vào quá khứ. Đây là một chút giống như khảo cổ học.

Với các tên bảng như Bảng 1, chúng tôi chưa có manh mối về cách hoạt động của đối tượng. Và ngay cả khi tên được mô tả, sự hiểu biết của chúng tôi về vấn đề hệ thống của bạn có thể rất khác so với những gì cần thiết trong trường hợp của bạn. Nó sẽ tùy thuộc vào bạn.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.