Bốn độ đo xếp hạng và chỗ chúng bất đồng ý
Bốn độ đo xếp hạng và chỗ chúng bất đồng ý
Một danh sách mười kết quả tìm kiếm, bốn con số chấm điểm nó, và bốn kết luận khác nhau về chất lượng. Chọn nhầm thước ở đây là cách phổ biến nhất để tự lừa mình khi đánh giá một hệ RAG.
Khâu truy hồi của một hệ RAG trả về một danh sách đã xếp hạng, và câu hỏi tự nhiên là danh sách đó tốt tới đâu. Có bốn con số hay được dùng để trả lời: precision@k, recall@k, MRR và nDCG@k. Chúng đo bốn thứ khác nhau, phản ứng khác nhau khi bạn xáo thứ tự, và trên cùng một danh sách chúng có thể dẫn tới bốn kết luận không giống nhau. Không con số nào sai. Vấn đề nằm ở chỗ báo cáo thường chỉ in một con số.
Ba điều cần thống nhất trước khi bấm gì. Thứ nhất, mỗi kết quả mang một mức liên quan từ 0 tới 3 chứ không chỉ đúng hoặc sai, vì trong thực tế có tài liệu trả lời trọn câu hỏi và có tài liệu chỉ liên quan xa. Thứ hai, precision, recall và MRR là các độ đo nhị phân nên chúng phải gộp thang bốn mức đó thành có hoặc không: ở đây quy ước kết quả nào có rel từ 1 trở lên thì tính là liên quan. Thứ ba, chỉ nDCG dùng được cả bốn mức, và đó vừa là sức mạnh vừa là chỗ nó sinh ra tranh cãi.
- 1Hướng dẫn đăng ký học phần trực tuyến
- 2Lịch đăng ký học phần từng khoá
- 3Giới thiệu chung về nhà trường
- 4Quy định số tín chỉ tối đa mỗi kỳ
- 5Thông báo nghỉ lễ Quốc khánh
- 6Xử lý lỗi thường gặp khi đăng ký
- 7Danh sách phòng học toà A
- 8Hướng dẫn rút học phần
- 9Biểu mẫu đơn xin phúc khảo
- 10Mức học phí và hạn nộp
số kết quả liên quan trong top k / k3 / 5 = 0.600rel ≥ 1 nằm trong 5 hạng đầu. Mẫu số là chính mốc cắt, nên precision không hề biết dưới mốc cắt còn gì.số kết quả liên quan trong top k / tổng số kết quả liên quan3 / 6 = 0.5006 kết quả liên quan. Vì mẫu số cố định, recall không bao giờ giảm khi bạn kéo k to ra.1 / vị trí kết quả liên quan đầu tiên1 / 1 = 1.000k, và cũng không đổi khi bạn xáo mọi thứ sau hạng 1.DCG@k / IDCG@k, với gain = rel và discount = log2(i + 1)5.123 / 7.141 = 0.717IDCG lấy từ thứ tự lý tưởng, tức chính các nhãn này xếp giảm dần, chứ không phải từ thứ tự đang hiển thị. Bỏ mốc cắt đi và tính trên cả 10 kết quả thì nDCG là 0.907.gain = relchỉ 5 dòng đầu vào tổng, phần còn lại để mờ| i | kết quả đang xếp | rel | gain | log2(i+1) | gain chia log2 | DCG cộng dồn | thứ tự lý tưởng | rel | gain | gain chia log2 | IDCG cộng dồn |
|---|---|---|---|---|---|---|---|---|---|---|---|
| 1 | Hướng dẫn đăng ký học phần trực tuyến | 3 | 3 | 1.000 | 3.000 | 3.000 | Hướng dẫn đăng ký học phần trực tuyến | 3 | 3 | 3.000 | 3.000 |
| 2 | Lịch đăng ký học phần từng khoá | 2 | 2 | 1.585 | 1.262 | 4.262 | Xử lý lỗi thường gặp khi đăng ký | 3 | 3 | 1.893 | 4.893 |
| 3 | Giới thiệu chung về nhà trường | 0 | 0 | 2.000 | 0.000 | 4.262 | Lịch đăng ký học phần từng khoá | 2 | 2 | 1.000 | 5.893 |
| 4 | Quy định số tín chỉ tối đa mỗi kỳ | 2 | 2 | 2.322 | 0.861 | 5.123 | Quy định số tín chỉ tối đa mỗi kỳ | 2 | 2 | 0.861 | 6.754 |
| 5 | Thông báo nghỉ lễ Quốc khánh | 0 | 0 | 2.585 | 0.000 | 5.123 | Hướng dẫn rút học phần | 1 | 1 | 0.387 | 7.141 |
| 6 | Xử lý lỗi thường gặp khi đăng ký | 3 | 3 | 2.807 | 1.069 | 6.192 | Mức học phí và hạn nộp | 1 | 1 | 0.356 | 7.497 |
| 7 | Danh sách phòng học toà A | 0 | 0 | 3.000 | 0.000 | 6.192 | Giới thiệu chung về nhà trường | 0 | 0 | 0.000 | 7.497 |
| 8 | Hướng dẫn rút học phần | 1 | 1 | 3.170 | 0.315 | 6.507 | Thông báo nghỉ lễ Quốc khánh | 0 | 0 | 0.000 | 7.497 |
| 9 | Biểu mẫu đơn xin phúc khảo | 0 | 0 | 3.322 | 0.000 | 6.507 | Danh sách phòng học toà A | 0 | 0 | 0.000 | 7.497 |
| 10 | Mức học phí và hạn nộp | 1 | 1 | 3.459 | 0.289 | 6.796 | Biểu mẫu đơn xin phúc khảo | 0 | 0 | 0.000 | 7.497 |
DCG cộng dồn và cột IDCG cộng dồn trùng nhau ở mọi dòng, nên thương của chúng bằng 1 với mọi k và với cả hai quy ước gain. Bấm Xếp theo thứ tự lý tưởng rồi kéo thanh k và gạt ô quy ước để tự kiểm.k = 5, hai quy ước gain cho hai con số: gain = rel ra 0.717, còn gain = 2^rel - 1 ra 0.698. Quy ước mũ khuếch đại khoảng cách giữa các mức, một kết quả rel 3 đáng giá 7 thay vì 3, nên nó phạt nặng hơn khi bạn chôn kết quả tốt nhất xuống dưới, và cũng thưởng đậm hơn khi bạn kéo nó lên đầu. Không quy ước nào đúng hơn quy ước nào. Đọc một bảng nDCG mà không biết người ta dùng quy ước nào thì con số đó không so sánh được với con số của bạn.3.Hãy làm năm việc trong sim, theo thứ tự.
Một: nhìn trạng thái mặc định trước khi bấm gì cả. Mười tài liệu được truy hồi cho truy vấn quy trình đăng ký học phần, mốc cắt đang là k = 5, quy ước gain đang là gain = rel. Sáu trong mười tài liệu liên quan, ba trong số đó nằm trong năm hạng đầu, và hạng 1 đã trúng đích. Bốn con số vì thế là precision@5 = 3/5 = 0.600, recall@5 = 3/6 = 0.500, MRR = 1/1 = 1.000 và nDCG@5 = 5.123 / 7.141 = 0.717.
Bốn con số này nói bốn chuyện. MRR bảo hệ hoàn hảo. precision@5 bảo hơn nửa số kết quả hiển thị là rác. recall@5 bảo bạn mới lấy được một nửa số tài liệu đáng lấy. nDCG@5 bảo thứ tự tạm ổn nhưng còn xa mức lý tưởng. Cả bốn đều đọc đúng cùng một danh sách. Và ngay tại đây, chỉ cần gạt ô Quy ước gain sang 2^rel - 1, nDCG@5 đã tụt từ 0.717 xuống 0.698 mà không một nhãn nào bị sửa. Ba con số kia đứng im, vì chúng không dùng tới thang bốn mức.
Hai: kéo thanh k và xem cái gì đi theo, cái gì không. Ở k = 1, precision là 1.000 và nDCG cũng là 1.000, trông như hoàn hảo, trong khi recall chỉ 0.167. Ở k = 3, ba số thành 0.667, 0.333 và 0.723. Ở k = 6, chúng thành 0.667, 0.667 và 0.826. Ở k = 10, recall chạm 1.000 vì mọi tài liệu liên quan đều đã nằm trong danh sách, còn precision quay về 0.600 và nDCG lên 0.907.
Ba điều đáng ghi. recall@k không bao giờ giảm khi k tăng, vì tử số chỉ có thể thêm còn mẫu số đứng yên. precision@k thì lên xuống tuỳ vị trí kế tiếp trúng hay trượt. Và MRR đứng im suốt cả hành trình kéo thanh trượt: nó chỉ nhìn đúng một kết quả, cái liên quan đầu tiên, nên mọi thứ về sau đều vô hình với nó. Kéo k lên 11 hoặc 12, tức quá số kết quả, thì sim hiện cảnh báo và nói rõ mẫu số của precision đang được lấy bằng min(k, n) chứ không phải k. Đây là một quy ước, thư viện khác có thể chia thẳng cho k và cho ra số thấp hơn trên đúng cùng dữ liệu.
Ba: bấm preset MRR mù. Truy vấn là cách xin cấp lại thẻ sinh viên. Hạng 1 trúng đích với rel 3, nhưng bốn tài liệu liên quan còn lại bị chôn ở các hạng 7, 8, 9, 10. Bốn con số ở k = 5: MRR = 1.000, precision@5 = 0.200, recall@5 = 0.200, nDCG@5 = 0.399.
Bây giờ bấm Xếp theo thứ tự lý tưởng rồi nhìn bảng so sánh hiện ra ngay dưới. precision@5 nhảy từ 0.200 lên 1.000, recall@5 cũng vậy, nDCG@5 từ 0.399 lên 1.000. MRR giữ nguyên 1.000, chênh lệch đúng bằng 0.000. Đây không phải lỗi cài đặt mà là định nghĩa: MRR là nghịch đảo vị trí của kết quả liên quan đầu tiên, và vị trí đó vốn đã là 1 nên không có gì để cải thiện. MRR là thước đúng cho bài toán chỉ cần một câu trả lời, chẳng hạn tìm kiếm điều hướng hay hỏi đáp một đáp án. Nó là thước sai cho RAG, vì RAG thường nhồi năm tới mười đoạn vào ngữ cảnh và cần cả năm đoạn đó đáng giá.
Bốn: bấm preset Ranh giới k, để k = 5, rồi bấm nút Đảo hạng 5 với hạng 6. Hạng 5 đang là một tài liệu không liên quan, hạng 6 là một tài liệu rel 3. Sau cú đảo, precision@5 nhảy từ 0.800 lên 1.000, tăng đúng một bậc 1/5. Trong khi đó nDCG tính trên cả danh sách, tức con số ở dòng dưới cùng của thẻ nDCG, chỉ nhích từ 0.931 lên 0.943, đúng 0.012.
Lý do rất cơ học. Với nDCG không cắt, đổi chỗ hai vị trí liền nhau chỉ đổi hai mẫu số chiết khấu là log2(6) = 2.585 và log2(7) = 2.807, hai số gần nhau nên hiệu quả nhỏ. Với precision@k, mốc cắt là một bức tường: ở bên này tường thì được tính, sang bên kia là biến mất hoàn toàn. Càng xuống cuối danh sách thì hiệu ứng càng nhạt đi chứ không đậm thêm. Nút đảo luôn ăn theo mốc cắt hiện tại, nên muốn thử ở đáy thì kéo k lên 9 cho nút đổi nhãn thành Đảo hạng 9 với hạng 10, bấm nó, rồi kéo k về lại 5. Lúc đó precision@5, recall@5, MRR và cả nDCG@5 đứng im tuyệt đối, còn nDCG cả danh sách chỉ nhúc nhích từ 0.931 lên 0.933, tức 0.16 điểm phần trăm, nhỏ hơn cú đảo ở mốc cắt gần tám lần.
Ở đây phải nói thẳng một chỗ mà nhiều tài liệu diễn đạt cẩu thả. Người ta hay bảo "nDCG mượt còn precision@k giật cục". Điều đó chỉ đúng với nDCG không cắt. Bản thân nDCG@k cũng có mốc cắt cứng y hệt: trong chính cú đảo hạng 5 với hạng 6 ở trên, nDCG@5 nhảy từ 0.787 lên 0.950, tức mạnh hơn cả precision@5. Cái mượt nằm ở hàm chiết khấu, không nằm ở chữ nDCG.
Năm: bấm preset Hai quy ước lệch xa nhất, để k = 5, rồi gạt ô Quy ước gain. Danh sách này có năm tài liệu rel 1 chiếm trọn top 5 và hai tài liệu rel 3 nằm ngay dưới mốc cắt. Với gain = rel, nDCG@5 là 0.475. Với gain = 2^rel - 1, nDCG@5 là 0.232. Chênh hơn gấp đôi, trên đúng cùng một danh sách, cùng một k, cùng một bộ nhãn.
Bảng từng vị trí giải thích ngay tại chỗ. DCG@5 không đổi giữa hai quy ước, vì top 5 toàn rel 1 mà cả hai quy ước đều gán gain bằng 1 cho mức đó. Cái đổi là IDCG@5: thứ tự lý tưởng bắt đầu bằng hai tài liệu rel 3, và rel 3 đáng giá 3 theo quy ước tuyến tính nhưng đáng giá 7 theo quy ước mũ. Mẫu số phình ra, thương số co lại.
Đây chính là chỗ hai thư viện cho hai kết quả khác nhau trên cùng dữ liệu, và cả hai quy ước đều là quy ước thật đang chạy trong công cụ thật. Bài gốc của Jarvelin và Kekalainen dùng gain = rel, và scikit-learn cài ndcg_score đúng theo lối tuyến tính đó. Các bài về quảng cáo và học xếp hạng về sau phổ biến hoá gain = 2^rel - 1 vì nó phạt nặng hơn khi tài liệu tốt nhất bị chôn, và đó là quy ước mà mục tiêu xếp hạng của LightGBM cũng như XGBoost dùng. Nghĩa là chấm cùng một bộ kết quả bằng scikit-learn và bằng LightGBM, bạn nhận hai con số nDCG khác nhau mà không bên nào tính sai. Ngày nay cả hai đều sống, và một số thư viện chọn sẵn một quy ước rồi không nói ra. Nếu bạn so nDCG của mình với nDCG in trong một bài báo mà không biết bài đó dùng quy ước nào, phép so đó không có nghĩa. Điều tương tự đúng với cơ số của hàm chiết khấu, với cách xử lý khi k vượt độ dài danh sách, và với cách xử lý các trường hợp 0/0.
Vài chỗ khác cần biết đúng:
- Ca vàng: thứ tự đã lý tưởng thì
nDCGbằng đúng1. Bấm presetThứ tự lý tưởng, rồi kéokqua mọi giá trị và gạt cả hai quy ước gain.nDCGluôn là1.000. Lý do nằm ngay trong bảng: khi danh sách đã xếp giảm dần theo mức liên quan, cộtDCG cộng dồnvà cộtIDCG cộng dồntrùng nhau ở mọi dòng, nên thương của chúng bằng 1 bất kể cắt ở đâu và gain tính thế nào. Ở preset đóprecision@5là1.000nhưngrecall@5chỉ0.714, vì trong bảy tài liệu liên quan mới lấy được năm. Xếp hoàn hảo không có nghĩa là lấy đủ. - Không kết quả nào liên quan là ca biên phải định nghĩa rõ. Bấm preset
Không cái nào liên quan:recalllà0/0,MRRkhông có vị trí nào để lấy nghịch đảo, vàIDCGbằng0nênnDCGcũng là0/0. Sim quy ước ba con số đó bằng0và nói rõ đó là quy ước hiển thị để không cóNaNlọt ra màn hình. Con số thứ tư thì không cần quy ước nào:precision@5bằng0một cách thật thà, vì nó là0/5chứ không phải0/0. Với ba con số kia, có thư viện trả vềNaN, có thư viện báo lỗi, có thư viện trả về0. Ba hành vi, ba con số trung bình khác nhau khi bạn gộp kết quả của nhiều truy vấn. - Đảo thứ tự các kết quả không liên quan với nhau thì không đổi con số nào. Muốn thử thì phải tìm được các hạng
rel 0nằm liền nhau. Bấm presetRanh giới k: hạng 7, 8 và 9 ở đó đều làrel 0. Kéo tài liệu hạng 7 xuống hạng 9, cả năm dòng của bảng so sánh hiện0.000, ở mọikvà ở cả hai quy ước gain. Đây không phải sự trùng hợp: cả hai quy ước gain đều gửirel 0vềgain 0, nên các vị trí đó không đóng góp gì vàoDCGdù chiết khấu của chúng khác nhau. - Nhưng kéo thả là phép dời chỗ, không phải phép đổi chỗ hai đầu. Ở danh sách mặc định, các hạng
rel 0là 3, 5, 7 và 9, không có hai hạng nào liền nhau. Kéo tài liệu hạng 3 xuống hạng 5 vì thế không hề vô hại: nó đẩy tài liệurel 2đang ở hạng 4 lên hạng 3, vànDCG@5nhích từ0.717lên0.737. Chỉprecision,recallvàMRRlà đứng im, vì cả ba đều không nhìn thứ tự bên trong mốc cắt. Đây là chỗ rất dễ tự lừa mình khi đọc nhanh: hai tài liệu bạn nhắm tới đềurel 0thật, nhưng cái bị xê dịch theo lại không phải. - Mọi mức bằng nhau thì thứ tự mất hết ý nghĩa. Bấm preset
Mọi mức bằng nhau: mười thông báo đềurel 2. Mọi thứ tự đều là thứ tự lý tưởng nênnDCGluôn1.000,precisionluôn1.000, vàrecall@kđơn giản làkchia10cho tới khikchạm10, sau đó nó nằm lì ở1.000dù bạn kéo tiếp lên11hay12, vì mốc cắt thật sự dừng ở số kết quả. Xáo trộn kiểu gì cũng không đổi được con số nào. Bài học kèm theo: nếu bộ nhãn của bạn chỉ có một mức,nDCGkhông còn phân biệt được gì và bạn đang trả tiền cho một công thức phức tạp mà không mua được thông tin. - Sim này chỉ có một truy vấn. Chữ
MtrongMRRlà mean, tức trung bình trên nhiều truy vấn. Ở đây chỉ có một truy vấn nên con số hiển thị thực chất làRRcủa truy vấn đó. Điều tương tự vớinDCGvàprecision: trong báo cáo thật, chúng được lấy trung bình trên cả tập truy vấn, và một truy vấn dễ có thể che một truy vấn khó. Sim không dựng được chuyện đó, nên đừng suy rộng từ một danh sách ra chất lượng của cả hệ thống.
Hỏi "hệ truy hồi của bạn đạt bao nhiêu" là hỏi chưa đủ. Phải hỏi thêm: đo bằng thước nào, cắt ở k bằng mấy, và nếu là nDCG thì dùng quy ước gain nào. MRR chỉ nhìn kết quả liên quan đầu tiên nên nó mù với phần còn lại của danh sách, hợp cho bài toán một đáp án và sai cho RAG. precision@k và nDCG@k đều có mốc cắt cứng nên một cú đảo vượt mốc k làm chúng nhảy mạnh, trong khi nDCG không cắt thì gần như không thấy gì. Và nDCG là con số duy nhất trong bốn con số mà chỉ riêng việc đổi một quy ước cài đặt đã đủ làm nó giảm hơn một nửa.
- 1Hai nhóm chấm cùng một danh sách kết quả, cùng k = 5, cùng bộ nhãn liên quan. Một nhóm báo nDCG@5 là 0.475, nhóm kia báo 0.232. Kết luận nào đúng?
- 2Một hệ trả kết quả đúng ngay ở hạng 1, còn bốn tài liệu liên quan khác bị chôn ở các hạng 7 tới 10. Bạn xếp lại danh sách cho hoàn hảo. Độ đo nào KHÔNG nhúc nhích?
- 3Ở k = 5, bạn đảo chỗ kết quả hạng 5 (không liên quan) với kết quả hạng 6 (rel 3). Điều gì xảy ra?