+4

Fullstack Vỡ Lòng 05: Các kiểu dữ liệu thường dùng nhất trong MySQL - String Data Types - Sự khác nhau giữa CHAR vs VARCHAR - Bạn đã hiểu rõ?

Mayfest2023

Trong nội dung bài viết trước, mình đã chia sẻ về "Kiểu dữ liệu dạng số - Numeric Data Types". Các bạn khi đọc bài viết ấy nhớ để ý những phần LƯU Ý của mình ở đầu bài, cũng như trong bài viết nhé. Đặc biệt là lưu ý những bài viết trong series Fullstack Vỡ Lòng của mình đang sử dụng MySQL version 8.0.32, vì vậy có thể có những điểm bạn đọc thấy không giống với kiến thức ở các version trước hoặc sau này.

Hôm nay, mình sẽ chia sẻ tiếp phần tiếp theo trong chuỗi 3 bài về "Các kiểu dữ liệu thường dùng nhất trong MySQL", đó là String Data Types.

Mô tả chung về String Data Types

  • Anh em cần lưu ý rằng: Các kiểu dữ liệu có thể có cách đặt tên KHÁC NHAU ở các HỆ QUẢN TRỊ CƠ SỞ DỮ LIỆU KHÁC NHAU.
  • Ví dụ: Nhiều bạn đã từng dùng các hệ quản trị cơ sở dữ liệu khác như SQL Server chẳng hạn, khi chuyển sang học MySQL sẽ không thấy kiểu dữ liệu NVARCHAR, UNIQUEIDENTIFIER. Các bạn có thể coi điều là này BÌNH THƯỜNG, giống như ngôn ngữ lập trình vậy đó, JavaC# cùng dùng trong lập trình hướng đối tượng, nhưng cú pháp của nó cũng khác nhau kha khá.
  • String Data Types trong MySQL bao gồm rất nhiều kiểu dữ liệu khác nhau như CHAR, VARCHAR, TEXT, BINARY, VARBINARY, BLOB, ENUM, SET. Tuy nhiên, trong khuôn khổ bài viết này, mình sẽ chỉ tập trung vào những kiểu dữ liệu thường được dùng nhất, đó là CHAR, VARCHARTEXT. Các kiểu dữ liệu còn lại trong String Data Types, các bạn có thể tìm hiểu thêm trên document của MySQL tại đây.

1. CHAR và VARCHAR

  • Kiểu dữ liệu CHARVARCHAR tương đối giống nhau.
  • Cả CHARVARCHAR đều cho phép bạn chỉ định độ dài tối đa cho số ký tự mà bạn muốn lưu trữ.
    • Ví dụ: Một cột có kiểu dữ liệu CHAR(30) tức là bạn có thể lưu trữ tối đa 30 ký tự.
  • SỰ KHÁC NHAU giữa chúng nằm ở 4 điểm sau:
    • Cách lưu trữ dữ liệu vào.
    • Các khoảng trắng ở cuối (trailing spaces).
    • Maximum length.
    • Cách lấy dữ liệu ra.
