目录
1.numpy数据库
1)数组
(1)创建数组
(2)花式索引
(3) 数组形状改变
2)通用函数
(1)重要函数
3)numpy文件读写
(1)文件读取
(2)文件存储
(3)numpy字符串
4)numpy运用
(1)随机数生成
2. pandas数据库
1)基本操作
(1)常用数据结构
(2)文件读取与保存
(3)数据筛选
2)pandas高级操作
(1)数据库读取与保存
(2)数据合并
(3)层次化索引
3)分组聚合和透视图
(1)数据排序
(2)分组聚合
(3)透视图和交叉表
4)pandas数据分析预处理
(1)pandas其他函数预算
(2)数据清洗
(3)数据离散化
# 导入库 import numpy as np
arr1 = np.array([-9,7,4,3])
np.arange(0,10,1)
np.linspace(1,10,10)
np.logspace(1,5,base=2,num=10)#创建等比数列
#特征
arr1.ndim: 返回int,表示ndarray的维度
arr1.shape: 返回尺寸,几行几列
arr1.size: 返回数组元素的个数 •
arr1.dtype: 返回数组中元素的类型 •
运算: 直接可以在每个元素加减乘除
arr2[[1,-1],[0,1]] #获取(1,0),(-1,1) 位置上的元素,(第二行,第一列)和(最后一行,第二列)的元素
arr2[[0,-1]][:,[0,1,3]] # 获取第一行,最后一行,以及第一列,第二列和第四列的元素
np.in1d(s,test) #测试s是否在test里面
s = np.array([1,2,3,4,3,1,2,2,4, 6,7,2,4,8,4,5])
np.sort(s)
np.argsort(s)
s.argmax()
s.argmin()
np.where(s>3,1#正确返回,-1#错误返回值)
np.extract(s>3,s)
# 读取文件
data = np.genfromtxt(r'E:\Numpy运用\arr.txt',delimiter=‘,’)
data = np.genfromtxt(r'E:\Numpy运\sales.csv',delimiter=',',skip_header= 1)
# 使用loadtxt读取
data = np.loadtxt(r'E:\Numpy运用\arr.txt',delimiter=',')
[i.title() for i in str_list]
np.char.title(str_arr)
np.char.isalpha(arr)
np.char.count(arr,’a’)
np.char.add(['中国','国庆'],['海军','大阅兵'])
[out] array(['中国海军', '国庆大阅兵'], dtype='
np.random.seed(100)
np.random.random(100)
np.random.randint(0,100,size= 100)
np.random.uniform(low=0,high=10,size=100)
np.percentile(da a,[0,25,50,75,100]) #分位数
np.transpose(arr2) #转置矩阵
#逆矩阵
from numpy.linalg import inv
arr2_inv = inv(arr2)
print(arr2_inv)
series1 = pd.Series([2.8,3.01,8.99,8.59,5.18])
series2 = pd.Series([2.8,3.01,8.99,8.59,5.18],index = ['a','b','c','d','e'],
name ='这是一 个series’)
series3 = pd.Series(np.array((2.8,3.10,8.99,8.59,5.18)),
index = ['a','b','c','d','e’])
series4 = pd.Series({'北京':2.8,'上海':3.01,'广东':8.99,'江苏':8.59,'浙江':5.18})
list1 = [['张三',23,'男'],['李四',27,'女'],['王二',26,'女']]#使用嵌套列表
df1 = pd.DataFrame(list1,columns=['姓名','年龄','性别'])
df2 = pd.DataFrame({'姓名':['张三','李四','王二'],'年龄':[23,27,26],
'性别':['男','女','女']})
array1 = np.array([['张三',23,'男'],['李四',27,'女'],['王二',26,'女']])# 使用numpy
df3 = pd.DataFrame(array1,columns=['姓名','年龄','性别'],index = ['a','b','c’] )
order.loc[0:2,['order_id','dish es_name’]] #A为行标签,B为列标签
order.loc[3:5,['order_id','dish es_name’]]
order.loc[0:2,['order_id','dishes_name']] #选择对应的行名称和多列
order.loc[order['order_id'] ==458,['order_id','dishes_name']] #按照条件选择
order.iloc[:,[0,2]] #位置索引
order.iloc[2:7,[1,2]]
order.drop(['pay_way','paymen t'],axis=1,inplace=True order.drop(labels = [3,4],inplace = True)
order.rename(columns = {'amounts':'payment'},inplace = True)
#####条件查询
order.loc[order['order_id'] ==458,['order_id','dishes_name']] #按照条件选择
#使用between
order[['dishes_id', 'dishes_name','amounts']][order['amounts'].between(10,30,inclusive=True)]
#使用pd.isin()
order[['dishes_id', 'dishes_name']][order['dishes_name'].isin(['蒙古烤羊腿','大蒜苋菜'])] # dishes_name里面带有['蒙古烤羊腿','大蒜苋菜']
###增删改查
#增
order['payment'] = order['counts']* order['amounts'] #增加一列
#假设我们希望emp_id位于第一列,怎么办,,,df.insert(位置,变量名称,取值)
#删
order.drop('pay_way',axis=1,inplace=True) #删除这一列 ,加inplace代表是否在原数据上操作
order.drop(labels = [3,4],inplace = True) # 删除索引为2对应的行
#改
order.loc[order['order_id']==458,'order_id'] = 45800 #修改数据(按照a条件)
#修改数据
order.rename(columns = {'amounts':'payment'},inplace = True)
order.describe().loc['count'] == 0 #判断计数是否为0
# 获取MYSQL数据集
import pymysql
import pandas as pd
from sqlalchemy import create_engine
# 按实际情况依次填写MySQL的用户名、密码、IP地址、端口、数据库名
conn=create_engine('mysql+pymysql://用户名:密码@服务器IP:端口/数据库名')
sql1='select * from 库名'
df1=pd.read_sql(sql1,conn)
merge1 = pd.concat([df1,df2],axis=1,join='inner’)
merge1 = pd.concat([df1,df2],axis=1,join='outer’)
order_merge = pd.concat([order1,order2,order3],axis=0,ignore_index=False)
order_merge.reset_index(inplace=True)
#•按照主键连接
merge1 = pd.merge(left = df1, right = df2, how = 'right', left_on='id', right_on='Id')#右连接
merge1 = pd.merge(left = df1, right = df2, how = 'outer', left_on='id', right_on='Id') #全连接
#按照索引上的进行合并
merge1 = pd.merge(left = df1, right = df2, how = 'left', left_index=True, right_index=True) #左连接
数据.sort_values('Year',ascending = True, na_position='last',inplace = True)
vgsales.sort_values(['NA_Sales','EU_Sales’])
vgsales.sort_values('Year',ascending = True, na_position='last',inplace = True) #升序(缺失值排最后面),inplace =True表示是否作用在原数据上
#重置索引
vgsales.reset_index(inplace = True,drop =True)
#在数据中找到JP_Sales中最小的两个值
vgsales.nsmallest(2,'JP_Sales')
#在数据中找到JP_Sales中最大的两个值
vgsales.nlargest(2,'JP_Sales')
数据名.groupby(by = 'Year').mean()
grouped = vgsales[names].groupby(by = 'Year’)
grouped1 = vgsales[names].groupby(by = ['Year','Genre’])
grouped = vgsales[names].groupby(by = 'Year',as_index=True, sort=True) #返回一个分组对象
grouped1 = vgsales[names].groupby(by = ['Year','Genre']) # 返回一个分组对象
#聚合函数 agg是一个作用于series或者DataFrame的函数,主要目的是针对分组后的对象,使用相关函数进行计算
grouped.agg([np.mean,np.sum])
grouped.agg([np.mean,np.sum]).loc[[1980,1981.0],('NA_Sales',['mean','sum'])]
grouped.agg({'NA_Sales':np.sum,'EU_Sales':np.mean}) #对2个变量分别计算不同的统计量
#apply
grouped.apply(np.mean)
vgsales[['NA_Sales','EU_Sales','JP_Sales','Other_Sales']].apply(np.mean,axis=0) #0代表计算列的情况
grouped.mean().transform(lambda x:x*2)
pivot_table( data, index, columns,value, aggfunc, fill_value, margins, margins_name=)
Index : 行分组键
columns: 列分组键
values: 分组的字段,只能为数值型变量
aggfunc: 聚合函数
margins: 是否需要总计
#案例
#margin =True 表示是否需要总计
pd.pivot_table(data= df,index='Year',values='Global_Sales',aggfunc=np.mean,margins=True,margins_name='总计')
# 两个变量列联表汇总
pd.pivot_table(data=df,index='Year',columns='Genre',values='Global_Sales',aggfunc=np.mean,margins=True,margins_name='总计')
#两层索引
pd.pivot_table(data= df,index=['Year','Platform'],values='Global_Sales',aggfunc=np.mean,margins=True, margins_name='总计')
pd.crosstab(index = df['Platform'], columns=df['Genre'],margins=True,normalize='columns') #index表示计算行百分比,columns表示计算列百分比
###交叉表
#是一种计算分组频数的特殊透视表
pd.crosstab(index = df['Platform'], columns=df['Genre'],margins=True)
#按照行进行汇总,计算频数占比
pd.crosstab(index = df['Platform'], columns=df['Genre'],margins=True,normalize='all')#normalize表示的是是否进行频率计算
pd.crosstab(index = df['Platform'], columns=df['Genre'],margins=True,normalize='columns') #index表示计算行百分比,columns表示计算列百分比
利用Pandas库中的sample。
DataFrame.sample(n=None, frac=None, replace=False, weights=None, random_state=None, axis=None)
n是要抽取的行数。(例如n=20000时,抽取其中的2W行)
frac是抽取的比列。(有一些时候,我们并对具体抽取的行数不关系,我们想抽取其中的百分比,这个时候就可以选择使用frac,例如frac=0.8, 就是抽取其中80%)
replace:是否为有放回抽样,取replace=True时为有放回抽样。
weights这个是每个样本的权重,具体可以看官方文档说明。
random_state这个在之前的文章已经介绍过了,可以理解为随机数种子
axis是选择抽取数据的行还是列。axis=0的时是抽取行,axis=1时是抽取列(也就是说axis=1时,在列中随机抽取n列,在axis=0时,在行中随机抽取n行)
#上牌时间应该为时间类型,新车价格应该为浮点型类型
sec_cars['Boarding_time'] = pd.to_datetime(sec_cars['Boarding_time'],format ='%Y年%m月',errors = 'coerce')#加上这个以防止数据格式有些数据不匹配
#时间差
sec_cars['diff_day'] = pd.datetime.today() - sec_cars['Boarding_time']
sec_cars['diff_day'] = sec_cars['diff_day']/np.timedelta64(1, 'D')#转化为天数 1代表周期,D代表天数
sec_cars['diff_year'] = pd.datetime.today().year - sec_cars['Boarding_time'].dt.year # 计算年份差
sec_cars['New_price'].str[:-1]
sec_cars['diff_day'] = pd.datetime.today() - sec_cars['Boarding_time']
df = data.sample(n=50000,replace=False)
# 将手机号中间4位隐藏
df.tel = df.tel.apply(lambda x: x.replace(x[3:7],'****'))
grouped_data['SMA_5'] = grouped_data['total_price'].rolling(5).mean()
•pct_change() #计算(后一个 - 前一个)/前一个
•计算变化率
•使用diff函数,效果如下
•diff(1) 代表用下一行减去上一行,例如第三行减去第二行
•dff(2) 代表用下二行减去上一行,例如第三行减去第一行
grouped_data['diff'] = grouped_data['total_price'].diff(1)
1.重复值处理
df[df.duplicated()] #识别重复值
np.sum(df.duplicated())
df.drop_duplicates()
df.drop_duplicates(subset= ['appname','size'],inplace=True) #删除重复值
2.缺失值处理
df.apply(lambda x: sum(x.isnull())/len(x),axis= 0) #缺失比例
###直接删除
df.dropna() 删除有缺失值的行
df.dropna(how='any',axis = 1 ) #只要有缺失,就删除这一列
###填充
df.age.fillna(df.age.mean())
df.age.fillna(df.age.median())
df.fillna(20)
#性别使用众数,年龄使用均值,收入使用中位数
df.fillna(value = {'gender':df.gender.mode()[0],'age':df.age.mean(),'income':df.income.median()})
###插补法
df.age.interpolate(method='polynomial',order=1)
3.异常值处理
pandas.cut(x, bins, right=True, labels=None, retbins=False, precision=3, include_lowest=False)
参数:
x,类array对象,且必须为一维,待切割的原形式
bins, 整数、序列尺度、或间隔索引。如果bins是一个整数,它定义了x宽度范围内的等宽面元数量,但是在这种情况下,x的范围在每个边上被延长1%,以保证包括x的最小值或最大值。如果bin是序列,它定义了允许非均匀bin宽度的bin边缘。在这种情况下没有x的范围的扩展。
right,布尔值。是否是左开右闭区间
labels,用作结果箱的标签。必须与结果箱相同长度。如果FALSE,只返回整数指标面元。
retbins,布尔值。是否返回面元
precision,整数。返回面元的小数点几位
include_lowest,布尔值。第一个区间的左端点是否包含
• 数据离散化就是分箱
• 一般常用分箱方法是等频或者等宽
sunspots.loc[sunspots['counts'] >P99,'counts_new'] = P99
sunspots.loc[sunspots['counts']