Pandas Dataframe - Giảm một số giờ trong ngày từ 20 năm dữ liệu lịch sử


8

Tôi có dữ liệu thị trường chứng khoán cho một bảo mật duy nhất trong 20 năm trở lại đây. Dữ liệu hiện đang ở trong DataFrame Pandas, theo định dạng sau:

nhập mô tả hình ảnh ở đây

Vấn đề là, tôi không muốn bất kỳ dữ liệu giao dịch "sau giờ" nào trong DataFrame của mình. Thị trường trong câu hỏi mở cửa từ 9:30 sáng đến 4:00 (09:30 đến 16:00 mỗi ngày giao dịch). Tôi muốn bỏ tất cả các hàng dữ liệu không nằm trong khung thời gian này.

Bản năng của tôi là sử dụng mặt nạ Pandas, mà tôi biết cách làm nếu tôi muốn một số giờ nhất định trong một ngày:

mask = (df['date'] > '2015-07-06 09:30:0') & (df['date'] <= '2015-07-06 16:00:0')
sub = df.loc[mask]

Tuy nhiên, tôi không biết làm thế nào để sử dụng một dữ liệu trên cơ sở quay vòng để xóa dữ liệu trong một số thời điểm nhất định trong ngày trong khoảng thời gian 20 năm.


kiểu dữ liệu của cột là gì date. Bạn có thể chạy lệnh này print(df['date'].map(type)) và gửi đầu ra của nó cho câu hỏi?
Andy L.

Câu trả lời:


8

Vấn đề ở đây là làm thế nào bạn đang nhập dữ liệu. Không có chỉ số cho dù 04:00 là sáng hay chiều? nhưng dựa trên ý kiến ​​của bạn, chúng tôi cần cho rằng đó là PM. Tuy nhiên đầu vào đang hiển thị nó là AM.

Để giải quyết điều này, chúng ta cần bao gồm hai điều kiện với mệnh đề OR.

  1. 9: 30-11: 59
  2. 0: 00-4: 00

Đầu vào:

df = pd.DataFrame({'date':   {880551: '2015-07-06 04:00:00', 880552: '2015-07-06 04:02:00',880553: '2015-07-06 04:03:00', 880554: '2015-07-06 04:04:00', 880555: '2015-07-06 04:05:00'},
                   'open':   {880551: 125.00, 880552: 125.36,880553: 125.34, 880554: 125.08, 880555: 125.12},
                   'high':   {880551: 125.00, 880552: 125.36,880553: 125.34, 880554: 125.11, 880555: 125.12},
                   'low':    {880551: 125.00, 880552: 125.32,880553: 125.21, 880554: 125.05, 880555: 125.12},
                   'close':  {880551: 125.00, 880552: 125.32,880553: 125.21, 880554: 125.05, 880555: 125.12},
                   'volume': {880551: 141, 880552: 200,880553: 750, 880554: 17451, 880555: 1000},
                   },
                   )


df.head()

    date    open    high    low close   volume
880551  2015-07-06 04:00:00 125.00  125.00  125.00  125.00  141
880552  2015-07-06 04:02:00 125.36  125.36  125.32  125.32  200
880553  2015-07-06 04:03:00 125.34  125.34  125.21  125.21  750
880554  2015-07-06 04:04:00 125.08  125.11  125.05  125.05  17451
880555  2015-07-06 04:05:00 125.12  125.12  125.12  125.12  1000

from datetime import time

start_first = time(9, 30)
end_first = time(11, 59)
start_second = time(0, 00)
end_second = time(4,00)
df['date'] = pd.to_datetime(df['date'])
df= df[(df['date'].dt.time.between(start_first, end_first)) | (df['date'].dt.time.between(start_second, end_second))]
df
date    open    high    low close   volume
880551  2015-07-06 04:00:00 125.0   125.0   125.0   125.0   141

Ở trên không phải là thực hành tốt, và tôi không khuyến khích sử dụng loại dữ liệu mơ hồ này. giải pháp thời gian dài là điền dữ liệu chính xác với am / pm.

