SQL Cơ bản Phần 2

sql.png

Hôm nay chúng ta sẽ tiếp tục cuộc hành trình tìm hiểu về ngôn ngữ sql, làm việc với nhiều bảng hơn, giới thiệu qua các quan hệ trong cơ sở dữ liệu và Join query.

bạn có thể xem lại PHẦN I để dễ dàng đọc phần này hơn nhé.

Các kiểu qan hệ database

Khi tạo một database, thường sử dụng mỗi bảng khác nhau cho mỗi thực thể(entity). Vd như bảng customers, bảng orders, bảng items... Nhưng chúng ta cần có quan hệ giữa các bảng này. Với hai bảng customers, orders và items thì: customers tạo orders và orders chứa các items. Nhờ có quan hệ này mà ta có thể sử dụng lệnh join query để lấy chính xác những gì chúng ta cần một cách dễ dàng. Các kiểu quan hệ trong cơ sở dũ liệu.

  • quan hệ một – một.
  • quan hệ một – nhiều.
  • quan hệ nhiều – nhiều.
  • quan hệ self reference.

Khi lấy dữ liệu từ nhiều bảng có quan hệ, chúng ta sẽ sử dụng JOIN query. Có một vài kiểu JOIN query mà chung ta sẽ tìm hiểu ở phần tiếp theo.

Quan hệ Một - một (one - one relationshiops)

Giả sử bạn có một bảng customers chứa tên và địa chỉ của nó:

customer.PNG

Chúng ta có thể đặt thông tin địa chỉ của mỗi customer trong một bảng riêng luôn là addresses.

customer_2.PNG addresss.PNG

Giờ thì ta có một quan hệ giữ bảng customers và bảng addresses. Nếu mỗi address có thể thuộc một và chỉ một customer thì quan hệ này gọi là quan hệ một – một.

Bạn có thể thấy giờ có một trường tên là “address_id” trong bảng customers, đó là một tham chiếu đến mỗi bản ghi trong bảng addresses. đây gọi là một khóa phụ “foregin key” và nó được sử dụng cho toàn bộ các loại quan hệ khác nữa trong DB.

Quan hệ Một - nhiều (one - many relationshiops)

Đây là loại quan hệ rất hay được sử dụng trong thiết kế database.

  • customer có thể tạo một hoặc nhiều orders.
  • orders có thể chứa nhiều items.
  • mỗi item có thế chứa description, name, price và một số các thông tin khác nữa.

Trong trường hợp như ví dụ dưới đây chúng ta tạo một quan hệ một – nhiều .

customer_2.PNG orders.PNG

Mỗi customer có thể không có hoặc nhiều order nhưng mỗi order chỉ thuộc về duy nhất một customer thôi.

Quan hệ nhiều - nhiều (many - many relationshiops)

Trong một vài trường hợp, chúng ta có thể cần cái quan hệ nhiều nhiều này. giả như mỗi order có thể có chứa nhiều items và mỗi item có thể có nằm trong nhiều order khác nhau. Trông quả xấu phết 😄 !. Dưới đây là VD cho cái quan hệ này:

nhieu.PNG

Trong bảng bills chỉ có một mục đích là để tạo quan hệ nhiều nhiều giữa cái orders và items. Khi mà bạn xác định quan hệ giữa hai thực thể mà ra cái quan hệ nhiều nhiều này thì phải cố tạo ra một bảng trung gian giữa hai thằng để có được quan hệ nhiề nhiều này.

Self Referencing Relationships

đây là quan hệ mà một bảng cần một quan hệ với chính nó. VD. khách hàng có thể tham chiếu với các customers khác nữa.

Foreign Keys

Trong phần chúng ta tìm hiểu thêm những gì về foreign key. Trong các quan hệ trên bạn có thể thấy có một số trường mà có type của nó là “xxx_id” tham chiếu đến một bảng khác như là customer_id nó là một foreign key trong bảng orders.

Với MySQL để tạo forengin key này ta làm như sau, tiện thể tạo luôn vài bảng để pratice trong phần JOIN.

CREATE TABLE customers (
	customer_id INT AUTO_INCREMENT PRIMARY KEY,
	customer_name VARCHAR(100)
);

Tiếp theo tạo một bảng orders mà cái order này sẽ chứa một forign key.

CREATE TABLE orders (
	order_id INT AUTO_INCREMENT PRIMARY KEY,
	customer_id INT,
	amount DOUBLE,
	FOREIGN KEY (customer_id) REFERENCES customers(customer_id)
);

Cơ mà bạn phải chắc chắn một điều là customer_id của bảng orders và customers phải cùng kiểu dữ liệu đấy nhé.

JOIN Queries

Để lấy dữ liệu từ database mà có quan hệ(relationship) thường sẽ dùng JOIN query này. Chúng ta đã tạo bảng customers và orders ở trên rồi, giờ thì thêm xíu dữ liệu vào để vọc mấy cái loại JOIN này. Các loại JOIN trong SQL:

  • Cross Join.
  • Natureal Join.
  • Left Join.
  • Right join.

Giờ tạo một vài ông customer:

INSERT INTO customers(customer_name) VALUES("Doan"), ("Linh"), ("Dieu"), ("Ha");

