Xác định ý định câu hỏi trong hệ thống hỏi đáp

Tram Ho

Mục tiêu bài viết

Phân tích câu hỏi là pha đầu tiên trong kiến trúc chung của một hệ thống hỏi đáp, có nhiệm vụ tìm ra các thông tin cần thiết làm đầu vào cho quá trình xử lý của các pha sau (trích chọn tài liệu, trích xuất câu trả lời, …). Vì vậy phân tích câu hỏi có vai trò hết sức quan trọng, ảnh hưởng trực tiếp đến hoạt động của toàn bộ hệ thống. Nếu phân tích câu hỏi không tốt thì sẽ không thể tìm ra được câu trả lời.

Hôm nay mình sẽ trình bày về các phương pháp phân loại ý định của người hỏi trong hệ thống hỏi đáp dựa trên tập dữ liệu là các câu hỏi của sinh viên trường Đại học Xây dựng. Trong quá trình xây dựng mình đã thử nghiệm nhiều phương pháp khác nhau, tuy nhiên với phạm vi blog này mình sẽ chia sẻ một phương pháp tốt nhất mà mình đã sử dụng, các phương pháp khác mình sẽ chia sẻ dần trong các bài viết tiếp theo.

Xác định ý định là gì?

Đối với hệ thống hỏi đáp, phân loại ý định (intent classification) là việc xác định ý định của người hỏi khi tương tác với hệ thống thông qua câu hỏi hay câu truy vấn của người dùng.
Ví dụ đối với câu hỏi: “Cho mình hỏi địa chỉ cơ sở A ở đâu ạ?”, thì ý định của người dùng là họ đang muốn hỏi về ‘ADDRESS’, ví dụ khác như câu hỏi : “Thời gian mở cửa của cửa hàng là mấy giờ?” thì ý định của người dùng là hỏi về ‘TIME’.
Dựa vào việc xác định ý định sẽ giúp việc trả lời câu hỏi được chính xác và đưa ra được câu trả lời mong muốn của người dùng.

Các phương pháp xác định ý định

Đối với các bài toán cần xác định ý định, có nhiều phương pháp để thực hiện.

Hướng tiếp cận nông (shalow)

Phương pháp cổ điển là dựa trên tần suất xuất hiện và mức độ quan trọng các từ trong các ý định đã biết hay còn gọi là hướng tiếp cận nông. Ví dụ để hỏi về thời gian thì trong câu hỏi sẽ hay xuất hiện các từ như “mấy giờ”, “ngày nào”, “tháng nào”, “năm nào”,…
Còn ý định muốn hỏi về địa điểm thì sẽ có các từ: “ở đâu”, “địa chỉ”, “chỗ nào”,..v.v.
Nhiều phương pháp sử dụng trong Q&A dùng các kĩ thuật dựa trên từ khóa để định vị các câu, đọan văn có khả năng chứa câu trả lời từ các văn bản được trích chọn về. Sau đó giữ lại các câu, đoạn văn có chứa chuỗi ký tự cùng loại với loại câu trả lời mong muốn (ví dụ các câu hỏi về tên người, địa danh, số lượng…).

Khi xác định được các từ hay xuất hiện trong các ý định thì tùy vào xác suất xuất hiện của các từ trong câu hỏi mà chúng ta sẽ dự đoán được khả năng ý định của người dùng sẽ thuộc vào loại nào.
Tuy nhiên việc xác định dựa trên từ điển như vậy sẽ không đầy đủ và thiếu chính xác. Ngôn ngữ tự nhiên là ngôn ngữ có tính nhập nhằng, vì vậy nên một số câu hỏi nếu dựa vào những từ như vậy chưa chắc đã xác định được ý định câu hỏi.

Hướng tiếp cận sâu (deep)

Trong những trường hợp khi mà hướng tiếp cận bề mặt
không thể tìm ra câu trả lời, những quá trình xử lý về ngữ pháp, ngữ nghĩa và ngữ cảnh là cần thiết để trích xuất hoặc tạo ra câu trả lời. Các kĩ thuật thường dùng như nhận dạng thực thể (named-entity recognition), trích xuất mối quan hệ, loại bỏ nhập nhằng ngữ nghĩa,… Hệ thống thường sử dụng các nguồn tri thức như Wordnet, ontology để làm giàu thêm khả năng lập luận thông qua các định nghĩa và mối liên hệ ngữ nghĩa. Các hệ thống hỏi đáp dựa theo mô hình ngôn ngữ thống kê cũng đang ngày càng phổ biến.

Trong bài viết này mình sẽ tiếp cận theo hướng tiếp cận sâu.

Dữ liệu sử dụng

Để xây dựng mô hình xác định ý định câu hỏi, mình sẽ sử dụng ontology là các cặp “câu hỏi – ý định” được thu thập từ sinh viên trường Đại học Xây dựng.
Mình sẽ đưa bài toán về việc xây dựng một mô hình phân lớp với các class là các ý định của người hỏi. Ví dụ sau đây là các câu hỏi trong tập dữ liệu:

Các câu hỏi được chia thành 10 nhóm ý định: ['DIEM', 'HOC_BONG', 'DKMH', 'HOC_PHI', 'KHAC', 'LICH_HOC', 'TAI_KHOAN', 'THU_TUC_SV', 'TN', 'TOEIC']
Trong đó

  • ‘DIEM’ bao gồm các câu hỏi thắc mắc về Điểm
  • ‘HOC_BONG’ bao gồm các câu hỏi thắc mắc về Học bổng
  • ‘DKMH’ bao gồm các câu hỏi thắc mắc về việc đăng ký môn học
  • ‘HOC_PHI’ bao gồm các câu hỏi thắc mắc về học phí

  • ‘KHAC’ bao gồm các câu hỏi không thuộc vào 1 trong 9 nhóm trên