Chúng tôi có thể đạt được nó theo hai cách trong trường hợp định dạng dữ liệu chính xác:

1) sử dụng datetime

from datetime import time

start = time(9, 30)
end = time(16)
df['date'] = pd.to_datetime(df['date'])
df= df[df['date'].dt.time.between(start, end)]

2) sử dụng giữa thời gian, chỉ hoạt động với chỉ số datetime

df['date'] = pd.to_datetime(df['date'])

df = (df.set_index('date')
          .between_time('09:30', '16:00')
          .reset_index())

Nếu bạn vẫn gặp phải lỗi, hãy chỉnh sửa câu hỏi của bạn theo cách tiếp cận từng dòng và lỗi chính xác.


Điều đó dẫn đến lỗi sauTypeError: Index must be DatetimeIndex
HMLDude

đã chỉnh sửa câu trả lời của tôi, df ['date'] = pd.to_datetime (df ['date'])
Bhavesh Ghodasara

Từ bài viết SO này , có vẻ như between_timeyêu cầu khung dữ liệu là chỉ số datetime. OP có thể thử ở cấp DataFrame : day_df = df.set_index('date').between_time('9:30', '16:00').
Parfait

BhaveshGhodasara Tôi đã thử những gì bạn đề xuất trong các chỉnh sửa mới nhất của bạn và kết quả là như nhau TypeError: Index must be DatetimeIndex.
HMLDude

@Parfait Tôi cũng đã thử đề xuất của bạn và một lần nữa thông báo lỗi là : TypeError: Index must be DatetimeIndex.
HMLDude

3

Tôi nghĩ rằng câu trả lời đã có trong các bình luận (@ Parfait's .b between_time ) nhưng nó đã bị mất trong các vấn đề gỡ lỗi. Nó xuất hiện df['date']cột của bạn chưa có loại Datetime.

Điều này là đủ để khắc phục điều đó và nhận được kết quả cần thiết:

df['date'] = pd.to_datetime(df['date'])
df = df.set_index('date')
df = df.between_time('9:30', '16:00')

0

Mã ví dụ này hợp nhất các câu trả lời được cung cấp bởi Bhavesh Ghodasara, Parfait và jorijnsmit thành một ví dụ hoàn chỉnh, nhận xét:

import pandas as pd

# example dataframe containing 6 records: 2 days of 3 records each in which all cases are covered:
# each day has one record before trading hours, one record during trading hours and one recrod after trading hours
df = pd.DataFrame({'date':   {0: '2015-07-06 08:00:00', 1: '2015-07-06 13:00:00', 2: '2015-07-06 18:00:00', 
                              3: '2015-07-07 08:00:00', 4: '2015-07-07 13:00:00', 5: '2015-07-07 18:00:00'},
                   'open':   {0: 125.00, 1: 125.36, 2: 125.34, 3: 125.08, 4: 125.12, 5: 125.37},
                   'high':   {0: 125.00, 1: 125.36, 2: 125.34, 3: 125.08, 4: 125.12, 5: 125.37},
                   'low':    {0: 125.00, 1: 125.36, 2: 125.34, 3: 125.08, 4: 125.12, 5: 125.37},
                   'close':  {0: 125.00, 1: 125.36, 2: 125.34, 3: 125.08, 4: 125.12, 5: 125.37},
                   'volume': {0: 141, 1: 200, 2: 750, 3: 17451, 4: 1000, 5: 38234},
                   },
                   )

# inspect the example data set
df.head(6)

# first, ensure that the 'date' column is of the correct data type: MAKE IT SO!
df['date'] = pd.to_datetime(df['date'])

# inspect the data types: date column should be of type 'datetime64[ns]'
print(df.dtypes)

# set the index of the dataframe to the datetime-type column 'data'
df = df.set_index('date')

# inspect the index: it should be a DatetimeIndex of dtype 'datetime64[ns]'
print(df.index)

# filter the data set
df_filtered = df.between_time('9:30', '16:00')

# inspect the filtered data set: Voilà! No more outside trading hours records.
df_filtered.head()
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.