Outliers/anomalies (dữ liệu ngoại lai/dữ liệu bất thường) là một trong những thuật ngữ được sử dụng rất rộng rãi trong thế giới data và đặc biệt là data science. Xác định và loại bỏ outliers là một bước cực kỳ quan trọng trong quá trình xử lý dữ liệu. Việc xử lý các dữ liệu ngoại lai sẽ giúp tăng cao độ chính xác cho các mô hình dự đoán hay các báo cáo doanh nghiệp một cách đáng kể.
Trong bài này chúng ta sẽ cùng tìm hiểu các vấn đề sau:
- Outliers thực chất là gì?
- Tầm quan trọng của việc xác định và loại bỏ outliers?
- Cùng so sánh và phân tích kết quả của trước và sau khi loại bỏ outliers
- Phương pháp và các bước thực hiện loại bỏ Outliers
- Thực hành xử lý Outliers bằng MySQL
- Cuối cùng là câu hỏi cho bạn thực hành
Lưu ý: Bài viết sẽ không đi nghiên cứu quá sâu về Outliers. Bài này chỉ dừng lại ở mức cơ bản để các bạn có thể đọc, hiểu và thực hành ngay.
Outliers (dữ liệu ngoại lai) là gì?
Để hiểu được bản chất thực sự của outliers là gì, các bạn có trước tiên tham khảo các hình bên dưới. Chú ý sự khác nhau giữa điểm màu đỏ với các điểm còn lại.
Qua các bức ảnh trên, chắc các bạn cũng thấy được điểm chung của các outliers. Hiểu đơn giản thì Outliers là một hoặc nhiều cá thể khác hẳn đối với các thành viên còn lại của nhóm. Sự khác biệt này có thể dựa trên nhiều tiêu chí khác nhau như giá trị hay thuộc tính.
Đối với 2 hình trên, chúng ta có thể dễ dàng xác định các outliers dựa trên giá trị của chúng vì những giá trị này khác xa với các giá trị còn lại của nhóm.
Ví dụ: trong một lớp học gồm 100 học sinh, phần lớn học sinh đều đạt kết quả dao động từ 5 đến 7 riêng chỉ có 1 bạn đạt điểm 1 và một bạn đạt điểm 10. Trong trường hợp này, 2 bạn có điểm 1 và 10 có thể được xem là 2 Outliers cho bài kiểm tra đó.
Trong trường hợp khác thì các outliers là những thành phần có thuộc tính hoặc tính cách khác với số còn lại.
Ví dụ: một công ty với mô hình B2B có rất nhiều khách hàng khác nhau nhưng trong những khách hàng này có một doanh nghiệp đến từ nước ngoài. Doanh nghiệp nước ngoài này có thể được xem là một outliers khi xét về tính chất khách hàng. Vì họ có thể có những hành vi mua hàng rất khác với khách hàng nội địa.
Trên thực tế, người ta chia outliers ra khá nhiều loại khác nhau. Nhưng ở đây mình chỉ muốn các bạn hiểu được bản chất của outliers và cách xác định những loại outliers đơn giản. Vậy nên mình gộp chung lại thành 2 dạng như trên.
Nếu muốn tìm hiểu xâu hơn về Outliers, các bạn có thể Google về nó. Có khá nhiều tài liệu cả tiếng Anh lẫn tiếng Việt giải thích về thuật ngữ này. Mình sẽ không phân tích sâu thêm nữa về định nghĩa cũng như phân loại.
Khi nào cần xác định và loại bỏ outliers
Trên thực tế, khi chúng ta làm báo cáo hay xây dựng model, sẽ rất khó để đạt giá trị tuyệt đối. Trong hầu hết các trường hợp, dữ liệu xấu hoặc bất thường sẽ luôn tồn tại. Những dữ liệu này tồn tại do khá nhiều nguyên nhân khác nhau tùy vào hoàn cảnh và mô hình kinh doanh.
Một vài ví dụ cụ thể như:
- Lỗi phát sinh trong quá trình nhập và chỉnh sửa dữ liệu như dư hay thiếu vài số 0 hay sai địa chỉ. Lỗi này mình thấy cực kỳ phổ biến.
- Đối với các mô hình online, người ta có thể cố ý tạo ra giá trị ảo để test thị trường hoặc làm mồi nhử. Ví dụ một căn nhà có thể được ra bán với giá 100,000 đồng hay 999 tỷ. Nếu bạn tính trung bình giá nhà tại khu vực tính luôn cả nhà phía trên, đảm bảo giá nhà sẽ cao ngất ngưởng so với thực tế.
- Khi muốn biết tổng giá trị sản phẩm bán ra trong ngày của một cửa hàng, chúng ta phát hiện có một vài ngày, con số này cao một cách đột biến so với các ngày còn lại. Nguyên nhân là do gần đó có một sự kiện cộng đồng kiến khách hàng đột ngột tăng lên.
Chúng ta có thể thấy được với 2 ví dụ (1) và (2) thì những dữ liệu xấu này cần được loại bỏ để tăng tính chính xác cho các model hoặc báo cáo. Nhưng với trường hợp thứ (3), các outliers này lại có thể cho chúng ta thấy được một tiềm năng doanh thu mới. Nếu chúng ta tìm hiểu nguyên nhân tại sao lại có sale tăng đột biến và chuẩn bị cho kỳ tiếp theo, khả năng là sẽ có thêm được nhiều lợi nhuận.
Vậy nên việc xác định Outliers là cần thiết trong phần lớn các trường hợp. Nhưng việc xử lý chúng như thế nào thì còn tùy thuộc vào từng hoàn cảnh. Chúng ta cần tìm hiểu sâu hơn nguyên nhân gây ra các Outliers trước khi quyết định loại bỏ hay giữ lại những outliers này.
Phương pháp xác định Outliers
Vì bản chất của outliers có khá nhiều loại khác nhau nên cũng sẽ có nhiều phương pháp khác nhau để xác định outliers. Trong bài viết này chúng ta sẽ chỉ tập trung vào một loại outliers là những data point có giá trị quá cao hoặc quá thấp so với phần lớn dữ liệu.
Chúng ta sẽ sử dụng bộ dữ liệu là SuperStore Sales và tìm outliers dựa trên tổng giá trị của mỗi hóa đơn tại mỗi state. Với câu hỏi này, dữ liệu mà chúng ta cần xử lý chỉ có một chiều (xem lại hình 2). Bạn nào chưa có dữ liệu SupperStore thì xem hướng dẫn tại đây.
Kết hợp với loại outliers, mình sẽ sử dụng phương pháp Extreme Value Analysis. Phương pháp này đơn giản là xác định các data points có giá trị cực cao/thấp (extreme value). Các giá trị extreme sẽ được xác định bằng khoảng cách của chúng so với giá trị trung bình (Average/Mean). Toàn bộ các giá trị Extreme đều được xác định là outliers.
Lưu ý: trên thực tế, các giá trị outliers có khả năng không phải là giá trị Extreme. Đặc biệt là đối với các mảng dữ liệu nhiều hơn 1 chiều.
Bạn nào tò mò các phương pháp khác thì có thể vào hỏi Google hoặc xem tại blog này
Okay, trước khi đi vào hướng dẫn các tìm và loại bỏ outliers, các bạn cùng xem một báo cáo mẫu do mình thiết kế trên Tableau để có thể hình dung ra được các Outliers là như thế nào.
Báo cáo mẫu về loại bỏ Outlier trên Tableau
Sử dụng báo cáo này như thế nào:
- Các bạn có thể rê chuột trên các giá trị để có thể thấy được những giá trị outliers.
- So sánh sự khác nhau giữa giá trị trung bình mỗi hóa đơn trước và sau khi loại bỏ Outliers.
- Điều chỉnh giá trị phía trên góc phải để thấy được sự thay đổi của Outliers. Các bạn sẽ hiểu những biến này ở phần sau của bài viết.
- Comment phía dưới xem bạn đã tìm được insight gì hay từ report này?
- Đổi chế độ điện thoại sang ngang (landscape) nếu không thấy rõ số liệu
- Boxplot trong hình chỉ để mục đích so sánh vì cách tính khác nhau
Các bạn có thể tải Workbook này xuống để tham khảo cách làm. Nếu có nhiều yêu cầu mình sẽ làm bài mới hướng dẫn từng bước cách làm một cái tương tự như vậy.
Okay giờ mình vào phần tiếp theo xem cách thức xác định Outliers nhé
Các bước cần thực hiện để xác định Outliers
Như mình đã nói phía trên, trong bài này chúng ta sẽ xác định outliers là những order có giá trị cao hoặc thấp hơn bất thường so với những orders còn lại trong nhóm. Để làm điều này chúng ta thực hiện những bước sau. Tùy theo từng môi trường chúng ta sẽ có cách khác nhau để thực hiện từng bước, nhưng cơ bản chúng ta sẽ đều trải qua những bước này.
Bước 0: Visualise/plot your data
Phác họa dữ liệu lên. Đây là cách nhanh nhất để phát hiện xem dữ liệu của bạn có xuất hiện Outliers hay không (dashboard phía trên chính là ví dụ). Nếu như dữ liệu của bạn hoàn toàn bình thường thì bạn không cần phải thêm gì nữa. Nếu có dấu hiệu bất thường thì tiếp tục nhé.
Bước 1: Tìm tổng giá trị của mỗi order. Các bạn có thể thay đổi giá trị cần tính tùy thuộc vào dataset mà các bạn làm việc. Ví dụ như số lượng khách hàng mới hay số lượng hợp đồng được ký trong ngày,…
Bước 2: Tính Average & Standard Deviation
Tính giá trị trung bình (Average/Mean) và độ lệch chuẩn (Standard Deviation) của tổng giá trị order theo từng Sub-Category. Việc tính 2 giá trị này sẽ cho chúng ta giá trị trung tâm (Average) và từ giá trị trung tâm chúng ta sẽ kiểm tra xem độ phân tán của dữ liệu như thế nào dựa trên giá trị của độ lệch chuẩn (Standard Deviation).
Với bộ dữ liệu có độ phân tán bình thường thì với 3 Standard Deviation (STD), chúng ta sẽ bao phủ được khoảng >99% của dữ liệu. Vậy nên những dữ liệu nằm ngoài 3 STD thường sẽ là Outliers.
Các bạn xem thêm về Standard Deviation ở đây nhé
Bước 3: Tính giá trị biên Upper/Lower whisker
Upper/lower whisker là 2 giá trị cực đại/tiểu nhằm giúp chúng ta xác định dữ liệu chuẩn (expected) và giá ngoại lai (outliers). Giá trị biên phía ngọn (upper whisker) và gốc (lower whisker) theo công thức sau:
Upper_whisker = AVG + STDV*Steps
Lower_whisker = AVG – STDV*Steps
Steps: ở đây là một dãy số tự nhiên chúng ta tự đặt ra tùy theo độ phân tán của dữ liệu. Trong phần lớn trường hợp, Steps = 3 (tương đương 3 Standard deviations) sẽ bao phủ tầm trên 90% tổng số dữ liệu. Các bạn có thể bắt đầu với Step = 3 trong phần lớn trường hợp.
Bước 4: Xác định outliers dựa trên giá trị biên
Việc này khá đơn giản, chúng ta chỉ cần thực hiện so sánh giá trị của Order với Upper whisker và Lower whisker. Nếu giá trị của Order nằm bên trong đoạn từ Upper đến lower thì sẽ là expected data, còn ngoài ra sẽ là outliers. Mình có công thức sau:
If Sum_sale > Upper_whisker or Sum_sale < Lower_whiske
then ‘Outlier’ else ‘Expected’
Như xác định phía trên là mọi giá trị nằm ngoài vùng biên đều là outliers.
Bước 5: Thực hiện tính toán khi đã loại bỏ Outliers
Bây giờ chúng ta đã biết được những order nào là Outliers. Bước tiếp theo đơn giản là thực hiện các phép tính cần thiết với điều kiện để loại outliers.
Ở đây mình sẽ thực hiện lại việc tính giá trị trung bình của mỗi hóa đơn tại mỗi State.
Bước 6: Kiểm tra và điều chỉnh giá trị Step
Sau khi đã có được kết quả mới, chúng ta thực hiện việc so sánh với kết quả trước đó xem sự khác nhau như thế nào. Lúc này chúng ta cũng cần quan tâm đến một giá trị khác nữa là số lượng dữ liệu mà chúng ta còn lại sau khi loại bỏ Outliers.
Việc này cực kỳ quan trọng cho kết quả cuối cùng. Tùy thuộc vào mục đích sử dụng mà chúng ta chọn giá trị khác nhau.
Lúc này các bạn thực hiện tính tổng số lượng data (order) còn lại so với dữ liệu gốc là bao nhiêu. Với số lượng dữ liệu như vậy đã đủ chưa hay quá nhiều?
Nếu muốn tăng số lượng dữ liệu thì chúng ta tăng giá trị của steps lên và ngược lại. Mình khuyến khích là mỗi lần nên tăng/giảm đi 0.5. Sau đó chúng ta quay lại bước 3 và lặp lại cho đến khi có bạn cảm thấy hài lòng.
Hướng dẫn xác định và loại bỏ outliers bằng SQL
Bây giờ các bạn đọc đoạn mã phía dưới nhé. Lưu ý, trong phần mình mình sử dụng SQL CTE (lệnh with). Bạn nào chưa hiểu về lệnh này thì đọc bài trước của mình tại link này nhé.
– Bước 0: mình đã làm với Tableau dashboard phía – trên rồi nên mình không quan tâm ở đây – Bước 1: Tổng giá trị mỗi order with sales_per_order as ( select Order_ID , state , sum(Sales) as total_order_sales from superstore.orders group by Order_ID, state ) – Bước 2: Tính avg và standard deviation – dựa trên total_order_sales và State , avg_std as ( select state ,sum(total_order_sales) as sum_sales ,count(*) as number_of_orders ,avg(total_order_sales) as avg_sales ,std(total_order_sales) as std_sales from sales_per_order group by state ) – Bước 3: tính Upper whisker và Lower whisker mỗi state – upper_whisker = avg + std*steps – lower_whisker = avg – std*steps – ở đây mình mặc đinh steps = 3 , upper_lower_whisker as ( select state , std_sales , avg_sales , number_of_orders , (avg_sales + std_sales*3) as upper_whisker – chúng ta đang kiểm tra giá trị của mỗi order – nên những giá trị <0 đều sẽ là lỗi , case when (avg_sales – std_sales*3) < 0 then 0 else (avg_sales – std_sales*3) end as lower_whisker from avg_std ) – Bước 4: xác định order là outliers – So sánh total_order_sales với upper và lower , find_outliers as ( select spo.Order_ID , spo.state , spo.total_order_sales , ulh.number_of_orders , ulh.std_sales , ulh.avg_sales , ulh.upper_whisker , ulh.lower_whisker , case when spo.total_order_sales > ulh.upper_whisker or spo.total_order_sales < ulh.lower_whisker then ‘Outlier’ else ‘Expected’ end as Outlier_status from sales_per_order as spo left join upper_lower_whisker as ulh on ulh.state = spo.state ) – Bước 5: Tính lại giá trị trung bình của mỗi order – sau khi loại bỏ các outliers (chỉ giữ lại Expected) select state – toàn bộ order của state , number_of_orders , std_sales , upper_whisker , lower_whisker , avg_sales , avg(total_order_sales) as avg_sales_no_outliers – số order sau khi đã loại bỏ outliers , count(*) as new_number_of_orders – tỉ lệ phần trăm dữ liệu còn lại , count(*)/number_of_orders*100 as remaining_data from find_outliers where outlier_status = ‘Expected’ group by state,number_of_orders – ở đây mình thấy với Step=3 mình đã có được phần lớn dữ liệu (>95%) – cộng với việc khi visualise mình thấy đã xác loại được khá nhiều outliers – vậy nên mình không thay đổi step nữa
Sau khi chạy đoạn code trên các bạn sẽ thấy được rất nhiều tiểu ban có giá trị trung bình mỗi hóa đơn giảm hơn rất nhiều so với bạn đầu.
Nếu đã có kết quả các bạn có thể quay trở lại Dashboard phía trên để kiểm tra và so sánh cũng như kiểm xem những outliers đã bị loại bỏ là những order nào.
Tổng kết và thực hành
Bài này chúng ta đã cùng nhau làm quen với khái niệm, có thể mới với một số bạn, là Outliers. Cùng với đó là những lợi ích cũng như cách để xác định và loại bỏ những Outliers không mong muốn.
Mình đã cho demo thử cách xác định outliers và loại bỏ chúng dựa trên tổng giá trị của một Order và State. Bây giờ các bạn có thể thực hành cùng với dataset đó nhưng sử dụng câu hỏi sau:
“Tính trung bình tổng giá trị mỗi order của mỗi tháng trong năm.”
Bạn nào chưa hiểu chỗ nào có thể comment phía dưới. Mình sẽ cố gắng giải đáp nếu có thể. Bookmark lại để quay lại khi cần nhé.
Đừng quên chia sẻ nếu thấy hữu ích nhé.
Bài viết thuộc quyền sở hữu của Data-fun.com