Điều kiện so sánh CHAR(size) VARCHAR(size)
Cách lưu trữ dữ liệu vào - Số ký tự của một cột có kiểu dữ liệu CHAR sẽ được fix cố định sau khi bạn tạo bảng. Ví dụ bạn khai báo một cột là CHAR(36), thì tất cả các dữ liệu sau này được insert vào cột đó sẽ đều chiếm 36 ký tự, bất kể bạn nhập ít hay nhiều hơn 36 ký tự.
- Nếu không bật strict mode, khi bạn cố insert một chuỗi có nhiều ký tự hơn max size, thì chuỗi đó sẽ bị cắt bớt đi để fit với size. Sẽ có warning đi kèm khi MySQL thực hiện việc này.
- Ngược lại, nếu bạn bật strict mode, khi số ký tự dài hơn max size, MySQL sẽ trả về thông báo lỗikhông cho phép insert vào database.
- Đối với các cột dữ liệu kiểu CHAR, việc cắt bỏ các khoảng trắng dư thừa ở cuối từ giá trị insert vào sẽ được thực hiện tự động mà không có warning, bất kể ở SQL mode nào.
- Còn VARCHAR thì chỉ lưu trữ đúng số lượng ký tự mà bạn nhập vào, miễn là số ký tự đó nhỏ hơn hoặc bằng size mà bạn đã chỉ định khi khai báo. Chữ VAR trong VARCHAR là viết tắt của từ Variable
- Tương tự CHAR, nếu không bật strict mode, khi bạn cố insert một chuỗi có nhiều ký tự hơn max size, thì chuỗi đó sẽ bị cắt bớt đi để fit với size. Sẽ có warning đi kèm khi MySQL thực hiện việc này.
- Ngược lại, nếu bạn bật strict mode, khi số ký tự dài hơn max size, sẽ trả về thông báo lỗikhông cho phép insert vào database.
- Đối với các cột dữ liệu kiểu VARCHAR, các khoảng trắng ở cuối cũng sẽ được cắt đi, nhưng sẽ có đi kèm với warning message.
Các khoảng trắng ở cuối (trailing spaces) - Khi lưu dữ liệu, nếu số ký tự của chuỗi bạn nhập vào nhỏ hơn size, thì MySQL sẽ tự thêm các khoảng trắng vào bên phải của chuỗi đó, cho đến khi số ký tự của chuỗi bằng với size - Đối với VARCHAR, MySQL sẽ KHÔNG TỰ THÊM khoảng trắng ở cuối chuỗi insert vào.
Maximum length size của CHAR có thể có giá trị từ 0 đến 255 - Trong khi với VARCHAR, size có thể có giá trị từ 0 đến 65,535.
- Các bạn cần ĐẶC BIỆT LƯU Ý, độ dài tối đa của VARCHAR còn tùy thuộc vào maximum row size (65,535 bytes, được chia sẻ cho tất cả các cột) và character set được sử dụng là gì.
- Ví dụ dễ hiểu về một trường hợp lỗi sau đây, mặc dù các giá trị size trong từng cột VARCHAR vẫn nhỏ hơn 65,535. Nhưng khi cộng tổng tất cả các cột vào thì nó đã lên tới 66,000 > 65,535. Và MySQL đã trả về thông báo lỗi Row size too large:
image.png
Cách lấy dữ liệu ra Khi lấy dữ liệu ra, MẶC ĐỊNH các khoảng trắng ở đầu và cuối chuỗi sẽ được loại bỏ (trim) Khi lấy dữ liệu ra, các khoảng trắng ở đầu và cuối chuỗi sẽ KHÔNG BỊ LOẠI BỎ.
- Ví dụ dưới đây sẽ giúp bạn hiểu rõ hơn:
image.png
  • Bổ sung thêm một ví dụ, mô tả sự khác nhau giữa CHAR(4)VARCHAR(4): image.png

  • LƯU Ý: Giá trị ở dòng cuối cùng trong bảng trên, sẽ chỉ đúng trong trường hợp strict mode bị tắt. Còn nếu bạn bật strict mode, và chuỗi insert vào vượt quá giá trị max size, thì chuỗi đó sẽ không được lưu lại, kèm theo một thông báo lỗi.

  • Một thuật ngữ khá phổ biến trong lập trình đó là "Tradeoff" - "Đánh đổi". Trong trường hợp để lựa chọn kiểu dữ liệu cho một cột là CHAR hay VARCHAR, bạn cũng cần cân nhắc giữa những sự đánh đổi này, đặc biệt trong trường hợp bảng dữ liệu của bạn lên tới HÀNG TRIỆU DÒNG, hoặc đánh index cho các cột :

    • Đánh đổi thứ nhất: VARCHAR lưu chuỗi theo độ dài của chính nó (variable-length), chứ không thêm các khoảng trắng vào cuối như CHAR (fixed-length). Vì vậy, đối với những cột thường xuyên có sự khác nhau giữa độ dài của các dòng trong bảng, thì lưu trữ theo kiểu VARCHAR sẽ tối ưu hơn, tốn ít dùng lượng lưu trữ hơn.
    • Đánh đổi thứ hai: Nhờ việc fix cứng chiều dài của mình, các thao tác chuỗi với kiểu dữ liệu CHAR sẽ nhanh hơn VARCHAR, vì các thao tác với chuỗi sẽ phải có thêm việc check length nếu bạn sử dụng VARCHAR. Ví dụ với việc đánh index, trung bình việc tìm kiếm dữ liệu với index của cột CHAR sẽ nhanh hơn 20% so với cột VARCHAR.