Xây dựng mô hình

Tài nguyên

Dữ liệu, pre-trained các mô hình biểu diễn từ các bạn có thể download ở đây.

Cài đặt các gói cần thiết

Trong bài này mình sử dụng thư viện pyvi để tiến hành một số tiền xử lý với văn bản. Để cài đặt bạn chạy lệnh sau:

Import các thư viện cần thiết

Khai báo các hàm tiền xử lý

Để loại bỏ từ dừng, mình dùng danh sách từ dừng, các bạn thay stopwords.csv bằng đường dẫn trong file mình để bên trên.

Huấn luyện mô hình FastText phù hợp với dữ liệu bài toán

Trong bài này mình sử dụng FastText trong gói thư viện của Gensim để thực hiện mã hóa các từ thành vector (word2vec). Dữ liêu huấn luyện mình để trong file xaa.
FastText được đánh giá là tốt hơn so với word2vec trong việc biểu diễn các từ mới nên mình sẽ sử dụng trong bài toán này.
Đây là file gồm 1 phần các bài viết từ wikipedia tiếng việt, các văn bản đã được tiền xử lý bằng một số
kỹ thuật như tách từ, loại bỏ từ dừng, chuẩn hóa…

Ngoài ra mình cũng cần bổ sung các câu trong file dữ liệu của bộ dữ liệu phân loại ý định để huấn luyện cho mô hình word2vec.
Điều này giúp bổ sung một số từ trong miền dữ liệu của topology mà trong bộ ngữ liệu của wikipedia không có. Điều này giúp mô hình FastText có khả năng biểu diễn đầy đủ hơn.

Huấn luyện mô hình FastText như sau:

Sau khi đã huấn luyện xong các bạn cần lưu lại model để sử dụng cho lần sau bằng đoạn code sau:

Để loại lại mô hình chúng ta làm như sau:

In thử kích thước một từ:

Biểu diễn từ và biểu diễn câu

Sau khi đã huấn luyện mô hình FastText, chúng ta sẽ tiến hành mã hóa các câu thành vector bằng cách mã hóa từng từ trong câu và đưa các vector biểu diễn các từ này vào một vector có kích thước bằng số từ của câu dài nhất (để đảm bảo các câu đều được biểu diễn đầy đủ).
Các câu ngắn hơn độ dài của câu dài nhất sẽ được thêm padding là các số 0 để đưa các câu về cùng kích thước mà không ảnh hưởng đến ý nghĩa của câu. Việc padding mình sử dụng hàm tf.keras.preprocessing.sequence.pad_sequences

Code thực hiện như sau:

Đọc dữ liệu

Phân chia dữ liệu

Vì dữ liệu trong các class là không đều nhau, vì vậy để đánh giá chính xác mô hình ta cần phân chia dữ liệu đánh giá sao cho số lượng các samples trong các class bằng nhau.

Đây là hình ảnh số lượng các câu hỏi trong các class tương ứng:

Số lượng các câu hỏi trong các class

Để phân chia sao cho các câu hỏi trong các class của tập validate như nhau ta thực hiện như sau:

Tiến hành chia dữ liệu huấn luyện và kiểm tra:

Định nghĩa mô hình

Trong bài này mình sử dụng LSTM để tiến hành phân lớp. Mạng LSTM được sử dụng với keras bằng cách khá đơn giản như sau

Xem chi tiết số lượng các tham số mô hình:

Huấn luyện mô hình

Để huấn luyên mô hình chúng ta sẽ fit dữ liệu huấn luyện và kiểm tra như sau:

Tham số verbose=1 để chỉ định in ra kết quả đánh giá sau mỗi lần thực hiện xong 1 epoch

Kết quả sau khi chạy xong 1 số epochs như sau:

Đánh giá mô hình

Import các thư viện cần thiết để đánh giá:

Chúng ta sẽ tiến hành đánh giá mô hình dựa trên các chỉ số như f1_score, độ chính xác (accuracy) như sau:

Các phương pháp đánh giá hệ thống phân lớp các bạn có thể xem tại đây

  • f1-score

Kết quả in ra sẽ được:

  • Độ chính xác

Kết quả:

Như vậy kết quả dự đoán của mô hình trên tập kiểm tra đạt 82.7 %. Kết quả chưa cao lắm nhưng có thể chấp nhận được.

Fine-tune mô hình

Để nâng cao độ chính xác của mô hình, bạn đọc có thể thử nghiệm các thay đổi bằng cách sử dụng mô hình biểu diễn từ tốt hơn hoặc sử dụng mô hình khác như BERT, GRU, RNN…
Ngoài ra chúng ta có thể thử nghiệm thay đổi các tham số để và so sánh các thay đổi để đưa ra được mô hình tốt nhất.

Tổng kết

Bài viết mình đã vừa trình bày về kỹ thuật xác định ý định của câu hỏi sử dụng deeplearning. Mọi thắc mắc và ý kiến đóng góp các bạn có thể trao đổi dưới bài viết này.

Link google colab của bài viết

Bài viết gốc

Cám ơn các bạn đã đọc bài viết.

Chia sẻ bài viết ngay

Nguồn bài viết : Viblo