2009-09-18 38 views
15

Tôi có một bảng có kích thước khiêm tốn, 277k bản ghi tại thời điểm này, mà tôi đang cố gắng thực hiện tìm kiếm FULLTEXT trên đó. Tìm kiếm có vẻ rất nhanh cho đến khi nó đến giai đoạn Gửi dữ liệu.MySQL "Gửi dữ liệu" khủng khiếp chậm

Bảng:

CREATE TABLE `sqinquiries_inquiry` (
    `id` int(11) NOT NULL AUTO_INCREMENT, 
    `ts` datetime NOT NULL, 
    `names` longtext NOT NULL, 
    `emails` longtext NOT NULL, 
    PRIMARY KEY (`id`), 
    FULLTEXT KEY `sqinquiries_inquiry_search` (`names`,`emails`) 
) ENGINE=MyISAM AUTO_INCREMENT=305560 DEFAULT CHARSET=latin1 

Các truy vấn:

SELECT * FROM `sqinquiries_inquiry` WHERE (
    MATCH (`sqinquiries_inquiry`.`names`) AGAINST ('smith' IN BOOLEAN MODE) OR 
    MATCH (`sqinquiries_inquiry`.`emails`) AGAINST ('smith' IN BOOLEAN MODE) 
) ORDER BY `sqinquiries_inquiry`.`id` DESC LIMIT 100 

Các hồ sơ: (Tôi snipped ra thông tin dường như vô dụng)

+-------------------------+----------+ 
| Status     | Duration | 
+-------------------------+----------+ 
| preparing    | 0.000014 | 
| FULLTEXT initialization | 0.000015 | 
| executing    | 0.000004 | 
| Sorting result   | 0.000008 | 
| Sending data   | 2.247934 | 
| end      | 0.000011 | 
| query end    | 0.000003 | 
+-------------------------+----------+ 

Các DESCRIBE sẽ rất tốt, một đơn giản lót: Các Mô tả:

id: 1 
select_type: SIMPLE 
table: sqinquiries_inquiry 
type: index 
possible_keys: NULL 
key: PRIMARY 
key_len: 4 
ref: NULL 
rows: 100 
Extra: Using where 

Vì vậy, những gì tôi không hiểu được nơi 2.25 giây gửi dữ liệu sẽ đến từ đâu? Tôi thấy hiệu suất tương tự trong Python và trong giao diện điều khiển mysql ứng dụng, cả hai kết nối với localhost.

Cập nhật:

  • mỗi comment yêu cầu kích thước hàng trung bình, đó là: 53,8485
  • mỗi bình luận, đây là DESCRIBE trên.
+0

lượng dữ liệu bạn đang truy xuất là bao nhiêu? nếu bạn không biết, hãy xem bảng thống kê và cho chúng tôi biết kích thước hàng trung bình. – longneck

+0

Không chắc chắn làm thế nào để tìm ra kích thước hàng trung bình, vì vậy tôi ném đầu ra này lên: 'SELECT AVG (LENGTH (tên) + LENGTH (email) + LENGTH (id) + LENGTH (ts)) như avg_length từ sqinquiries_inquiry'. Nếu có cách nào tốt hơn, hãy cho tôi biết. –

+0

Vấn đề là bạn không sử dụng 'FULLTEXT KEY'. Bạn có thể vui lòng đăng 'DESCRIBE'? – Quassnoi

Trả lời

32

DESCRIBE trông tuyệt vời, một lớp lót đơn giản.

Vì bạn chỉ đang sử dụng một bảng trong truy vấn của mình nên không thể có bất kỳ thứ gì khác ngoài một lớp lót.

Tuy nhiên, truy vấn của bạn không sử dụng chỉ mục FULLTEXT.

Đối với các chỉ số để có thể sử dụng, bạn nên viết lại truy vấn một chút:

SELECT * 
FROM sqinquiries_inquiry 
WHERE MATCH (names, emails) AGAINST ('smith' IN BOOLEAN MODE) 
ORDER BY 
     id DESC 
LIMIT 100 

MATCH chỉ sử dụng các chỉ số nếu bạn kết hợp chống lại các thiết lập chính xác các cột chỉ số được xác định trên.

Do đó truy vấn của bạn sử dụng quét chỉ mục trên id: Using index; Using where ở cuối của DESCRIBE.

Sending data là khá gây hiểu lầm: đây thực sự là thời gian trôi qua giữa khi kết thúc hoạt động trước đó và kết thúc của hoạt động hiện tại.

Ví dụ, tôi chỉ cần chạy truy vấn này:

SET profiling = 1; 

SELECT * 
FROM t_source 
WHERE id + 1 = 999999; 

SHOW PROFILE FOR QUERY 39; 

mà trở lại một hàng duy nhất và hồ sơ này:

'starting', 0.000106 
'Opening tables', 0.000017 
'System lock', 0.000005 
'Table lock', 0.000014 
'init', 0.000033 
'optimizing', 0.000009 
'statistics', 0.000013 
'preparing', 0.000010 
'executing', 0.000003 
'Sending data', 0.126565 
'end', 0.000007 
'query end', 0.000004 
'freeing items', 0.000053 
'logging slow query', 0.000002 
'cleaning up', 0.000005 

Kể từ khi chỉ số này không sử dụng được, MySQL cần thực hiện đầy đủ các bảng quét.

0.126565 giây là thời gian từ lúc bắt đầu thực hiện (thời gian hàng đầu tiên được đọc) và kết thúc vào quá trình thực hiện (thời gian hàng cuối cùng được gửi cho khách hàng).

Hàng cuối cùng này nằm ở cuối bảng và mất nhiều thời gian để tìm và gửi.

P. S. Edited để loại bỏ các downvote :)

+0

Tôi đang sử dụng phiên bản 5.1.35. Và tại sao chỉ mục không thể sử dụng được? –

+0

'@Jack M.': bài đăng của tôi giải thích lý do. – Quassnoi

+0

'@Jack M.': và bạn có thể giải thích câu trả lời của mình không? – Quassnoi

-8

Tôi nghĩ bạn chuyển nhiều dữ liệu của một kết nối mạng chậm.

Thay vì chọn * chỉ chọn các cột bạn thực sự cần.

Nếu bảng của bạn chứa các trường văn bản lớn mà bạn muốn hiển thị trong kết quả, bạn có thể sử dụng chuỗi con để chỉ chuyển một vài ký tự/từ đầu tiên của văn bản.

Một số khách hàng hỗ trợ nén các gói kết quả. Có lẽ yxou muốn có một cái nhìn về điều đó.

+2

Điều này đang chạy từ máy chủ cục bộ, chỉ trả về 100 kết quả và hầu hết kết quả là 1 địa chỉ email và một tên. Không phải số lượng lớn dữ liệu, không phải là kết nối chậm. –

Các vấn đề liên quan