学习Pandas的主要知识点
- 创建Series
- Series基本操作
- 创建DataFrame
- DataFrame基本操作
- DataFrame文件操作
- Series,DataFrame切片和索引
- 透视表
- 数据清洗
- 数据预处理
- 分组聚合分析
- 可视化
了解 Numpy 的 ndarray
import numpy as np
import pandas as pd
#构建一维数组
array1 = np.array([1,2,3,4])
print(array1)
'''
[1 2 3 4]
'''
# 构建二维数组
data = [[1,2],[3,4],[5,6]]
array2 = np.array(data)
print(array2)
'''
[[1 2]
[3 4]
[5 6]]
'''
# 构建三维数组
array3 = np.array([[[1,2],[3,4]],[[5,6],[7,8]],[[9,10],[11,12]]])
display(array3)
'''
array([[[ 1, 2],
[ 3, 4]],
[[ 5, 6],
[ 7, 8]],
[[ 9, 10],
[11, 12]]])
'''
一维数组,二维数组,Series,DataFrame
a=np.array([1,2,3,4,5])
print(a) #ndarray
print("----------")
b=np.arange(9).reshape(-1,3)
print(b) #ndarray
print("----------")
c=pd.Series([1,2,3,4,5],index=list('abcde'))
print(c) #Series
print("----------")
d=pd.DataFrame(np.arange(9).reshape(-1,3),index=list("abc"),
columns=['A','B','C'])
print(d) #DataFrame
了解pandas的Series和DataFrame
s1 = pd.Series(data=[1,2,3,4], index=["a", "b", "c", "d"])
s1
print(s1.loc["b"]) #索引
print(s1.iloc[1]) #位置
'''
2
2
'''
df1 = pd.DataFrame(data=[[1,2,3], [4,5,6]], columns=["a", "b", "c"], index=[11, 22])
display(df1)
pandas提供两个常用的数据类型:
- Series:Series是一维带标签的数组,它可以包含任何数据类型。由一组数据和与之相关的index组成,这个结构一看似乎与dict字典差不多。
- DataFrame:DataFrame是一种类似于MySQL的具有行标识和列标识的二维表格。
DataFrame 的常规操作
# 先构造一个 DataFrame
# 创建DataFrame,指定行,列索引。
df = pd.DataFrame(np.random.rand(5, 6),
index=["地区1", "地区2", "地区3", "地区4", "地区5"],
columns=["北京","天津", "上海","沈阳", "广州", "长沙"])
display(df)
# 取一列
df["北京"]
# 取一行
df.loc["地区2"]
# 取多列
df[["北京", "长沙"]]
# 取多行
df.loc[["地区3", "地区4"]]
# 获取多行多列
df[["北京", "长沙"]].loc[["地区3", "地区4"]]
# 一些简单运算
df.max()#默认是取每列中最大的值
'''
对每一列都进行这个聚合函数的操作
'''
# 按行求最大值!
df.max(axis=1)
解释一波什么是向量
x=[1,2,3,4,5]
print(type(x))
for i in range(len(x)):
x[i]=x[i]+1
x
---------------------------------------
import numpy as np
y=[1,2,3,4,5]
y=np.array(y)
y=y+1
print(type(y))
y
# 实质就是每个分量进行对应的计算(广播机制)
合并数组
"""
合并的前提是二维数组,-1是根据列自动计算行,这里也可以是(150,1)
"""
t1=np.array([[1,2,3],[6,7,8]])
t2=np.array(['a','b'])
t3=np.concatenate([t1,t2.reshape(-1,1)],axis=1)#数组
t4=pd.DataFrame(t3,columns=['数值1','数值2','数值3','type'])
print(t4)
---------------------------------------
t1=np.array([1,2,3])
t2=np.array(['a','b','b'])
t3=np.concatenate([t1,t2])#数组
t4=pd.DataFrame(t3,columns=['new'])
print(t4)
数据分析常见方式方法
- 数据读写
- 数据去重
- 数据缺失值
- 数据过滤
- 数据转换
- 数据排序
- 数据组合/分割
- 数据分组聚合
数据分析的步骤:
1.数据加载
2.数据提取(根据业务)
3.数据清洗(代码能力,pandas)
4.数据分析(商业指标,数据透视表,建模等)
Series有两个基本属性:index和values【是一个定长的字典】
X1=Series([1,2,3,4]) #index默认0123
X2=Series(data=[1,2,3,4],index=['a','b','c','d'])
print(X1)
print(X2)
数据加载
1.消除警告
import warnings
warnings.filterwarnings("ignore")
2.设置绘制中文配置
mpl.rcParams["font.family"] = "SimHei"
mpl.rcParams["axes.unicode_minus"]=False # 用来正常显示负号
plt.rcParams['font.sans-serif']=['SimHei'] # 用来正常显示中文标签
%matplotlib inline
3.保存表格
df.to_csv('name.csv',index=False)
数据加载:
---csv文件:
df = pd.read_csv('./。。。.csv', index_col='id')
df.head()
---excel文件:
df = pd.read_excel('D:/Casedata/。。。.xlsx',index_col='id')
df.head()
数据处理
建立数据框:
data={'Chinese':[66,78,98,33],'Math':[65,78,94,66]}
df1=pd.DataFrame(data) #索引为012
df1
更改索行引:
df2=pd.DataFrame(data,index=['小明','小华','小红','小明'])
df2
重命名列名:
df2.rename(columns={'Chinese':'语文','Math':'数学'},inplace=True)
更改数据格式:
df2['Chinese'].astype('str')
df2['Chinese'].astype(np.int64)
删除
删除行,列,重复,特定条件
1.删除特定条件的行:
df.drop(df[df.payMoney<0].index,inplace=True)
2.删除列:
df.drop(['desc','url'],axis=1) #按照列中,删除描述和URL链接
3.删除空值超过行数一半的列
half_count=len(df)/2
df.dropna(thresh=half_count,axis=1)
4.简单粗暴的删除空行
df.dropna(axis=0)
5.去掉除了空值,就只有一个属性的列
orig_columns=df.columns#展现所有的列
drop_columns=[]
for col in orig_columns:
#dropna()先删除空值,再去重计算唯一的属性
col_series=df[col].dropna().unique()
if len(col_series)==1:
drop_columns.append(col)
df=df.drop(drop_columns,axis=1)
print(drop_columns)#查看删除了哪些列
6.删除特定字段含有特定属性的行
df.drop(df[df['挂牌价格']=='暂无数据'].index,inplace=True)
#df['挂牌价格']=='暂无数据'返回的是布尔值
删除字段中为空值的行
df.drop(df[df['Type'].isnull()].index,replace=True)
查看
查看空值
查看整体描述
1.整体描述
df.describe() #对数值型的数据作基本描述
df.info()
2.查看订单记录
df.orderID.size #有重复的订单记录
df.orderID.unique().size #没有重复的订单记录
df.orderID.unique() #不重复的具体是哪几个
3.在某个字段中满足条件的记录数(查看下架商品的个数)
df.goodsID[df.goodsID=='PR000000'].size
4.数据表的合并:
df1=DataFrame({'name':['小明','小华','小红'],'data1':range(1,4)})
df2=DataFrame({'name':['小明','小华','小北'],'data2':range(3,6)})
df3=pd.merge(df1,df2,on='name',how='left')
df3
5.字段太长,展示第一行
df.iloc[0]
6.数据有多少行、列
df.shape#行、列
df.shape[0]#行
df.shape[1]#列
7.注意[]里面是布尔值
df[df.orderAmount < 0]
df[df.Size=='Varies with device']
8.查看是数值型是记录
df['A'].isnumeric().sum()
常见函数的使用
1.mask函数
df['payment'] = df['payment'].mask(df['discount']>1,None)
#mask,一一对应的,就是discount>1,就设置为None,类似于map函数
#这种情况就是支付金额大于订单金额
display(df["带看次数"].head(3))
display(df["带看次数"].apply(lambda x:x*100).head(3))
提取字段中的信息作为新字段
例如:
房子成交标题 弘善家园 3室2厅 128.78平米
df_series=df['房子成交标题'].str.split(' ').apply(lambda x:x[0])
df.insert(1,'小区',df_series)
分组聚合、统计(数据透视表相关)
统计每个分类的频数【kmodel.labels_是ndarray】
pd.Series(kmodel.labels_).value_counts()
每个种类的的记录数,类似groupby的用法,包括空值的个数,默认不统计空值的记录
df['Category'].value_counts(dropna=False)
#查看票房收入统计
#1.导演vs票房收入(统计每个导演的总票房)降序
group_director=data.groupby(by='director_name').['gross'].sum().sort_values(ascending=False)
group_director
# 1.3 导演+主演vs票房收入
#先按导演分组,也就是可能一个导演下有多个演员
group_actor = data.groupby(by=['director_name','actor_1_name'])['gross'].sum().sort_values(ascending=False)
统计特定字段特定属性的记录数
df["挂牌价格"][df["挂牌价格"] == "暂无数据"].count()
统计某个字段的属性的值
df['A'].value_counts()
df.dtypes.value_counts()
只选定字符串类型的列
object_columns_df=df.select_dtypes(include=['object'])
一次性查看指定列的标签统计
cols=['A','B','C','D']
for c in cols:
print(df.[c].value_counts())
---------------------------------------------------------------------------------------
# 任务2、查看imdb评分统计
# 2.1 查看各imdb评分的电影个数
imdb = data.groupby('imdb_score')['movie_title'].count()
imdb
# 2.2 查看平均imdb评分最高的前20导演
director_mean = data.groupby('director_name')['imdb_score'].mean()
top20_imdb_directors = director_mean
---------------------------------------------------------------------------------------
# 任务3、电影产量年份趋势
movie_years = data.groupby('title_year')['movie_title'].count()
加一个占比字段:【】
size=size.to_frame()
size['rfm_pct'] = ["%.2f%%" % (i/sum(size.values) * 100) for i in size.values]
缺失值处理
*如何发现?
1.查看非空信息
df.info()
#每个字段非空的记录数,看哪个字段的记录不一致,说明其有空记录
2.统计每列的缺失值并加起来
df.isnull().sum()
3.怎样处理?
1.对于字符串直接删除:
df.drop(index=df[df.channelId.isnull()].index,inplace=True)
df[df.channelId.isnull()] #显示0
2.对于字符串填设定值:
--填默认值
--向上填充 ffill
--向下填充 bfill
3.对于数值类型:
--用平均数填充
df['Rating'].fillna(value=df['Rating'].mean(), inplace=True)
重复值的处理
1.如何发现:
对于订单编号而言,其值时唯一的,一定要处理
但是对于用户id、城市id等重复值正常的
#1.查看有无重复值
df.orderId.unique().size#104530
df.orderId.size#104557 ,说明有重复值
#具体哪些是重复的
result = df[df.duplicated(keep=False)]
print(result)
2.怎么处理?
直接删除:
df.drop(df[df.orderId.duplicated()].index, inplace=True)
df.orderId.unique().size
数据替换【replace】
1.指标转换【新加一列】
【full paid:1,charged:0】
data=['haha','hehe','haha']
df = pd.DataFrame(data,
index=["小明", "小红", "小华"],
columns=["stauts"])
#df
tran={'haha':1,'hehe':0}
df['sign']=df['stauts'].map(tran)
df
【直接替换的情况】:
stauts={'stauts':{'haha':1,'hehe':0}}
df=df.replace(stauts)
df
2.replace的使用(30M--->30e+6)
df['Size'] = df['Size'].str.replace('M', 'e+6')
df["建筑面积"] = 128.78㎡ 去掉单位,转换成数值类型
result_df = df["建筑面积"].str.replace("㎡", "").astype(float)
提取字段中的信息作为新字段
例如:
房子成交标题 弘善家园 3室2厅 128.78平米
df_series=df['房子成交标题'].str.split(' ').apply(lambda x:x[0])
#Series
df.insert(1,'小区',df_series)
去掉字段末尾字符【※※※】
例如:2019.11 成交
df['成交日期']=df['成交日期'].str.replace(' 成交','')
重点分析场景
1.#支付金额大于订单金额的情况,计算平均折扣,用订单金额*平均折扣
1.平均折扣:
#用准确折扣之和/打折扣的订单数
df['discount'] = (df.payment/df.orderAmount) #创建折扣字段
meanDiscount = df[df['discount']<=1].discount.sum() / df[df['discount']<=1].discount.size
meanDiscount
#4.对折扣大于1的数据进行填补 (先把他变为空值)
df['payment'].fillna(value=df.orderAmount*meanDiscount , inplace=True)
'''
#按照周来分析,2020年每一周中的北京市的二手房交易的数量是上涨还是下降趋势,还是基本不变?
思路:
1.将日期中的年、月、周提取出来,作为新的列
2.增加一个新列count=1
3.将年、周分组,计算count的和
4.提取想要的年份,各周的count值
lianjia.groupby(["成交时间-年","成交时间-周"])["count"].sum()
'''
'''
#按照周来分析二手房成交的单位均价的走势怎么样?
思路:
1.单位均价=这周房子总成交价/这周房子总建筑面积。将年、周分组,计算成交价格求和,计算建筑面积求和:
lianjia.groupby(["成交时间-年","成交时间-周"])[["成交价格", "建筑面积"]].agg({"成交价格":"sum", "建筑面积":"sum"})
'''
合并多张表格
import os
import pandas as pd
os.chdir(r"D:\美云智数\test1")
path=r"D:\美云智数\test1"
table=pd.DataFrame()
files=os.listdir(path)
for i in files:
info=pd.read_excel(i)
table=table.append(info)
print(excel_name)
table
# table.to_excel("合并.xlsx")