Lập chỉ mục các trường boolean


76

Đây có lẽ là một câu hỏi thực sự ngu ngốc, nhưng sẽ có nhiều lợi ích khi lập chỉ mục một trường boolean trong một bảng cơ sở dữ liệu?

Với một tình huống phổ biến, chẳng hạn như các bản ghi "xóa mềm" được gắn cờ là không hoạt động và do đó hầu hết các truy vấn đều bao gồm WHERE deleted = 0, liệu có hữu ích để trường đó được lập chỉ mục riêng hay nó được kết hợp với các trường thường được tìm kiếm khác trong một chỉ số khác nhau?



18
@AmirAliAkbari: Ồ! Không! Một tham chiếu vòng tròn! Hy vọng rằng SO sẽ không nổ!
Paul

Câu trả lời:


59

Không.

Bạn lập chỉ mục các trường được tìm kiếm và có tính chọn lọc / số lượng cao. Cardinality của trường boolean bị xóa trong gần như bất kỳ bảng nào. Nếu bất cứ điều gì, nó sẽ làm cho việc viết của bạn chậm hơn (bởi một lượng rất nhỏ).

Có thể bạn sẽ đặt nó trở thành trường đầu tiên trong chỉ mục được phân cụm nếu mọi truy vấn đều tính đến các thao tác xóa mềm?


5
tưởng tượng một cuốn sách lớn với hàng ngàn trang. Các trang chứa một chữ cái duy nhất, 'A' hoặc 'B' và một số ngẫu nhiên. Bạn có lợi ích khi tìm một mục nhập số ngẫu nhiên mà bạn biết rằng nó nằm trên một trong các trang 'A' khi trang A và trang B không được trộn lẫn nhưng cuốn sách chỉ bắt đầu với trang A rồi đến trang B không? Có bạn sẽ .. vì vậy tôi đoán bạn sai ..
tObi

1
Bạn có chắc điều này là đúng? Tôi có thể dễ dàng thấy một trường như vậy có giá trị, ví dụ: 99% trường hợp giá trị là 'không' và bạn chỉ truy vấn các giá trị 'có'. (EG chỉ có các bản ghi đang hoạt động?)
RonLugge

1
Tôi nghĩ câu trả lời là quá đơn giản, với nhiều chiến lược lập chỉ mục khác trong cơ sở dữ liệu hiện đại. Ví dụ: một chỉ mục một phần WHERE field = falsehoặc một số chỉ mục không phải btree khác thường dành riêng cho nền tảng, cung cấp các lựa chọn thay thế cho btree để tìm kiếm boolean. Nó cũng phụ thuộc vào điều kiện tìm kiếm của bạn và phần nào trong bảng là true so với false.
DB140141

17

Điều gì về cột đã xóa vào DATETIME? Có hai lợi ích.

  1. Nếu bạn cần một cột duy nhất như tên, bạn có thể tạo và xóa mềm một bản ghi có cùng tên nhiều lần (nếu bạn sử dụng chỉ mục duy nhất trên các cột đã xóa_tên VÀ tên)
  2. Bạn có thể tìm kiếm các bản ghi đã xóa gần đây.

Truy vấn của bạn có thể trông như thế này:

SELECT * FROM xyz WHERE deleted_at IS NULL

6

Tôi nghĩ nó sẽ hữu ích, đặc biệt là trong việc bao trùm các chỉ số.

Bao nhiêu / ít tất nhiên là phụ thuộc vào dữ liệu và truy vấn của bạn.

Bạn có thể có đủ loại lý thuyết về các chỉ số nhưng câu trả lời cuối cùng được đưa ra bởi công cụ cơ sở dữ liệu trong cơ sở dữ liệu với dữ liệu thực. Và bạn thường ngạc nhiên vì câu trả lời (hoặc có thể lý thuyết của tôi quá tệ;)

Kiểm tra kế hoạch truy vấn của các truy vấn của bạn và xác định xem các truy vấn có thể được cải thiện hoặc liệu các chỉ số có thể được cải thiện hay không. Nó khá đơn giản để thay đổi các chỉ số và xem nó tạo ra sự khác biệt gì


3
@OMGPonies Tác hại là phí ghi bổ sung, trên một bảng bận rộn với nhiều hàng, điều này thực sự có thể làm giảm hiệu suất truy vấn. Nó chỉ là một lợi ích khi có số lượng bản gốc cao và các truy vấn được xây dựng để tận dụng.
oucil

2

Tôi nghĩ sẽ hữu ích nếu bạn đang sử dụng chế độ xem (nơi đã xóa = 0) và bạn thường xuyên truy vấn từ chế độ xem này.


2

tôi nghĩ rằng nếu lĩnh vực boolean của bạn là như vậy mà bạn sẽ được đề cập đến chúng trong nhiều trường hợp, nó sẽ làm cho tinh thần để có một bảng riêng biệt, ví dụ DeletedPages, hoặc SpecialPages, sẽ có nhiều lĩnh vực kiểu boolean, như is_deleted, is_hidden, is_really_deleted, requires_higher_uservv, và thì bạn sẽ tham gia để có được chúng.

Thông thường, kích thước của bảng này sẽ nhỏ hơn và bạn sẽ nhận được một số lợi thế bằng cách tham gia, đặc biệt là liên quan đến khả năng đọc và khả năng bảo trì mã. Và đối với loại truy vấn này:

select all pages where is_deleted = 1

Sẽ nhanh hơn nếu nó được triển khai như thế này:

select all pages where pages 
inner join DeletedPages on page.id=deleted_pages.page_id 

Tôi nghĩ rằng tôi đã đọc nó ở đâu đó về cơ sở dữ liệu mysql rằng bạn cần một trường ít nhất phải có số lượng là 3 để làm cho việc lập chỉ mục hoạt động trên trường đó, nhưng hãy xác nhận điều này.


1
Thật khó để nói rằng boolean quá mỏng và chúng tôi không có bất kỳ dữ liệu nào, nhưng việc phát sinh một phép nối và quy trình làm việc của nó mỗi truy vấn sẽ làm cho các truy vấn chậm hơn, không nhanh hơn, đặc biệt nếu các khóa chính được phân nhóm khác nhau và nếu các trang bị xóa bảng là cần thiết cho mọi truy vấn.
Đánh dấu Canlas

0

Nếu bạn đang sử dụng cơ sở dữ liệu hỗ trợ chỉ mục bitmap (chẳng hạn như Oracle), thì một chỉ mục như vậy trên cột boolean sẽ hữu ích hơn nhiều so với không có.

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.