Hướng dẫn này khám phá tái lấy mẫu chuỗi thời gian trong pandas, bao gồm cả upsampling và downsampling bằng các phương pháp như .asfreq() và .resample().
Thời gian là một chiều cơ bản trong phân tích dữ liệu. Theo thời gian, các giá trị có thể dao động, tạo xu hướng hoặc giữ ổn định. Khi phân tích cách dữ liệu biến đổi theo thời gian, chúng ta đang làm việc với chuỗi thời gian.
Một nhiệm vụ thường gặp trong phân tích chuỗi thời gian là điều chỉnh tần suất của ngày giờ trong dữ liệu, kỹ thuật này được gọi là tái lấy mẫu. Trong hướng dẫn này, chúng ta sẽ tận dụng Pandas, một thư viện có bộ công cụ mạnh mẽ để thao tác chuỗi thời gian trực quan và hiệu quả.
Chúng ta sẽ bắt đầu với những khái niệm cơ bản và dần tiến tới các kỹ thuật tái lấy mẫu nâng cao hơn. Bài viết cung cấp ví dụ thực tế và chia sẻ các thực hành tốt nhất để việc phân tích chuỗi thời gian hiệu quả và tối ưu hiệu năng.
Tương tự như cách chúng ta có thể nhóm dữ liệu theo danh mục, tái lấy mẫu cho phép nhóm dữ liệu vào các khoảng thời gian khác nhau. Điều này hữu ích cho cả làm sạch dữ liệu lẫn phân tích chuỗi thời gian chuyên sâu. Ví dụ, ta có thể cần căn chỉnh hai chuỗi thời gian về cùng một tần suất trước khi so sánh.
Có hai kiểu tái lấy mẫu chính:
Upsampling: Tăng tần suất dữ liệu (ví dụ: từ hàng năm lên hàng tháng). Việc này tạo ra các mốc thời gian mới cần được điền hoặc nội suy.
Downsampling: Giảm tần suất (ví dụ: từ hàng tháng xuống hàng năm). Việc này liên quan đến việc gộp các điểm dữ liệu trong những khoảng thời gian lớn hơn.
Tái lấy mẫu bằng phương thức asfreq() của Pandas
Chúng ta có thể tái lấy mẫu với pandas bằng hai phương thức chính: .asfreq() và .resample().
Để bắt đầu, trước tiên chúng ta cần nhập thư viện pandas với bí danh quen thuộc pd. Chúng ta cũng nhập matplotlib để trực quan hóa kết quả.
import pandas as pd
import matplotlib.pyplot as pltĐược hỗ trợ bởi
Hãy bắt đầu với phương thức .asfreq(). Phương thức này chuyển một chuỗi thời gian về tần suất chỉ định, trả về dữ liệu gốc được căn chỉnh với chỉ mục mới ở tần suất đó.
Chúng ta sẽ làm việc với bộ dữ liệu chứa nhiệt độ hằng ngày ở Madrid từ năm 1997 đến 2015. Hãy bắt đầu với một vài bước tiền xử lý trước khi đi vào tái lấy mẫu.
url ='https://raw.githubusercontent.com/jcanalesluna/courses_materials/master/datasets/Madrid%20Daily%20Weather%201997-2015.csv'
df = pd.read_csv(url, usecols=['CET','Max TemperatureC','Mean TemperatureC','Min TemperatureC'])# Change column names
df.columns =['time','max_temp','mean_temp','min_temp']# Convert string column to datetime
df['time']= pd.to_datetime(df['time'])# Set time column as index
df = df.set_index('time')
dfĐược hỗ trợ bởi
Upsampling với asfreq()
Để minh họa upsampling, giả sử chúng ta muốn chuyển dữ liệu nhiệt độ theo ngày thành theo giờ. Ta có thể thực hiện bằng phương thức .asfreq() với tham số freq='H'.
Bộ dữ liệu thu được lớn hơn đáng kể, vì các hàng mới đã được tạo ở tần suất theo giờ thay vì theo ngày. Mặc định, .asfreq() lấy mục đầu tiên trong chỉ mục gốc và điền các giờ còn lại bằng giá trị null.
Bộ dữ liệu kết quả lớn hơn đáng kể, vì các hàng mới đã được tạo với dữ liệu theo giờ thay vì theo ngày. Theo mặc định, .asfreq() lấy mục đầu tiên trong chỉ mục gốc và tạo giá trị null cho các giờ còn lại.
Pandas cung cấp ba chiến lược để điền các giá trị null này:
Điền tiến (ffill): Lan truyền quan sát hợp lệ gần nhất về phía trước.
Điền lùi (bfill): Dùng quan sát hợp lệ kế tiếp để lấp khoảng trống.
Giá trị điền: Cung cấp một giá trị cụ thể để thay cho dữ liệu thiếu.
Hai chiến lược đầu được triển khai bằng tham số method trong phương thức .asfreq(), trong khi giá trị điền được chỉ định bằng tham số fill_value.
Bây giờ hãy xem downsampling. Giả sử chúng ta muốn đổi tần suất hằng ngày thành hằng tháng. Ta có thể thực hiện bằng .asfreq() với tham số freq='M'.
Trong trường hợp này, chúng ta đang giảm tần suất dữ liệu, chuyển từ theo ngày xuống theo tháng. DataFrame kết quả chỉ có 228 hàng, so với 6.812 hàng ở DataFrame gốc.
Lưu ý rằng .asfreq() chỉ đơn giản chọn ngày cuối cùng của mỗi tháng và dùng giá trị của ngày đó để đại diện cho cả tháng. Không có phép gộp nào được thực hiện (ví dụ: tính nhiệt độ trung bình theo tháng). Để thực hiện các phép gộp như vậy, chúng ta sẽ dùng phương thức .resample() ở phần tiếp theo.
Tái lấy mẫu bằng phương thức resample() của Pandas
Mặc dù .asfreq() hữu ích để hiển thị dữ liệu chuỗi thời gian ở tần suất khác, phương thức .resample() là công cụ ưu tiên khi cần thực hiện các phép gộp đồng thời với tái lấy mẫu.
Phương thức .resample() hoạt động khá giống .groupby(): nó nhóm dữ liệu trong một khoảng thời gian xác định rồi áp dụng một hoặc nhiều hàm cho mỗi nhóm. Kết quả của các hàm này được gán cho một ngày mới trong khoảng đó.
Chúng ta dùng .resample() cho cả upsampling (điền hoặc nội suy dữ liệu thiếu) và downsampling (gộp dữ liệu).
Hãy quay lại ví dụ chuyển đổi theo giờ để xem upsampling hoạt động với .resample() như thế nào. Áp dụng .resample() trả về một đối tượng Resampler, sau đó ta có thể áp dụng phương thức khác để thu được một DataFrame.
Nhưng .resample() cũng cung cấp các phương thức bổ sung mà .asfreq() không có. Chẳng hạn, chúng ta có thể dùng phương thức .interpolate(), ước lượng giá trị tại các mốc thời gian mới bằng cách tìm các điểm trên đường thẳng nối giữa các điểm dữ liệu hiện có.
Phương thức .resample() thực sự phát huy khi downsampling, vì nó cho phép áp dụng nhiều phương pháp gộp để tóm tắt dữ liệu. Ví dụ, hãy tính nhiệt độ trung bình theo tháng và trung vị theo quý ở Madrid bằng .resample().
Ngoài các thao tác cơ bản, các phương thức tái lấy mẫu của Pandas cũng xử lý được những tình huống nâng cao hơn. Hãy cùng khám phá một số trường hợp phổ biến.
Tần suất thời gian tùy chỉnh
Tái lấy mẫu cho phép tạo chuỗi thời gian mới với tần suất phù hợp nhu cầu cụ thể. Một số tần suất thường dùng gồm:
W: Hàng tuần (kết thúc vào Chủ Nhật)
M: Cuối tháng theo lịch
Q: Cuối quý theo lịch
H: Hàng giờ
Tuy nhiên, Pandas cung cấp nhiều lựa chọn khác tùy yêu cầu. Chúng ta có thể xác định tần suất theo ngày đầu hoặc cuối kỳ, dùng ngày làm việc thay vì ngày lịch, thậm chí tạo tần suất hoàn toàn tùy chỉnh.
df.mean_temp.resample('M').mean()# calendar month end
df.mean_temp.resample('MS').mean()# calendar month start
df.mean_temp.resample('BM').mean()# business calendar end
df.mean_temp.resample('BMS').mean()# business calendar startĐược hỗ trợ bởi
Nhiều phép gộp khi downsampling
Tương tự phương thức groupby(), .resample() cho phép áp dụng nhiều phép gộp đồng thời. Chúng ta có thể dùng .agg() và truyền vào danh sách các hàm gộp như mean, median và độ lệch chuẩn.
df.mean_temp.resample('M').agg(['mean','median','std'])Được hỗ trợ bởi
Tái lấy mẫu: Thực hành tốt và lỗi thường gặp
Pandas được tối ưu hóa cao để xử lý tập dữ liệu lớn, nhưng khi kích thước DataFrame tăng, việc xử lý và thao tác có thể trở nên tốn tài nguyên tính toán. Điều này đặc biệt đúng với upsampling. Hãy tưởng tượng tái lấy mẫu chuỗi theo giờ xuống theo giây – DataFrame kết quả có thể khổng lồ!
Nếu gặp vấn đề hiệu năng với tập dữ liệu lớn, bạn có thể áp dụng các chiến lược sau:
Chỉ đọc các cột bạn cần dùng.
Dùng kiểu dữ liệu hiệu quả, tiêu tốn ít bộ nhớ hơn.
Dùng kỹ thuật chia lô (chunking) khi đọc tệp.
May mắn thay, các phiên bản pandas 2.0 trở lên đã tích hợp các kỹ thuật nâng cao để xử lý hiệu quả hơn. Bạn có thể tìm hiểu thêm trong bài viết về Pandas 2.0.
Kết luận
Tái lấy mẫu là một kỹ thuật nền tảng trong phân tích chuỗi thời gian, cho phép điều chỉnh tần suất dữ liệu bằng cách gộp (downsampling) hoặc nội suy (upsampling) các giá trị. Chúng ta đã khám phá cách pandas cung cấp các công cụ mạnh như .asfreq() và .resample() để giúp quy trình này trực quan và hiệu quả.
Để đào sâu hiểu biết về tái lấy mẫu và thao tác chuỗi thời gian trong Python, hãy xem các tài nguyên sau:
Tôi là một chuyên viên phân tích dữ liệu tự do, hợp tác với các công ty và tổ chức trên toàn thế giới trong các dự án khoa học dữ liệu. Tôi cũng là giảng viên khoa học dữ liệu với hơn 2 năm kinh nghiệm. Tôi thường xuyên viết bài về khoa học dữ liệu bằng tiếng Anh và tiếng Tây Ban Nha; một số bài đã được đăng trên các trang uy tín như DataCamp, Towards Data Science và Analytics Vidhya. Là một nhà khoa học dữ liệu có nền tảng khoa học chính trị và luật, mục tiêu của tôi là làm việc tại giao điểm giữa chính sách công, pháp luật và công nghệ, tận dụng sức mạnh của ý tưởng để thúc đẩy các giải pháp và cách tiếp cận mới nhằm giúp chúng ta đối mặt với những thách thức cấp bách, đặc biệt là khủng hoảng khí hậu. Tôi xem mình là người tự học, không ngừng trau dồi và là một người ủng hộ vững chắc cho tính đa ngành. Không bao giờ là quá muộn để học điều mới.
Câu hỏi thường gặp về tái lấy mẫu Pandas
Sự khác nhau giữa rolling và resample trong pandas là gì?⌄
Tái lấy mẫu thay đổi tần suất dữ liệu chuỗi thời gian của bạn, trong khi các phép toán rolling tính toán thống kê trên một cửa sổ trượt có kích thước cố định trong tần suất gốc.
resample('MS') trong Python là gì?⌄
resample('MS') là một tham số cụ thể trong phương thức .resample(). Nó yêu cầu pandas tái lấy mẫu dữ liệu theo tần suất bắt đầu tháng. 'MS' là viết tắt của Month Start (đầu tháng).
Khi nào tôi nên dùng tái lấy mẫu?⌄
Tái lấy mẫu hữu ích cho nhiều tác vụ, bao gồm:
Căn chỉnh nhiều chuỗi thời gian về cùng một tần suất để so sánh.
Gộp dữ liệu về tần suất thấp hơn để phân tích hoặc trực quan hóa (ví dụ: dữ liệu hằng ngày thành trung bình hằng tháng).
Điền các điểm dữ liệu thiếu trong chuỗi thời gian thông qua nội suy (upsampling).
Nhược điểm của tái lấy mẫu là gì?⌄
Upsampling có thể gây sai lệch nếu phương pháp nội suy không được chọn cẩn thận.
Downsampling có thể dẫn đến mất mát thông tin do dữ liệu bị gộp lại.
Tái lấy mẫu trên các tập dữ liệu lớn có thể tốn kém tài nguyên tính toán.
Thời gian là một chiều cơ bản trong phân tích dữ liệu. Theo thời gian, các giá trị có thể dao động, tạo xu hướng hoặc giữ ổn định. Khi phân tích cách dữ liệu biến đổi theo thời gian, chúng ta đang làm việc với chuỗi thời gian.
Một nhiệm vụ thường gặp trong phân tích chuỗi thời gian là điều chỉnh tần suất của ngày giờ trong dữ liệu, kỹ thuật này được gọi là tái lấy mẫu. Trong hướng dẫn này, chúng ta sẽ tận dụng Pandas, một thư viện có bộ công cụ mạnh mẽ để thao tác chuỗi thời gian trực quan và hiệu quả.
Chúng ta sẽ bắt đầu với những khái niệm cơ bản và dần tiến tới các kỹ thuật tái lấy mẫu nâng cao hơn. Bài viết cung cấp ví dụ thực tế và chia sẻ các thực hành tốt nhất để việc phân tích chuỗi thời gian hiệu quả và tối ưu hiệu năng.
Nếu bạn muốn tìm hiểu thêm về chuỗi thời gian, hãy xem khóa học về thao tác dữ liệu chuỗi thời gian trong Python.
Tái lấy mẫu chuỗi thời gian là gì?
Tương tự như cách chúng ta có thể nhóm dữ liệu theo danh mục, tái lấy mẫu cho phép nhóm dữ liệu vào các khoảng thời gian khác nhau. Điều này hữu ích cho cả làm sạch dữ liệu lẫn phân tích chuỗi thời gian chuyên sâu. Ví dụ, ta có thể cần căn chỉnh hai chuỗi thời gian về cùng một tần suất trước khi so sánh.
Có hai kiểu tái lấy mẫu chính:
Tái lấy mẫu bằng phương thức asfreq() của Pandas
Chúng ta có thể tái lấy mẫu với pandas bằng hai phương thức chính:
.asfreq()và.resample().Để bắt đầu, trước tiên chúng ta cần nhập thư viện
pandasvới bí danh quen thuộcpd. Chúng ta cũng nhậpmatplotlibđể trực quan hóa kết quả.Hãy bắt đầu với phương thức
.asfreq(). Phương thức này chuyển một chuỗi thời gian về tần suất chỉ định, trả về dữ liệu gốc được căn chỉnh với chỉ mục mới ở tần suất đó.Chúng ta sẽ làm việc với bộ dữ liệu chứa nhiệt độ hằng ngày ở Madrid từ năm 1997 đến 2015. Hãy bắt đầu với một vài bước tiền xử lý trước khi đi vào tái lấy mẫu.
Upsampling với asfreq()
Để minh họa upsampling, giả sử chúng ta muốn chuyển dữ liệu nhiệt độ theo ngày thành theo giờ. Ta có thể thực hiện bằng phương thức .asfreq() với tham số
freq='H'.Bộ dữ liệu thu được lớn hơn đáng kể, vì các hàng mới đã được tạo ở tần suất theo giờ thay vì theo ngày. Mặc định, .asfreq() lấy mục đầu tiên trong chỉ mục gốc và điền các giờ còn lại bằng giá trị null.
Bộ dữ liệu kết quả lớn hơn đáng kể, vì các hàng mới đã được tạo với dữ liệu theo giờ thay vì theo ngày. Theo mặc định, .asfreq() lấy mục đầu tiên trong chỉ mục gốc và tạo giá trị null cho các giờ còn lại.
Pandas cung cấp ba chiến lược để điền các giá trị null này:
ffill): Lan truyền quan sát hợp lệ gần nhất về phía trước.bfill): Dùng quan sát hợp lệ kế tiếp để lấp khoảng trống.Hai chiến lược đầu được triển khai bằng tham số
methodtrong phương thức.asfreq(), trong khi giá trị điền được chỉ định bằng tham sốfill_value.Downsampling với asfreq()
Bây giờ hãy xem downsampling. Giả sử chúng ta muốn đổi tần suất hằng ngày thành hằng tháng. Ta có thể thực hiện bằng .asfreq() với tham số
freq='M'.Trong trường hợp này, chúng ta đang giảm tần suất dữ liệu, chuyển từ theo ngày xuống theo tháng. DataFrame kết quả chỉ có 228 hàng, so với 6.812 hàng ở DataFrame gốc.
Lưu ý rằng
.asfreq()chỉ đơn giản chọn ngày cuối cùng của mỗi tháng và dùng giá trị của ngày đó để đại diện cho cả tháng. Không có phép gộp nào được thực hiện (ví dụ: tính nhiệt độ trung bình theo tháng). Để thực hiện các phép gộp như vậy, chúng ta sẽ dùng phương thức.resample()ở phần tiếp theo.Tái lấy mẫu bằng phương thức resample() của Pandas
Mặc dù
.asfreq()hữu ích để hiển thị dữ liệu chuỗi thời gian ở tần suất khác, phương thức.resample()là công cụ ưu tiên khi cần thực hiện các phép gộp đồng thời với tái lấy mẫu.Phương thức
.resample()hoạt động khá giống.groupby(): nó nhóm dữ liệu trong một khoảng thời gian xác định rồi áp dụng một hoặc nhiều hàm cho mỗi nhóm. Kết quả của các hàm này được gán cho một ngày mới trong khoảng đó.Chúng ta dùng
.resample()cho cả upsampling (điền hoặc nội suy dữ liệu thiếu) và downsampling (gộp dữ liệu).Hãy quay lại ví dụ chuyển đổi theo giờ để xem upsampling hoạt động với
.resample()như thế nào. Áp dụng.resample()trả về một đối tượngResampler, sau đó ta có thể áp dụng phương thức khác để thu được mộtDataFrame.Về upsampling, phương thức
.resample()có thể thực hiện các tác vụ tương tự như.asfreq().Chúng ta cũng có thể áp dụng các chiến lược điền và nội suy tương tự như với
.asfreq(). Ví dụ, để dùng điền tiến:Nhưng
.resample()cũng cung cấp các phương thức bổ sung mà.asfreq()không có. Chẳng hạn, chúng ta có thể dùng phương thức.interpolate(), ước lượng giá trị tại các mốc thời gian mới bằng cách tìm các điểm trên đường thẳng nối giữa các điểm dữ liệu hiện có.Phương thức
.resample()thực sự phát huy khi downsampling, vì nó cho phép áp dụng nhiều phương pháp gộp để tóm tắt dữ liệu. Ví dụ, hãy tính nhiệt độ trung bình theo tháng và trung vị theo quý ở Madrid bằng.resample().Kỹ thuật tái lấy mẫu nâng cao
Ngoài các thao tác cơ bản, các phương thức tái lấy mẫu của Pandas cũng xử lý được những tình huống nâng cao hơn. Hãy cùng khám phá một số trường hợp phổ biến.
Tần suất thời gian tùy chỉnh
Tái lấy mẫu cho phép tạo chuỗi thời gian mới với tần suất phù hợp nhu cầu cụ thể. Một số tần suất thường dùng gồm:
W: Hàng tuần (kết thúc vào Chủ Nhật)M: Cuối tháng theo lịchQ: Cuối quý theo lịchH: Hàng giờTuy nhiên, Pandas cung cấp nhiều lựa chọn khác tùy yêu cầu. Chúng ta có thể xác định tần suất theo ngày đầu hoặc cuối kỳ, dùng ngày làm việc thay vì ngày lịch, thậm chí tạo tần suất hoàn toàn tùy chỉnh.
Nhiều phép gộp khi downsampling
Tương tự phương thức groupby(), .resample() cho phép áp dụng nhiều phép gộp đồng thời. Chúng ta có thể dùng .agg() và truyền vào danh sách các hàm gộp như mean, median và độ lệch chuẩn.
Tái lấy mẫu: Thực hành tốt và lỗi thường gặp
Pandas được tối ưu hóa cao để xử lý tập dữ liệu lớn, nhưng khi kích thước DataFrame tăng, việc xử lý và thao tác có thể trở nên tốn tài nguyên tính toán. Điều này đặc biệt đúng với upsampling. Hãy tưởng tượng tái lấy mẫu chuỗi theo giờ xuống theo giây – DataFrame kết quả có thể khổng lồ!
Nếu gặp vấn đề hiệu năng với tập dữ liệu lớn, bạn có thể áp dụng các chiến lược sau:
May mắn thay, các phiên bản pandas 2.0 trở lên đã tích hợp các kỹ thuật nâng cao để xử lý hiệu quả hơn. Bạn có thể tìm hiểu thêm trong bài viết về Pandas 2.0.
Kết luận
Tái lấy mẫu là một kỹ thuật nền tảng trong phân tích chuỗi thời gian, cho phép điều chỉnh tần suất dữ liệu bằng cách gộp (downsampling) hoặc nội suy (upsampling) các giá trị. Chúng ta đã khám phá cách pandas cung cấp các công cụ mạnh như
.asfreq()và.resample()để giúp quy trình này trực quan và hiệu quả.Để đào sâu hiểu biết về tái lấy mẫu và thao tác chuỗi thời gian trong Python, hãy xem các tài nguyên sau: