pandas基于numpy, 偏重于数据分析。
两种数据类型
Series
# data可以是 list, np.array, dict.
# index 可选, 默认为 整数索引
data =pd.Series(data,index=index,dtype=dtype) # 用于创建 一维数组
>>>0 1.5
1 3.0
2 4.5
3 6.0
dtype: float64
data = pd.Series([1.5,3,4.5,6], index=["a","b","c","d"])
>>>a 1.5
b 3.0
c 4.5
d 6.0
dtype: float64
a_dict = {1:1,2:2}
data = pd.Series(a_dict)
print(data)
>>>1 1
2 2
dtype: int64
##### 对于dict index进行设置
a_dict = { "burger":10, "fries":3, "drink":2 }
data = pd.Series(a_dict, index=["burger","noodels"])
print(data)
>>>burger 10.0
noodels NaN
dtype: float64
#### data为标量情况
data = pd.Series(5,index=[100,200,300])
>>>100 5
200 5
300 5
dtype: int64
#根据标签 搜索数据
data["a"]
>>> 1.5
##### pd.Series支持多种数据类型在一个序列中
### 数据类型 会因为数据的类型进行跃升,成为Object
data = pd.Series([1,2,"3",4])
print(data)
>>>0 1
1 2
2 3
3 4
dtype: object
###### 数据类型强制转换
data = pd.Series([1,2,"3",4], dtype=float)
### "3"被强制转换为float
print(data)
>>>0 1.0
1 2.0
2 3.0
3 4.0
dtype: float64
DataFrame
# data: 数据, list, dict, numpy
# index: 行索引
# columns: 列标签
pd.DataFrame(data, index=index, columns=columns)
###### 从 Series创建 DataFrame
population_dict = {
"Beijing": 2154,
"Shanghai": 2424,
"Shenzhen": 1303,
"Hangzhou": 981
}
population_ser = pd.Series(population_dict)
population_df = pd.DataFrame(population_ser)
print(population_df)
## 因为 columns标签缺省,因此自动columns设置为0.
>>>
0
Beijing 2154
Shanghai 2424
Shenzhen 1303
Hangzhou 981
###### 从 Series创建 DataFrame
population_dict = {
"Beijing": 2154,
"Shanghai": 2424,
"Shenzhen": 1303,
"Hangzhou": 981
}
population_ser = pd.Series(population_dict)
population_df = pd.DataFrame(population_ser, columns=["population"])
print(population_df)
>>>
population
Beijing 2154
Shanghai 2424
Shenzhen 1303
Hangzhou 981
import pandas as pd
import numpy as np
population_dict = {
"Beijing": 2154,
"Shanghai": 2424,
"Shenzhen": 1303,
"Hangzhou": 981
}
GDP_dict = {
"Beijing": 1000,
"Shanghai": 1000,
"Shenzhen": 1000,
"Hangzhou": 1000
}
population_ser = pd.Series(population_dict)
GDP_ser = pd.Series(GDP_dict)
data_df = pd.DataFrame({"population":population_ser, "GDP":GDP_ser, "country":"China"})
data = np.random.randint( 10, size=(3,2) )
print( pd.DataFrame( data, columns=["foo","bar"], index=["a","b","c"] ) )
>>>
> foo bar
a 5 6
b 0 8
c 2 9
##### csv中获取数据
pd.read_csv("population.csv")
常用属性
data_df.values # 返回Numpy类型
data_df.index
data_df.columns
data_df.shape # 数据i形状
data_df.size # 大小
data_df.dtypes # 返回每一个columns对应的dtype
索引
列索引
population GPA country
Beijing 2154 1000 China
Shanghai 2424 1000 China
Shenzhen 1303 1000 China
Hangzhou 981 1000 China
data_df[ "population" ] # 类型是 Series
data_df[ ["GPA", "population"] ] # 仍是 DataFrame
data_df.population # 等同于 data_df["population"]
行索引
##### 绝对索引
data_df.loc[ "Beijing" ]
data_df.loc[ ["Beijing","Hangzhou"] ]
##### 相对索引
data.iloc[0]
data.iloc[ [1,3] ]
获取标量
data_df.loc[ "Beijing", "GDP" ]
data_df.iloc[0, 1]
data_df.values[0][1]
切片
dates = pd.date_range(start="2019-01-01", periods=6)
data_df = pd.DataFrame(np.random.randn(6,4), index=dates, columns=["A","B","C","D"])
print(data_df)
###### 获取部分行的全部信息
data_df["2019-01-01":"2019-01-03"]
data_df.loc["2019-01-01":"2019-01-03"]
data_df.iloc[0:3]
###### 获取部分列的全部信息
data_df.loc[:, "A":"B"]
data_df.iloc[:, 0:3]
###### 同时对 行和列进行切片
data_df.loc[ "2019-01-01":"2019-01-03", "A":"B" ]
布尔索引
data_bool = data_df>0 # 对所有元素分别进行操作
data_df[ data_df>0 ] # 不满足的部分 会被填充 NaN
########## isin 函数
dates = pd.date_range(start="2019-01-01", periods=6)
data_df = pd.DataFrame(np.random.randn(6,4), index=dates, columns=["A","B","C","D"])
data_df["E"] = list( range(6) )
print( data_df["E"].isin( [1,2] ) )
## isin 会查看每一个的数据是否在 [1,2]中,在则为True, 不在则为False
>>>
2019-01-01 False
2019-01-02 True
2019-01-03 True
2019-01-04 False
2019-01-05 False
2019-01-06 False
Freq: D, Name: E, dtype: bool
赋值
# 直接添加就可以,此处不做讲解
#### 都是可以修改的
data_df.index
data_df.columns
数值运算和统计分析函数
数值查看
data_df.head(n) # 查看前N行
data_df.tail(n) # 查看最后N行
data.info() # 查看非空数据
通用函数
##### 基本运算
data_df + 5
np.exp(data_df) # 会被每个数值都求exp(x)运算
x_df*y_df # 每个位置的对应元素都会进行运算
x.T # 求转置
x.dot(y) # 矩阵的乘法
##### 广播运算
### 行广播
x = pd.DataFrame( np.random.randint(10, size=(3,3)), columns=list("ABC") )
y = x/x.iloc[0] # x.iloc[0]取出来第0行, 然后所有行都对第0行进行运算
x.div(x.iloc[0],axis=1) # 按行进行运算
### 列广播
x.div(x["A"],aixs=0) # 按列进行运算
统计相关
数据类型统计
y = np.random.randint( 3, size=20 )
y_df = pd.DataFrame(y,columns=["A"])
print(y_df["A"].unique()) # 查看 unique值
print(y_df["A"].value_counts()) # 查看每个值的数量
print(y_df.sort_values("A",ascending=False)) # 将值进行排序
## 行排序
y_df.sort_index() # 按照行的标签进行排序
y_df.sort_index(axis=1, ascending=True) # 按照列的标签进行排序
y = np.random.randint( 6, size=(5,5) )
y_df = pd.DataFrame(y,columns=[list("ABCDE")])
print( y_df.count()) # 每列的非空元素的个数
print( y_df.sum()) # 按列求和
print( y_df.sum(axis=1)) # 按行求和
print(y_df.max()) # 每一列的最大值
print(y_df.max(axis=1)) # 每一行的最大值
y_df.idxmax() # 每一列最大值的坐标
y_df.mean() # 均值
y_df.var() # 方差
y_df.std() # 标准差
y_df.median() # 中位数
y_df.mode() # 众数
y_df,quantile(0.75) # 任意的分位数
y_df.describe()
##### 相关性系数
y_df.corr()
y_df.corrwith(y_df["A"]) # 求一列的相关性系数
## apply 方法
y_df.apply(np.cumsum) # 对每一列的数据进行累加
y_df.apply(np.cumsum,axis=1) # 对每一行的数据进行累加
y_df.apply(lambda x:x.max()-x.min())
处理缺失值
data = pd.DataFrame( np.array([
[1, np.nan, 2],
[np.nan, 3, 4],
[5, 6, None]]), columns=["A","B","C"] )
print(data)
data.isnull()
data.notnull()
# 删除缺失值
data.dropna() # 会将有缺失值的整行进行删除
data.dropna(how="all") # 只有整列都是null才会删除
data.dropna(how="any") # 只要有缺失值就会删除
data.dropna(axis="columns")
# 填充缺失值
data.fillna(value=5)
data.fillna(value=data.mean()) # 使用每一列的均值 进行填充
#### 全部数据的平均值
fill = data.stack().mean() # 全部数据的填充值
data.fillna(value=fill)
数据合并
pd.concat( [y1_df, y2_df], ignore_index=True ) # 列标签相同, 将行合并叠加
# ignore_index 会重新标记 标签,避免重复
pd.concat( [y1_df, y2_df], axis=1) # 行标签相同, 将列进行合并叠加
pd.merge(y1_df,y2_df) # 会按照列标签, 将相同的进行合并. 会默认设置交集
pd.merge(y1_df,y2_df,how="outer") # 并集
分组和数据透视表
分组
df = pd.DataFrame({
"key": list("ABCCBA"),
"data1": range(6),
"data2": np.random.randint(0,10,size=6)
})
print(df)
for i in df.groupby("key"):
print(i)
('A', key data1 data2
0 A 0 5
5 A 5 6)
('B', key data1 data2
1 B 1 3
4 B 4 8)
('C', key data1 data2
2 C 2 0
3 C 3 1)
实际上 df.groupy("key")形成的是一个迭代器, 每一个迭代器都是一个元组, 每个元组包含两个元素, 第一个元素是 "key"的元素, 第二个元素是 "key"中元素对应的 DataFrame数据
for data, group in df.groupby("key"):
# data 表示 "key"中元素
# group 表示 对应的 DataFrame
df.groupby("key").sum() # 按"key"将数据进行分组,然后按照每组的方式进行求和
df.groupby("key").mean()
df.groupby("key")["data2"] # 会将数据中的 ["data2"]取出来, 然后还是和之前相同的结构, 只不过元组中的数据只有"data2"。
df.groupby("key")["data2"].describe()
df.groupby("key").aggregate(["min","median","max"])
data1 data2
min median max min median max
key
A 0 2.5 5 0 0.5 1
B 1 2.5 4 2 5.0 8
C 2 2.5 3 0 2.5 5
df.groupby("key").filter(filter_func) # filter_func 会根据 每一个 "key"对应的元素 进行运算, function结果输出bool值, 最后filter输出满足结果的"key"对应的部分
df.groupby("key").transform(lambda x:x-x.mean()) # 将 groupby之后的数据 按照每列进行运算。 列与列之间不会进行运算
df.groupby("key").apply(lambda x:x.max()-x.mean()) # 对groupby之后的 每一个dataframe进行处理,需要返回处理后的dataframe
###### 自定义分组键
L =[0, 1, 0, 1, 2, 0]
df.groupby(L).sum()
data1 data2
0 7 8
1 4 12
2 4 2
##### 字典映射分组
df = df.set_index("key")
mapping = {"A":"first", "B":"constant", "C":"constant"}
print(df.groupby(mapping).sum())
import pandas as pd
import numpy as np
import seaborn as sns
titanic = sns.load_dataset("titanic")
# 数据透视表
print(titanic.pivot_table( "survived",index="sex", columns="class" ))
>>>
class First Second Third
sex
female 0.968085 0.921053 0.500000
male 0.368852 0.157407 0.135447
print(titanic.pivot_table( "survived",index="sex", columns="class", aggfunc="mean", margins=True ))
class First Second Third All
sex
female 0.968085 0.921053 0.500000 0.742038
male 0.368852 0.157407 0.135447 0.188908
All 0.629630 0.472826 0.242363 0.383838
# 数据透视表
print(titanic.pivot_table( index="sex", columns="class", aggfunc={"survived":"sum","fare":"mean"}))
fare survived
class First Second Third First Second Third
sex
female 106.125798 21.970121 16.118810 91 70 72
male 67.226127 19.741782 12.661633 45 17 47
多级索引
base_data = np.array([
[1771,11115],
[2154,30320],
[2141,14070],
[2424,32680],
[1077,7806],
[1303,24222],
[798,4789],
[981,13468]
])
df = pd.DataFrame( base_data, index=[ [ "beijing", "beijing", "shanghai", "shanghai", "shenzhen", "shenzhen", "hangzhou", "hangzhou" ] , [2008,2018]*4 ],
columns=["population","GDP"])
print(df)
df.index.names = ["city", "year"]