Thông báo: Download 4 khóa học Python từ cơ bản đến nâng cao tại đây.
KNN (K Nearest Neighbors) trong Python
Trong bài hướng dẫn này, mình sẽ triển khai thuật toán K Nearest Neighbors (KNN) bằng cách chỉ sử dụng các module có sẵn của Python và thư viện numpy. Đồng thời, bạn cũng sẽ hiểu về khái niệm và toán học đằng sau thuật toán ML phổ biến này.

KNN là gì?
.jpg)
K Nearest Neighbors là một thuật toán học máy đơn giản nhưng mạnh mẽ. Thuật toán này dựa trên nguyên lý "láng giềng gần nhất" để dự đoán nhãn của một điểm dữ liệu dựa vào những dữ liệu lân cận gần nhất trong tập huấn luyện.
KNN thuộc nhóm thuật toán không tham số, tức là không giả định bất kỳ mô hình nào cho tập dữ liệu. Nó rất hữu ích trong cả bài toán phân loại và hồi quy.
Ý tưởng cốt lõi của KNN
- Tính toán khoảng cách giữa điểm cần dự đoán với tất cả các điểm trong tập dữ liệu huấn luyện (thường dùng khoảng cách Euclid).
 - Xác định k láng giềng gần nhất (những điểm dữ liệu có khoảng cách ngắn nhất).
 - Dựa vào nhãn của các láng giềng gần nhất, chọn ra nhãn phổ biến nhất (trong phân loại) hoặc trung bình (trong hồi quy).
 
Triển khai thuật toán KNN từ đầu trong Python
Dưới đây là mã Python để triển khai thuật toán KNN:
Bài viết này được đăng tại [free tuts .net]
Code đầy đủ:
import numpy as np
from collections import Counter  # Thư viện để đếm tần suất các phần tử
# Hàm tính khoảng cách Euclid
def euclidean_distance(x1, x2):
    return np.sqrt(np.sum((x1 - x2) ** 2))  # Công thức khoảng cách Euclid
# Lớp KNN
class KNN:
    def __init__(self, k=3):  # Giá trị k: số láng giềng gần nhất
        self.k = k
    def fit(self, X, y):
        """Lưu lại tập huấn luyện và nhãn tương ứng"""
        self.X_train = X  # Tập dữ liệu huấn luyện
        self.y_train = y  # Nhãn của tập dữ liệu
    def predict(self, X):
        """Dự đoán nhãn cho tập dữ liệu mới"""
        y_pred = [self._predict(x) for x in X]  # Duyệt qua từng điểm để dự đoán
        return np.array(y_pred)  # Trả về mảng kết quả
    def _predict(self, x):
        """Dự đoán nhãn cho một điểm dữ liệu"""
        # Tính khoảng cách giữa điểm x và tất cả điểm trong tập huấn luyện
        distances = [euclidean_distance(x, x_train) for x_train in self.X_train]
        # Lấy chỉ số của k láng giềng gần nhất
        k_idx = np.argsort(distances)[:self.k]  # argsort sắp xếp chỉ số theo giá trị
        # Lấy nhãn của k láng giềng gần nhất
        k_neighbor_labels = [self.y_train[i] for i in k_idx]
        # Đếm nhãn xuất hiện nhiều nhất và trả về nhãn đó
        most_common = Counter(k_neighbor_labels).most_common(1)  # Trả về nhãn phổ biến nhất
        return most_common[0][0]
Giải thích mã:
euclidean_distance: Hàm này tính khoảng cách Euclid giữa hai điểm  và  bằng công thức:
Lớp KNN:
__init__(self, k=3): Xác định số láng giềng gần nhất .fit(self, X, y): Lưu lại tập huấn luyện và nhãn để sử dụng trong dự đoán.predict(self, X): Áp dụng hàm_predictcho từng điểm trong tập dữ liệu mới để trả về dự đoán._predict(self, x):- Tính toán khoảng cách từ điểm cần dự đoán đến tất cả các điểm trong tập dữ liệu huấn luyện.
 - Chọn  điểm gần nhất bằng cách sử dụng 
np.argsort. - Đếm nhãn xuất hiện nhiều nhất trong  điểm gần nhất với 
Counter.most_common(1). 
Ưu điểm và hạn chế của KNN trong Python
Ưu điểm:
- Đơn giản để hiểu và triển khai.
 - Hiệu quả với dữ liệu nhỏ hoặc dữ liệu có không gian đặc trưng ít.
 
Hạn chế:
- Hiệu suất chậm khi dữ liệu quá lớn do cần tính khoảng cách cho toàn bộ tập huấn luyện.
 - Nhạy cảm với giá trị : Việc chọn sai giá trị có thể dẫn đến dự đoán sai.
 
Kết bài
KNN là thuật toán học máy mạnh mẽ, dễ triển khai và lý tưởng cho các bài toán phân loại hoặc hồi quy đơn giản. Tuy nhiên, khi làm việc với các tập dữ liệu lớn hơn hoặc nhiều đặc trưng hơn, bạn nên cân nhắc sử dụng các thuật toán khác như SVM hoặc Random Forest để cải thiện hiệu suất.
Chúc bạn học vui!

            Các kiểu dữ liệu trong C ( int - float - double - char ...)        
            Thuật toán tìm ước chung lớn nhất trong C/C++        
            Cấu trúc lệnh switch case trong C++ (có bài tập thực hành)        
            ComboBox - ListBox trong lập trình C# winforms        
            Random trong Python: Tạo số random ngẫu nhiên        
            Lệnh cin và cout trong C++        
                Cách khai báo biến trong PHP, các loại biến thường gặp            
                Download và cài đặt Vertrigo Server            
                Thẻ li trong HTML            
                Thẻ article trong HTML5            
                Cấu trúc HTML5: Cách tạo template HTML5 đầu tiên            
                Cách dùng thẻ img trong HTML và các thuộc tính của img            
                Thẻ a trong HTML và các thuộc tính của thẻ a thường dùng