遍历 pandas 数据帧
Looping through pandas dataframe
数据框:
date A B C D
index
0 2015-01 .. .. .. ..
1 2015-01 .. .. .. ..
2 2015-02 .. .. .. ..
3 2015-02 .. .. .. ..
4 2015-03 .. .. .. ..
5 2015-03 .. .. .. ..
6 2015-04 .. .. .. ..
7 2015-04 .. .. .. ..
8 2015-05 .. .. .. ..
9 2015-05 .. .. .. ..
...
1000 ... .. .. .. ..
我想使用从固定 window 开始的日期 (pd.to_datetime) 进行迭代(例如,前三个月 [2015-01、2015-01、2015-02、2015-02 , 2015-03, 2015-03]) 和 returning 数据框:
date A B C D
index
0 2015-01 .. .. .. ..
1 2015-01 .. .. .. ..
2 2015-02 .. .. .. ..
3 2015-02 .. .. .. ..
4 2015-03 .. .. .. ..
5 2015-03 .. .. .. ..
然后添加下个月 [2015-04, 2015-04] 并删除最旧的月份 [2015-01, 2015-01],return 下一个数据帧:
date A B C D
index
2 2015-02 .. .. .. ..
3 2015-02 .. .. .. ..
4 2015-03 .. .. .. ..
5 2015-03 .. .. .. ..
6 2015-04 .. .. .. ..
7 2015-04 .. .. .. ..
继续这个直到数据结束。
我想出了以下代码:
periods = len(dataframe)
fxw = 3
for i in range(0, periods):
start = i
if i + fxw > periods:
break
else: end_df = i + fxw
# output:
# df1
date A B C D
index
0 2015-01 .. .. .. ..
1 2015-01 .. .. .. ..
2 2015-02 .. .. .. ..
# df2
date A B C D
index
3 2015-02 .. .. .. ..
4 2015-03 .. .. .. ..
5 2015-03 .. .. .. ..
...
# dfend
我可以设置一个固定的 window (fxw = 3) 以在数据帧的长度上一次迭代 3 行,直到数据结束。 (例如,如果数据框有 12 行,它将 return 4 个数据框,每个数据框有 3 行)。但是,通过这种方式,我既没有按日期选择 window,也没有删除最后一个数据点并添加下一个数据点。我还不知道该怎么做。如果有人有可能 solution/suggestion,将不胜感激!
谢谢!
如果我理解正确,你想遍历数据框并每次获取 4 行的块。您可以尝试这样的操作并根据需要进行调整:
首先按日期对数据框进行排序。为此,您可以使用 sort_values
函数:
df = your_df.sort_values(by='date')
请注意,如果您的日期列的日期时间格式不正确,那么您需要在排序之前执行此操作:
your_df['date'] =pd.to_datetime(your_df.date)
然后你可以使用for循环
for i in range(0, len(df), 4): # the 4 here means return a chunk of 4 rows
chunk = df.iloc[i:i+4, :]
print(chunk)
# do your magic
这是一种方法。从构建数据框开始:
import numpy as np
import pandas as pd
date = [ f'2015-{i:02d}' for i in range(1, 7) ]
date = np.repeat(date, 2)
date = [pd.Period(d) for d in date]
n = len(date)
amt = [10 * i for i in range(n)]
df = pd.DataFrame({'date': date, 'amt': amt})
print(df.head())
接下来,使用数据框中的最小和最大日期构造一个周期范围:
period_range = pd.period_range(start=df['date'].min(),
end=df['date'].max(),
freq='M')
现在,遍历数据框:
months_in_window = 2
for start, end in zip(period_range, period_range[months_in_window - 1: ]):
mask = (start <= df['date']) & (df['date'] <= end)
print(df[mask], end='\n\n')
date amt
0 2015-01 0
1 2015-01 10
2 2015-02 20
3 2015-02 30
date amt
2 2015-02 20
3 2015-02 30
4 2015-03 40
5 2015-03 50
<rest of output omitted to save space>
您可以经常使用 pandas 工具(包括 groupby
和 rolling
)来避免迭代数据框。
更新:
我们可以控制一个 window 的长度,以及从一个 window 开始到下一个开始的时间:
# create list of periods
periods = pd.period_range(start='2020-01-01', periods=24, freq='M')
# create parameters
months_in_window = 3 # start of window i to end of window i
step = 5 # start of window i to start of window i+1
# create start and end points for each window
windows = [
(start, end)
for start, end
in zip(periods[::step], periods[window_size-1::step])
]
for w in windows: print(w)
(Period('2020-01', 'M'), Period('2020-03', 'M'))
(Period('2020-06', 'M'), Period('2020-08', 'M'))
(Period('2020-11', 'M'), Period('2021-01', 'M'))
(Period('2021-04', 'M'), Period('2021-06', 'M'))
(Period('2021-09', 'M'), Period('2021-11', 'M'))
最后,迭代一个数据框看起来像这样(掩码没有变化):
for start, end in windows:
mask = (start <= df['date']) & (df['date'] <= end)
print(df[mask], end='\n\n')
数据框:
date A B C D
index
0 2015-01 .. .. .. ..
1 2015-01 .. .. .. ..
2 2015-02 .. .. .. ..
3 2015-02 .. .. .. ..
4 2015-03 .. .. .. ..
5 2015-03 .. .. .. ..
6 2015-04 .. .. .. ..
7 2015-04 .. .. .. ..
8 2015-05 .. .. .. ..
9 2015-05 .. .. .. ..
...
1000 ... .. .. .. ..
我想使用从固定 window 开始的日期 (pd.to_datetime) 进行迭代(例如,前三个月 [2015-01、2015-01、2015-02、2015-02 , 2015-03, 2015-03]) 和 returning 数据框:
date A B C D
index
0 2015-01 .. .. .. ..
1 2015-01 .. .. .. ..
2 2015-02 .. .. .. ..
3 2015-02 .. .. .. ..
4 2015-03 .. .. .. ..
5 2015-03 .. .. .. ..
然后添加下个月 [2015-04, 2015-04] 并删除最旧的月份 [2015-01, 2015-01],return 下一个数据帧:
date A B C D
index
2 2015-02 .. .. .. ..
3 2015-02 .. .. .. ..
4 2015-03 .. .. .. ..
5 2015-03 .. .. .. ..
6 2015-04 .. .. .. ..
7 2015-04 .. .. .. ..
继续这个直到数据结束。
我想出了以下代码:
periods = len(dataframe)
fxw = 3
for i in range(0, periods):
start = i
if i + fxw > periods:
break
else: end_df = i + fxw
# output:
# df1
date A B C D
index
0 2015-01 .. .. .. ..
1 2015-01 .. .. .. ..
2 2015-02 .. .. .. ..
# df2
date A B C D
index
3 2015-02 .. .. .. ..
4 2015-03 .. .. .. ..
5 2015-03 .. .. .. ..
...
# dfend
我可以设置一个固定的 window (fxw = 3) 以在数据帧的长度上一次迭代 3 行,直到数据结束。 (例如,如果数据框有 12 行,它将 return 4 个数据框,每个数据框有 3 行)。但是,通过这种方式,我既没有按日期选择 window,也没有删除最后一个数据点并添加下一个数据点。我还不知道该怎么做。如果有人有可能 solution/suggestion,将不胜感激! 谢谢!
如果我理解正确,你想遍历数据框并每次获取 4 行的块。您可以尝试这样的操作并根据需要进行调整:
首先按日期对数据框进行排序。为此,您可以使用 sort_values
函数:
df = your_df.sort_values(by='date')
请注意,如果您的日期列的日期时间格式不正确,那么您需要在排序之前执行此操作:
your_df['date'] =pd.to_datetime(your_df.date)
然后你可以使用for循环
for i in range(0, len(df), 4): # the 4 here means return a chunk of 4 rows
chunk = df.iloc[i:i+4, :]
print(chunk)
# do your magic
这是一种方法。从构建数据框开始:
import numpy as np
import pandas as pd
date = [ f'2015-{i:02d}' for i in range(1, 7) ]
date = np.repeat(date, 2)
date = [pd.Period(d) for d in date]
n = len(date)
amt = [10 * i for i in range(n)]
df = pd.DataFrame({'date': date, 'amt': amt})
print(df.head())
接下来,使用数据框中的最小和最大日期构造一个周期范围:
period_range = pd.period_range(start=df['date'].min(),
end=df['date'].max(),
freq='M')
现在,遍历数据框:
months_in_window = 2
for start, end in zip(period_range, period_range[months_in_window - 1: ]):
mask = (start <= df['date']) & (df['date'] <= end)
print(df[mask], end='\n\n')
date amt
0 2015-01 0
1 2015-01 10
2 2015-02 20
3 2015-02 30
date amt
2 2015-02 20
3 2015-02 30
4 2015-03 40
5 2015-03 50
<rest of output omitted to save space>
您可以经常使用 pandas 工具(包括 groupby
和 rolling
)来避免迭代数据框。
更新:
我们可以控制一个 window 的长度,以及从一个 window 开始到下一个开始的时间:
# create list of periods
periods = pd.period_range(start='2020-01-01', periods=24, freq='M')
# create parameters
months_in_window = 3 # start of window i to end of window i
step = 5 # start of window i to start of window i+1
# create start and end points for each window
windows = [
(start, end)
for start, end
in zip(periods[::step], periods[window_size-1::step])
]
for w in windows: print(w)
(Period('2020-01', 'M'), Period('2020-03', 'M'))
(Period('2020-06', 'M'), Period('2020-08', 'M'))
(Period('2020-11', 'M'), Period('2021-01', 'M'))
(Period('2021-04', 'M'), Period('2021-06', 'M'))
(Period('2021-09', 'M'), Period('2021-11', 'M'))
最后,迭代一个数据框看起来像这样(掩码没有变化):
for start, end in windows:
mask = (start <= df['date']) & (df['date'] <= end)
print(df[mask], end='\n\n')