2008-12-28 24 views
6

Tôi đang thực hiện chức năng tìm kiếm cho trang web của mình, tìm các kết quả có liên quan từ cơ sở dữ liệu. Tôi đang tìm một cách để đếm số lần xuất hiện của một từ, nhưng tôi cần đảm bảo rằng có các ranh giới từ trên cả hai mặt của từ (vì vậy tôi không kết thúc với "ba" khi tôi muốn "rip").Số lần xuất hiện của một từ liên tiếp trong MySQL

Có ai có ý tưởng nào không?


dân đã hiểu lầm câu hỏi của tôi:

Làm thế nào tôi có thể đếm số lần xuất hiện như trong một hàng duy nhất?

Trả lời

2

Đây không phải là thứ mà cơ sở dữ liệu quan hệ rất giỏi, trừ khi bạn có thể sử dụng chỉ mục toàn văn, và bạn đã tuyên bố rằng bạn không thể, vì bạn đang sử dụng InnoDB. Tôi khuyên bạn nên chọn các hàng có liên quan của bạn và thực hiện đếm số từ trong mã ứng dụng của bạn.

0

Something như thế này nên làm việc:

select count (*) từ bàn nơi fieldname REGEXP '[[: <:]] từ [[:>:]]';

Chi tiết gory có trong sách hướng dẫn sử dụng MySQL, mục 11.4.2.

+2

này kiểm tra có bao nhiêu hàng chứa chuỗi tìm kiếm. Người hỏi muốn đếm tần suất chuỗi tìm kiếm được chứa trong mỗi hàng. – flu

0

Thứ gì đó như LIKE hoặc REGEXP sẽ không được chia tỷ lệ (trừ khi đó là giá trị tiền tố ngoài cùng bên trái).

Hãy xem xét thay vì sử dụng fulltext index cho những gì bạn muốn làm.

select count(*) from yourtable where match(title, body) against ('some_word'); 
+0

Không thể làm chỉ mục toàn văn ... Tôi đang sử dụng InnoDB. – stalepretzel

0

Tôi đã sử dụng kỹ thuật như được mô tả trong liên kết bên dưới. Phương pháp này sử dụng các hàm lengthreplace của MySQL.

Keyword Relevance

1

Bạn có thể thử cách biến thái này:

SELECT 
(LENGTH(field) - LENGTH(REPLACE(field, 'word', '')))/LENGTH('word') AS `count` 
ORDER BY `count` DESC 
  • Truy vấn này có thể rất chậm
  • Nó trông khá xấu xí
  • REPLACE() là trường hợp nhạy cảm
+0

Điều này sẽ tính * chuỗi *, chứ không phải * từ *. – RandomSeed

1

Bạn có thể khắc phục sự cố chức năng REPLACE() phân biệt chữ hoa chữ thường của mysql bằng cách sử dụng LOWER().

Sự cẩu thả của nó, nhưng cuối cùng, truy vấn này chạy khá nhanh.

Để tăng tốc độ, tôi lấy kết quả trong một lựa chọn mà tôi đã khai báo dưới dạng bảng dẫn xuất trong truy vấn 'bên ngoài' của tôi. Kể từ mysql đã có kết quả tại thời điểm này, phương pháp thay thế hoạt động khá nhanh chóng.

Tôi đã tạo truy vấn tương tự như truy vấn bên dưới để tìm kiếm nhiều cụm từ trong nhiều bảng và nhiều cột.Tôi có được một 'phù hợp' số tương đương với tổng số lượng của tất cả các occurrances của tất cả các thuật ngữ tìm kiếm tìm thấy trong tất cả các cột đã tìm kiếm

SELECT DISTINCT ( 
((length(x.ent_title) - length(replace(LOWER(x.ent_title),LOWER('there'),'')))/length('there')) 
+ ((length(x.ent_content) - length(replace(LOWER(x.ent_content),LOWER('there'),'')))/length('there')) 
+ ((length(x.ent_title) - length(replace(LOWER(x.ent_title),LOWER('another'),'')))/length('another')) 
+ ((length(x.ent_content) - length(replace(LOWER(x.ent_content),LOWER('another'),'')))/length('another')) 
) as relevance, 
x.ent_type, 
x.ent_id, 
x.this_id as anchor, 
page.page_name 
FROM ( 
(SELECT 
'Foo' as ent_type, 
sp.sp_id as ent_id, 
sp.page_id as this_id, 
sp.title as ent_title, 
sp.content as ent_content, 
sp.page_id as page_id 
FROM sp 
WHERE (sp.title LIKE '%there%' OR sp.content LIKE '%there%' OR sp.title LIKE '%another%' OR sp.content LIKE '%another%') AND (sp_content.title NOT LIKE '%goes%' AND sp_content.content NOT LIKE '%goes%') 
) UNION (
    [search a different table here.....] 
) 
) as x 
JOIN page ON page.page_id = x.page_id 
WHERE page.rstatus = 'ACTIVE' 
ORDER BY relevance DESC, ent_title; 

Hy vọng điều này sẽ giúp người

- Seacrest ra

+0

Điều này sẽ tính * chuỗi *, chứ không phải * từ *. – RandomSeed

-3

Nó phụ thuộc vào những gì DBMS bạn đang sử dụng, một số cho phép viết UDF có thể làm điều này.

0

Nếu bạn muốn tìm kiếm, tôi sẽ tư vấn cho một số thứ như Sphinx hoặc Lucene, tôi thấy Sphinx (là một chỉ mục toàn văn độc lập) dễ thiết lập và chạy hơn. Nó chạy nhanh và tạo các chỉ mục rất nhanh. Ngay cả khi bạn đang sử dụng MyISAM tôi sẽ đề nghị sử dụng nó, nó có nhiều quyền lực hơn một chỉ mục văn bản đầy đủ từ MyISAM.

Nó cũng có thể tích hợp (phần nào) với MySQL.

1

tạo một người dùng hàm được định nghĩa như thế này và sử dụng nó trong truy vấn của bạn

DELIMITER $$ 

CREATE FUNCTION `getCount`(myStr VARCHAR(1000), myword VARCHAR(100)) 
    RETURNS INT 
    BEGIN 
    DECLARE cnt INT DEFAULT 0; 
    DECLARE result INT DEFAULT 1; 

    WHILE (result > 0) DO 
    SET result = INSTR(myStr, myword); 
    IF(result > 0) THEN 
     SET cnt = cnt + 1; 
     SET myStr = SUBSTRING(myStr, result + LENGTH(myword)); 
    END IF; 
    END WHILE; 
    RETURN cnt;  

    END$$ 

DELIMITER ; 

Hy vọng nó giúp Refer This

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