这个问题已经用R解决了,但是我还没有看到关于Python的有用示例。我想学习如何将日历年(1990年1月1日到2010年12月31日)的排放数据转换为水年数据(即从1990年1月1日到2010年9月31日)。谢谢您的协助。
答案 0 :(得分:0)
您可以使用apply并编写自己的函数来创建新列WY
:
如果您有df
:
Date Discharge
0 2011-10-01 00:00:00 0.0
1 2011-10-01 01:00:00 0.0
2 2011-10-01 02:00:00 0.0
3 2011-10-01 03:00:00 0.0
4 2011-10-01 04:00:00 0.0
然后:
import pandas as pd
def assign_wy(row):
if row.Date.month>=10:
return(pd.datetime(row.Date.year+1,1,1).year)
else:
return(pd.datetime(row.Date.year,1,1).year)
df['WY'] = df.apply(lambda x: assign_wy(x), axis=1)
答案 1 :(得分:0)
使用来自USGS 03335500 WABASH RIVER AT LAFAYETTE, IN的数据
必须在 for element in coordonnees_voisine:
element_voisin = self.obtenir_case(element[0], element[1])
if element_voisin == case:
case.ajouter_une_mine_voisine()
else:
None
列中将'datetime'
datetime
设置为dtype
,或在导入数据后使用parse_dates
将其设置为pd.to_datetime()
使用pandas.Series.where
确定水年。
.dt
accessor提取month
和year
数字。.dt.year
,否则,水年为.dt.year + 1
.apply
行,282757
函数快13倍。import pandas as pd
# Load the data
df = pd.read_csv('WabashRiver_Flow.csv', parse_dates=['datetime'])
# drop na values
df = df.dropna()
# determine the water year
df['water_year'] = df.datetime.dt.year.where(df.datetime.dt.month < 10, df.datetime.dt.year + 1)
# display(df.head())
agency_cd site_no datetime tz_cd discharge_cfps water_year
0 USGS 3335500 2001-10-01 00:00:00 EST 2610 2002
1 USGS 3335500 2001-10-01 01:00:00 EST 2610 2002
2 USGS 3335500 2001-10-01 02:00:00 EST 2610 2002
3 USGS 3335500 2001-10-01 03:00:00 EST 2630 2002
4 USGS 3335500 2001-10-01 04:00:00 EST 2630 2002
annual_mean_discharge_rate = df.groupby('water_year')[['discharge_cfps']].mean()
# display(annual_mean_discharge_rate)
discharge_cfps
water_year
2002 9379.829589
2003 8678.468324
2004 8562.505005
2005 8928.776256
2006 6710.805312
2007 10331.564789
2008 10626.336623
2009 8972.046607
2010 5298.569557
2011 10519.540869
2012 9013.624424
2013 9007.924205
2014 9079.561658
2015 12267.393776
2016 6445.875810
2017 10240.721464
annual_mean_discharge_rate.plot.bar(figsize=(8, 6), xlabel='Water Year', ylabel='Discharge (cubic feet / sec)', legend=False)
%%timeit
比较pandas.Series.where
与pandas.Series.apply
和np.where
的比较,该函数来自另一个答案。
.Series.where
是矢量化的,而.apply
不是矢量化的。import numpy as np
# function from other answer; updated because pd.datetime is deprecated
def assign_wy(row):
if row.month>=10:
return(row.year + 1)
else:
return(row.year)
%%timeit
df.datetime.dt.year.where(df.datetime.dt.month < 10, df.datetime.dt.year + 1)
[out]:
66.9 ms ± 1.67 ms per loop (mean ± std. dev. of 7 runs, 10 loops each)
%%timeit
df.datetime.apply(lambda v: np.where(v.month >= 10, v.year + 1, v.year))
[out]:
1.38 s ± 23 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)
%%timeit
df.datetime.apply(lambda x: assign_wy(x))
[out]:
861 ms ± 9.3 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)