tiếp theo tạo order cho nó:

INSERT INTO orders(customer_id, amount) VALUES (1, 19.99),( 1, 35.15), (3, 17.56), (4, 12.34);

Vậy là chúng ta có 4 customers. mỗi customer có số các hóa đơn khác nhau. Giờ thì hãy nhìn sự khác biệt giữa các loại join dưới đây nhé.

CROSS JOIN

Đây là loại mặc định của JOIN query khi bạn kông chỉ rõ loại join trong câu query.

SELECT * FROM customers JOIN orders;

cross join.PNG

Kết quả ta nhận được gọi là tích đề các(Descaries). Nó có nghĩa là mỗi dòng trong bảng đầu tiên sẽ được match với mỗi row trong bảng thứ hai . Hai bảng trên mỗi bảng có 4 rows (record ) vậy kết quả ta nhận được sau khi JOIN cross là 16 rows.

Từ khóa JOIN này có thể được thay thế bằng dấu ‘,’ giữa hai bảng với nhau. Bạn thữ query với câu sau thì kết quả sẽ trả về y hệt.

SELECT * FROM customers, orders;

NATURAL JOIN

Với cái loại này ý thì bảng cần phải có một cột trùng tên với nhau. Trong trường hợp của chúng ta cả hai bảng đều có customer_id. Vì vậy MySQL sẽ join các bản ghi mà có giá trị trùng nhau thôi.

SELECT * FROM customers NATURAL JOIN orders;

natural join.PNG

Như bạn thấy customer_id được hiển thị mỗi một lần thôi mặc dù ta dùng SELECT (*). Đó là vì kiến trúc cơ sở dữ liệu đối xử với nó như hai cột đó có giá trị trùng nhau .

INNER JOIN

Khi một câu lệnh join có một điều kiện cụ thể thì đó là Inner JOIN. Trong trường hợp này nó sẽ là một ý tưởng tốt để xử lý hai bảng có field name tên của nó có thể khác nhau. Kết quả sẽ tương tự như natural Join

SELECT * FROM customers JOIN orders WHERE customers.customer_id = orders.customer_id;

inner join.PNG

Kết quả tra về có khác một chút so với kiểu natural join. Trường customer_id được xuất hiện những hai lần tương ứng với mỗi bảng. Đó là vì chúng ta chỉ đơn thuần yêu câu DB match giá trị trên hai column rõ ràng.

Tiếp theo chúng ta thử thêm một vài điều kiện vào câu query xem

SELECT * FROM customers JOIN orders WHERE customers.customer_id = orders.customer_id AND customers.customer_name LIKE ‘ %D%’;

inerr join 2.PNG

Câu query này sẽ lấy toàn bộ những bản ghi của hai bảng có trùng customer_id và phải có customer_name chứa chữ ‘D’.

** Mệnh đề ON**

Trước khi đi tiếp sang các loại JOIN khác. Chúng ta sẽ tìm hiểu về mệnh đề ON này. Nó thật sự có ích cho việc đưa các điều kiện JOIN trong một điều kiện riêng biệt. nào thử câu query sau

SELECT * FROM customers JOIN orders ON(customers.customer_id = orders.customer_id) WHERE order.amount > 20;

onclause.PNG

Nhìn câu query trên bạn có thể thấy clear hơn so với việc không sử dụng mệnh đề ON.

** Mệnh đề USING**

Using nó cũng tương tự như mệnh đề ON thôi nhưng nó ngăn hơn một chút với điều kiện là hai column trong hai bảng phải có tên trùng nhau cơ. Cách sử dụng thì như dưới đây.

SELECT * FROM customers JOIN orders USING(customer_id) WHERE order.amount > 20;

Nhưng thật ra nếu mà hai column mà tên trùng nhau thì dùng xừ luôn Natural Join luôn. Kết quả ra y hệt nhau luôn.

LEFT JOIN

LEFT JOIN là một trong những lọai của OUTER JOIN. Trong câu query mà sử dụng LEFT JOIN nếu không match với bảng thứ hai thì các bản ghi của bảng một vẫn sẽ được hiển thị bình thường.

SELECT * FROM customers LEFT JOIN orders On(customers.customer_id = orders.customer_id);

leftjoin.PNG

Từ kết quả trả về bạn có thể thấy cái cô Linh này không có một order nào thì ở bảng thứ hai sẽ là NULL Thử thêm vài điều kiện vào nhé.

SELECT * FROM customers LEFT JOIN orders On(customers.customer_id = orders.customer_id) WHERE orders.amount > 15;

leftjoin2.PNG

Oh nếu bạn để ý thì cô Hà và Linh mất rồi. Đó là vì LEFT JOIN đã trả về toàn bộ customers kể cả không match với bảng 2. Vấn đề là ở mệnh đề WHERE đã loại bỏ những bản ghi mà hóa đơn có amount <= 15.

RIGHT JOIN

Right JOIn thì tương tự với left join. Nhưng thứ tự thì được đảo lại.

righ join.PNG

Kết Luận

Cảm ơn các bạn đã đọc bài viết hy vọng qua một số các ví dụ cơ bảnm, Hi vọng sẽ giúp bạn nắm được một số syntax cơ bản trong MySQL.