一. Cov() 协方差
-       corr()是 相关系数 ,他将 协方差 cov 进一步压缩在 -1  ~ 1 之间 ,  
  - 1 是正相关
- 0 是不相干
- -1 是 负相关
 
	A	B	C
0	68	95	66
1	99	87	67
2	87	87	91
3	59	87	72
4	59	91	79
5	82	88	50
6	88	74	85
7	95	67	72
8	95	67	64
9	62	91	86
协方差 计算 :
np.sum ( (df.A - df.A.mean()) * (df.B - df.B.mean()))  / ( df.shape[0] )  这里自由度也是0
这里是 A 和 B 的对比
df.cov(ddof = 0)  自由度为0 是总体的 
	A	       B	      C
A	227.44	-97.56	-34.18
B	-97.56	93.64	4.82
C	-34.18	4.82	136.96二 . 矩估计 (点估计)
- 4阶梯 矩(单位)
- 一阶矩 均值
- 二阶矩 方差 2次方
  
- 三阶矩 偏度 3次方 (偏度系数)
数值越大,偏得越厉害
                
df.skew()
# -1  : 有偏态  正偏态
# 0  : 标准的高斯分布
# 1  : 左偏态  负偏态          
这里的 m 是样本量
- 四阶矩 峰度 4次方 (峰度系数)
df.kurt()
# -1  : 扁平分布
# 0  : 标准的高度
# 1  : 尖峰分布                  
     
三 . 非统计函数
3.1 乘法 : product() | mul()
df 如下
	A	B	C
0	68	95	66
1	99	87	67
2	87	87	91
3	59	87	72
4	59	91	79
5	82	88	50
6	88	74	85
7	95	67	72
8	95	67	64
9	62	91	86
df.product()  一列进行连乘
df.mul(10) 每个数 x 103.2 加减除法 , 保留小数
df.add()   加法
df.div()   除法
df.sub()   减法
df.round()   保留几位小数3.3 空值
判断是否为空值
isna()  
isnull()
判断是否不为空值
notna()
notnull() 
3.4 值计数
	A	B	C
0	68	95	66
1	99	87	67
2	87	87	91
3	59	87	72
4	59	91	79
5	82	88	50
6	88	74	85
7	95	67	72
8	95	67	64
9	62	91	86
df.A.value_counts()
对A 列进行 计数 ,看出现几次
A
59.0    2
95.0    2
68.0    1
99.0    1
87.0    1
82.0    1
88.0    1
62.0    1
Name: count, dtype: int643.5 去重计数
	A	B	C
0	68	95	66
1	99	87	67
2	87	87	91
3	59	87	72
4	59	91	79
5	82	88	50
6	88	74	85
7	95	67	72
8	95	67	64
9	62	91	86
去重后 计数
df.A.nunique()   # 8
去重 不计数
df.A.unique()
array([68., 99., 87., 59., 82., 88., 95., 62.])3.6 排序
# 按照A列来升序排列  , False就是降序
df.A.sort_values(ascending= True)
df.sort_values(by= "A",ascending= True)
四. 移动计算
4.1 shift()
df.A
0    68.0                               
1    99.0
2    87.0
3    59.0
4    59.0
5    82.0
6    88.0
7    95.0
8    95.0
9    62.0
Name: A, dtype: float64
df.A.shift(1)   # 所有数往下移一格
0     NaN
1    68.0
2    99.0
3    87.0
4    59.0
5    59.0
6    82.0
7    88.0
8    95.0
9    95.0
Name: A, dtype: float644.2 同比增长率 pct_change()
df["A1"] = df.A.shift(1)
	A	B	C	A1
0	68.0	95.0	66.0	NaN
1	99.0	87.0	67.0	68.0
2	87.0	87.0	91.0	99.0
3	59.0	87.0	72.0	87.0
4	59.0	91.0	79.0	59.0
5	82.0	88.0	50.0	59.0
6	88.0	74.0	85.0	82.0
7	95.0	67.0	72.0	88.0
8	95.0	67.0	64.0	95.0
9	NaN	91.0	86.0	95.0
df.pct_change()
# (99-68)/68 = 0.455882
A	B	C	A1
0	NaN	NaN	NaN	NaN
1	0.455882	-0.084211	0.015152	NaN
2	-0.121212	0.000000	0.358209	0.455882
3	-0.321839	0.000000	-0.208791	-0.121212
4	0.000000	0.045977	0.097222	-0.321839
5	0.389831	-0.032967	-0.367089	0.000000
6	0.073171	-0.159091	0.700000	0.389831
7	0.079545	-0.094595	-0.152941	0.073171
8	0.000000	0.000000	-0.111111	0.079545
9	0.000000	0.358209	0.343750	0.000000df.dtypes
df.支付时间 = df.支付时间.astype("datetime64[ns]")
订单ID             int64
用户ID             int64
地区ID             int64
订单金额           float64
支付时间    datetime64[ns]
dtype: object
提取时间 (hour)
df["时间"] = df.支付时间.dt.hour
df.groupby(by = "时间").订单金额.sum()
按照时间 进行 分组 ,并计算订单金额的总和
4.3 agg() 返回的是dataframe
df_ref = df.groupby(by = "时间").agg({"订单金额":"sum"})
返回的是 dataframe
	订单金额
