utils操作

除了画图和基本clean up操作以外,在分析数据集的过程中还有一些基本的切片操作以及其他,在这里记录一下。
数据集来源pokemon kaggle,基本样式

        #        Name	       Type 1	Type 2	HP	Attack	Defense	Sp. Atk	Sp. Def	Speed Generation Legendary
0	1	Bulbasaur	Grass	Poison	45	49	49	65	65	45	1	False
1	2	Ivysaur	        Grass	Poison	60	62	63	80	80	60	1	False
2	3	Venusaur	Grass	Poison	80	82	83	100	100	80	1	False
3	4	Mega Venusaur	Grass	Poison	80	100	123	122	120	80	1	False
4	5	Charmander	Fire	NaN	39	52	43	60	50	65	1	False

pandas相关

1. loc,iloc操作,slice操作

# loc,使用index获取第一二行的name和hp
df.loc[[0,1],['Name','HP']]
# 获取整行
df.loc[[0,1]]
# 获取整列
df.loc[:,'Name']
# 切片
df.loc[2:3,'Name']
# 条件操作
df.loc[lambda df:df['Attack']>50]
df.loc[df['Attack']>50]
# 2个以上条件,用np.logical_xxx(矩阵元素相乘)
df.loc[np.logical_or((df['Name'] == 'Ivysaur'), (df['Name'] == 'Venusaur'))]
# iloc: integer-based loc
# 基本操作和loc很接近
df.iloc[0]
df.iloc[2:3]
df.iloc[[2,3]]
# 对于col的选择不能用string,而是对应的index
df.iloc[2:3,0:3]
# 每隔2个index选一下
df.iloc[df.index %2 == 0]

2. index操作

# 设定新的index
df.set_index(['Name'])
# 还可以设置两个index
df.set_index(['Name','Legendary'])
# 这时候的loc访问使用tuple,而且要按照对应type给定,而不是str!(数字就是40,boolean就是True,不用加''!)
df.loc[('Bulbasaur',False)]

3. 将datetime set index然后resample操作

# 我们新建一个time index然后设置为index,然后再resample
dateindex = pd.date_range(start= '1/1/2000', periods=9, freq='T')
series = pd.Series(range(9), index=dateindex)
# 重新没3分钟采样,将采样结果求和
series.resample('3T').sum()
series.resample('30S').apply(np.sum)
# 如果采样后存在nan的情况可以用pad()去除或者bfill/ffill(backfill用后面的数值填充nan/forwardfill)
series.resample('3T').pad().sum()
series.resample('3T').bfill().sum()
# 自定义resampler
def custom_resampler(array_like):
    return np.sum(array_like) + 5
series.resample('30S').apply(custim_resampler)

4. group然后aggregate操作

按照官网上的说法groupby操作被分为:split(按照axis=0,1进行split),apply(是否需要apply什么func),combine(组合成一个新的dataframe)

# 比如我们可以看不同类型的Pokemon他们的所有数值平均
df.groupby(by='Type 1',axis=0,sort=False,dropna=False).aggregate(np.mean)
# 这里可以看到黑暗属性的HP平均都比BUG的高,而且BUG里面没有传说。
	#	      HP	      Attack	      Defense	      Sp. Atk	      Sp. Def	      Speed	      Generation	Legendary
Type 1									
Bug	369.072464	56.884058	70.971014	70.724638	53.869565	64.797101	61.681159	3.217391	0.000000
Dark	508.387097	66.806452	88.387097	70.225806	74.645161	69.516129	76.161290	4.032258	0.064516

5. apply,transform操作

apply,transform和aggregate的区别都在那里? ---> 根据这篇https://stackoverflow.com/questions/27517425/apply-vs-transform-on-a-group-object

  1. 输入:
    • apply将整个dataframe作为整体导入你的func里面
    • transform/aggregate将你dataframe每个column切片成Series,一个个导入你的func里面
  2. 输出:
    • apply自定义func的输出可以是dataframe,series,np.adarray,list,scaler
    • transform自定义输出必须是1-dim sequence和输入的长度保持一致
df.groupby(by='Type 1').apply(np.mean)
df.groupby(by='Type 1').transform(np.mean)

6. concat,stack,melt,pivot操作 -----------> 到下一章

7. 基本IO,to_csv,to_json操作

# 直接
df.to_csv()
df.to_json()
df.to_txt()

8. sort操作

可以sort_values/sort_index

# sort_values
# 选择axis=0,然后by column,快速排序,排序的方法key是ascii小的在前
df.sort_values(by=['col'], axis=0, ascending=True, inplace=False, kind='quicksort', key=lambda col: col.str.lower())

# sort_index
df.sort_index(axis=0,  ascending=True,  kind='quicksort', key=lambda col: col.str.lower())

9. 包含特定str操作

对于series可以有regex查询str的操作

s1 = pd.Series(['Mouse', 'dog', 'house and parrot', '23', np.NaN])
s1.str.contains('house|dog', regex=True)
# 用于寻找包含某个特殊字段的df
df[df['Name'].str.contains('saur').fillna(False)]

10. 创建date_range操作

# 明确开始,结束和分几段
date_range = pd.date_range(start='1/1/2020',end='12/1/2020',periods=5)
# 开始,结束,间隔
date_range = pd.date_range(start='1/1/2020',end='12/1/2020',freq='M')
# 开始,间隔,分段
date_range = pd.date_range(start='1/1/2020',periods=5,freq='M')
# 精确到秒
date_range = pd.date_range(start='2018-04-24 12:00:00',periods=5,freq='M')
# 常见freq
Y,M,D,H,min/T,S,ms,us:年月日(calender day),小时,分钟,秒,毫秒,微妙
Q:quarter季度
W:周
B:business day工作日

11. 简单类型转换操作as_type

# 可以用df.info()来查看变化
df['Name'] = df['Name'].astype('category')

12. inplace的含义:

  • 也就是不用将输出再赋值给输入,输入自动inplace就改变了。