2. TEXT

  • Có 4 kiểu dữ liệu TEXT

    • TINYTEXT: "Tiny" nghĩa là nhỏ xíu, rất nhỏ. Các cột có kiểu dữ liệu TINYTEXT sẽ có thể lưu các chuỗi với chiều dài tối đa là 255 ký tự (= 28{2^8} - 1).
    • TEXT: normal-text, bình thường. Các cột có kiểu dữ liệu TEXT sẽ có thể lưu các chuỗi với chiều dài tối đa là 65,535 ký tự (= 216{2^{16}} - 1).
    • MEDIUMTEXT: "Medium" là trung bình. Các cột có kiểu dữ liệu MEDIUMTEXT sẽ có thể lưu các chuỗi với chiều dài tối đa là 16,777,215 ký tự (= 224{2^{24}} - 1).
    • LONGTEXT: "Long" là dài. Các cột có kiểu dữ liệu LONGTEXT sẽ có thể lưu các chuỗi với chiều dài tối đa là 4,294,967,295 ký tự (= 232{2^{32}} - 1).
  • Trong dự án mình làm trước, có chức năng Soạn mailGửi mail marketing. Để lưu trữ được nội dung HTML của email marketing mà người dùng đã soạn, thì mình đã phải sử dụng đến kiểu ký tự MEDIUMTEXT mới đủ để lưu trữ.

  • Nếu các bạn đã đọc bài viết về "Kiểu dữ liệu dạng số - Numeric Data Types" thì sẽ thấy một sự KHÔNG NHẤT QUÁN nho nhỏ trong cách đặt tên của MySQL.

    • Đó là: Với kiểu dữ liệu INTEGER, thì size của INT sẽ lớn hơn MEDIUMINT.
    • Tuy nhiên, khi đặt tên với TEXT, thì MySQL lại để max length của TEXT nhỏ hơn MEDIUMTEXT 😮‍💨
    • Vì vậy, các bạn hãy để ý điểm này để không bị nhầm nhé.
  • Sự khác nhau giữa TEXT với CHAR, VARCHAR:

    TEXT CHAR(size), VARCHAR(size)
    Fix cứng max size65,535 ký tự (bạn không thể tùy biến giá trị max size này) Bạn có thể tùy biến giá trị size để quyết định số ký tự trong một cột. Giá trị size sẽ nằm trong khoảng từ 0 đến 65,535.
    - Nếu muốn đánh index cho cột có kiểu dữ liệu TEXT, bạn cần phải chỉ định số ký tự bạn sẽ đánh index cho một cột có kiểu dữ liệu TEXT.
    - Ví dụ:
    CREATE TABLE test_table (text_col TEXT, INDEX(text_col(10)));
    - Ý nghĩa của đoạn code trên là bạn sẽ đánh index cho cột text_col, nhưng sẽ chỉ sử dụng 10 ký tự đầu tiên trong các giá trị của cột text_col này.
    - Ngoại trừ một trường hợp đặc biệt, nếu bạn vẫn muốn đánh index sử dụng tất cả ký tự trong cột TEXT, bạn có thể đánh index kiểu FULLTEXT. Tuy nhiên, MySQL khuyến nghị cách đánh index FULLTEXT sẽ chậm hơn.
    Vì vậy, nếu muốn đánh index cho cột, thì bạn nên lựa chọn CHAR hoặcVARCHAR nếu có thể.

TÀI LIỆU THAM KHẢO

Ngoài ra, các bạn cũng có thể follow page Facebook và channel Youtube này để cập nhật những thông tin thú vị về Lập trình nhé: Facebook Youtube


All rights reserved

Viblo
Hãy đăng ký một tài khoản Viblo để nhận được nhiều bài viết thú vị hơn.
Đăng kí