时间	
0	170800.39
1	46212.68
2	9872.74
3	3955.66
4	1525.86
5	8439.76
6	10410.76
7	31955.27
8	18348.254.4 diff() 移动计算 (下面行 - 上面行)
df_ref.diff(1)
	订单金额
时间	
0	170800.39
1	46212.68
2	9872.74
3	3955.66
4	1525.86
5	8439.76
6	10410.76
7	31955.27
8	18348.25
	订单金额
时间	
0	NaN
1	-124587.71
2	-36339.94
3	-5917.08
4	-2429.80
5	6913.90
6	1971.00
7	21544.51
8	-13607.02
9	4820.64.5 rank()
一般不直接这么用  df_ref.rank()   不能对重复值进行排序
drop_duplicates() 多列去重
df_ref.sort_values(by=["订单金额"],ascending = False).drop_duplicates(subset = ["订单金额"]).rank(ascending = False)
 先去重 ,再按照订单金额 从大到小排序
rank_ = df_ref.sort_values(by=["订单金额"],ascending = False).drop_duplicates(subset = ["订单金额"]).rank(ascending = False).rename(columns={"订单金额":"序号"})
rename(columns={"订单金额":"序号"})
给列重新命名  订单金额 改为 序号
s.rank(method = "min")   # 排名时 有重复的话 会把相同的放在同一名, 然后 会跳排名
rank()
s.rank(method = "first") # 排名时 不会跳,相同排名 也 往下, 相当于数 行
row_number
s.rank(method = "dense")   #不会跳排名,相同排名也会放一起4.6 join() sort_values() sort_index()
df_ref.join(rank_).sort_values(by="序号")
将 df_ref 和 rank_ 进行左右的拼接   ,然后按照列 序号进行升序排序
df_ref.join(rank_).sort_values(by="序号").sort_index()
按照行 索引 进行排列 4.7 rolling()
df_ref.rolling(2).sum()
每两行 进行累加
五. 左右连接
5.1 同时获取多张表
data = pd.read_excel("./电商数据.xlsx",sheet_name=["订单信息","订单详情","地区信息"])
data["订单信息"]
5.2 merge 连接
pd.merge 进行 两表合并  这里不写 On 是 自然连接(同名字段 进行自动连接)
pd.merge(data["订单详情"],data["订单信息"])
深层复制 
订单详情 = data["订单详情"].copy()
订单信息 = data["订单信息"].copy()
5.3 两张表中没有同名字段
#如果没有相同的名称需要手动关联
#如果两列的名称不一致 ,连接以后,关联列都会保留 ,则可以删除一列
pd.merge(订单详情,订单信息,left_on=["ID"],right_on=["订单ID"]).drop(columns=["订单ID"])5.4 表的关联字段 被作为了行索引
- 设置行索引
#设置某一列为 行索引
订单详情1.set_index(["ID"],inplace=True)
订单信息1.set_index(["订单ID"],inplace=True)- 通过 行索引 进行关联
#left_index=True 代表使用 行索引作为关联
#pandas 在1.0.0 版本以后  不强制 是left_index ,也可以使用 left_on
pd.merge(订单详情,订单信息,left_index=True,right_index=True)5.5 同名列 非关联字段(列名一致,内容无关)
- 改列名
   suffixes = ()
将关联列 订单详情2,订单信息2 改名为  _订单详情2 ","_订单信息2
pd.merge(订单详情2,订单信息2,left_index=True,right_index=True,suffixes=("_订单详情2 ","_订单信息2"))
  add_prefix
订单详情2.add_prefix("订单详情2_") #为了防止 列名冲突  提前加上前缀
rename
订单详情2.rename(columns={"支付时间":"xxx时间"})#为了防止 列名冲突  提前修改列名
5.5 连接方式
- how 连接方式
pd.merge(data["订单信息"],data["地区信息"],how="inner")5.6多表连接
pd.merge(
    pd.merge(data["订单信息"],data["订单详情"],how="inner"),
    data["地区信息"]
)六 . 分组依据
-  groupby :指定一列或者 多列分组         
  - 返回的是DataFrameGroupBy 后面不会直接加聚合函数
- DataFrameGroupBy.column   ->   SeriesGroupBy.聚合函数 (返回的Series) 
    - reset_index : Series 变为 DataFrame
- un_stack : 行索引 变列索引 (得到透视表)
 
 
6.1 把行索引变成列
df.groupby(by=["省份","城市"]).订单金额.sum().reset_index()  #把行索引 恢复成列6.2 unstack() 透视表
df.groupby(by=["省份","城市"]).订单金额.sum().unstack(level=0).fillna(0)  # 透视表 把其中一个行索引 转换成列6.3 多列运算
df.groupby(by=["省份","城市"]).agg({"订单金额":["sum","mean"],"数量":"sum"})6.4 遍历运算
map 是 Series的循环
apply 任意循环
x 代表的是 被分组的 dataframe
# sumx("表",[单价] * [数量])
df.groupby(by=["省份","城市"]).apply(lambda x : (x["单价"] * x["数量"]).sum() )找个各个 省份 购买 颜色最多的 项
df.groupby(by=["省份"]).apply(lambda x :  ",".join(x.颜色.mode()) )
















