您现在的位置是:首页 >技术杂谈 >python数据分析网站首页技术杂谈
python数据分析
读数据并显示前6行。
# 读数据
import pandas as pd
# dtype=object,防止年份信息读取为小数。
df = pd.read_csv("Nowcoder.csv", sep=",", dtype=object)
print(df.head(6))
显示行列数,53行,6列,(53,6)
print(df.shape)
取第10行数据
# 通过行号来取行数据
# print(df.iloc[10,:])
# 通过行索引 "Index" 中的具体值来取行数据
print(df.loc[10,:])
取某一列
# 读取第一列的所有行
data.iloc[:,1]
第10行,第20行,第5列的
print(df.iloc[[10,20],5])
如果你想知道这份数据是不是所有列的信息都是有数据的,有没有哪些列的数据没有补全,请输出每列信息是否有为空值。
print(df.isnull().any(axis=0))
取language=python的一行
print(df[df['Language']=='Python'])
取语言为Python对应的成就值这一列的信息,包括列号。
print(df[df['Language'] == 'Python']['Achievement_value'])
最后5行用户的用户ID、等级、成就值、常用语言等数据,包括行号。
print(df.iloc[-5:][['Nowcoder_ID', 'Level', 'Achievement_value', 'Language']])
该数据集中语言为Java且毕业年份为2020的对应的所有列的信息,包括列号。
print(df[(df['Graduate_year']==2020)&(df['Language']=='Java')])
print(Nowcoder.query('Graduate_year ==2020 & Language == "Java"'))
输出该数据集中语言为CPP、C、C#对应的所有列的信息,包括列号。
# print(Nowcoder.loc[(Nowcoder.Language=='C')|(Nowcoder.Language=='CPP'),:])
# print(Nowcoder[Nowcoder['Language'].isin (['CPP','C','C#'])])
# print(Nowcoder.query("Language == 'CPP' or Language == 'C'"))
print(Nowcoder.query("Language in ['CPP','C']"))
# print(Nowcoder.loc[Nowcoder.Language.isin(["CPP", "C"])])
刷题量不低于500对应的等级与成就值这一列的信息,包括列号
print(Nowcoder.query("Num_of_exercise>=500").loc[:,['Level','Achievement_value']])
想要知道牛客网有哪些使用CPP的7级用户,且他们的毕业年份和你不是同年的,请问该怎么筛选?
print(df.query('Language == "CPP" & Level >= 7 & Graduate_year != 2018'))
各种语言的人数
print(Nowcoder["Language"].value_counts())
最大和最小
print(df["Continuous_check_in_days"].max())
print(df["Continuous_check_in_days"].min())
Python用户的平均提交次数
print((Nowcoder.query("Language == 'Python'")['Number_of_submissions'].mean().round(1)))
题数量不低于10题的那部分用户。用户等级的中位数
print(int(Nowcoder[Nowcoder['Num_of_exercise']>=10]['Level'].median()))
## 求中位数: median()函数
## 求平均数: mean()函数
语言个数及种类
# nunique可以直接统计不同值的个数
print(Nowcoder['Language'].nunique())
print(Nowcoder['Language'].unique())
等级的众数
print(pd.DataFrame(Nowcoder['Level'].mode(), columns=['Level']))
用户成就值与最近连续签到天数的四分之一分位数以及刷题量与代码提交次数的四分之三分位数
import pandas as pd
Nowcoder = pd.read_csv('Nowcoder.csv', sep=',')
print(Nowcoder[['Achievement_value','Continuous_check_in_days']].quantile(q=0.25))
print(Nowcoder[['Num_of_exercise','Number_of_submissions']].quantile(q=0.75))
7级用户中最高成就值与最低成就值之差。
import pandas as pd
df= pd.read_csv('Nowcoder.csv',sep = ',')
print(int(df.query("Level == 7")['Achievement_value'].max()-df.query("Level == 7")['Achievement_value'].min()))
用户刷题量的方差以及提交代码次数的标准差
# var
print(Nowcoder['Num_of_exercise'].var().round(2))
# std
print(Nowcoder['Number_of_submissions'].std().round(2))
大佬的成就值各自占据了所有人成就值总和的百分之多少
print(Nowcoder.query("Level == 7")['Achievement_value'] / Nowcoder['Achievement_value'].sum())
正确率(刷题量/代码提交次数)
print((file.query("Num_of_exercise > 10")['Num_of_exercise'] / file.query("Num_of_exercise > 10")['Number_of_submissions']).max().round(3))
输出每一行用户名字的长度,包括行号。
print(df['Name'].str.len())
去掉有缺失数据的行
Nowcoder.dropna(axis=0,inplace=True)
用当前的最大年份填充缺失的毕业年份(“Graduate_year”),用Python填充缺失的常用语言(“Language”),用成就值的均值(四舍五入保留整数)填充缺失的成就值(“Achievement_value”)。
df['Graduate_year'].fillna(df['Graduate_year'].max(),inplace=True)
df['Language'].fillna('Python',inplace=True)
df['Achievement_value'].fillna(int(df['Achievement_value'].mean()),inplace=True)
输出重复的数据,以及删除重复行后的全部数据
print(Nowcoder.duplicated())
print(Nowcoder.drop_duplicates())
用户ID、等级与最后提交日期三列,包括行号。
df['Last_submission_time'] = pd.to_datetime("2022-01-01")
print(df[['Nowcoder_ID','Level','Last_submission_time']])
读json
data = pandas.read_json("Nowcoder.json", dtype=dict)
2021年12月每天练习题目的数量。
import pandas as pd
nowcoder = pd.read_csv('nowcoder.csv', parse_dates=True, index_col='date')
daily_num = nowcoder.groupby('date')['question_id'].count()
print(daily_num)
用户练习的平均次日留存率
--复制一张表,并将时间加1天,两张表进行合并,取交集(how='inner'),此时运行的结果就是第二天继续的user,然后count
import pandas as pd
df = pd.read_csv('nowcoder.csv',sep=',')
df['date'] = pd.to_datetime(df['date']).dt.date
df1 = df.copy()
df1['date'] = df1['date'] + pd.Timedelta(days=1)
total = pd.merge(df,df1,how='inner',on=['user_id','date'])
n = total['user_id'].count()
n1 = df['user_id'].count()
print(round(n / n1 ,2))
每日正确与错误的答题次数
import pandas as pd
nowcoder = pd.read_csv('nowcoder.csv')
nowcoder['year-month-day'] = pd.to_datetime(nowcoder['date']).dt.date
print(nowcoder.groupby(['result','year-month-day'])['year-month-day'].count())
答题正误总数
print(df.groupby(['result'])['result'].count())
连续练习题目3天及以上的用户
'''
代码已通过,两个要点:
1. 先去掉date的时间,再转为日期格式;
2. 对user_id和答题日期去重。
'''
import pandas as pd
from datetime import timedelta
nowcoder = pd.read_csv('nowcoder.csv')
nowcoder['date'] = pd.to_datetime(nowcoder['date'].str.split(' ', expand=True).iloc[:,0]) # 去掉时间,然后将字符串转为日期格式
df = nowcoder[nowcoder['date'].dt.strftime("%Y-%m") == '2021-12'][['user_id','date']].drop_duplicates() # 筛选12月的数据,只取user_id和答题日期,并去重
df['rk'] = pd.to_timedelta(df.groupby(['user_id'])['date'].rank(),unit='d') # 根据user_id分组,并根据答题日期date排序;将排序转为日期差rk,以天为单位
df['diff'] = df['date']-df['rk'] # 答题日期减去日期差rk,得到diff;同一个用户同一次连续答题,会有一样的diff值
df1 = df.groupby(['user_id','diff']).count() # 得到每个用户每次连续答题的天数
df2 = df1.groupby('user_id')['rk'].max() # 取用户最大连续答题天数
print(df2[df2>=3])
每年毕业生中最高的成就值分别是多少?
result = data.groupby('Graduate_year')['Achievement_value'].max()
按照等级顺序输出每个等级下每种常用语言的使用人数
print(Nowcoder.groupby(['Level','Language']).Nowcoder_ID.count())
在人数大于5的条件下,各个等级都分别有多少人?
print(df.groupby(['Level']).Nowcoder_ID.count()>5)
报名人数不为0的项目及其对应的报名人数
import pandas as pd
signup = pd.read_csv('signup.csv')
items = pd.read_csv('items.csv')
m = pd.merge(items,signup,on='item_id')
print(m.groupby(['item_name']).employee_id.count()>0)
所有项目的报名人数(没有人报名的项目的报名人数输出为0即可
import pandas as pd
signup = pd.read_csv('signup.csv')
items = pd.read_csv('items.csv')
# 合并
data = pd.merge(items, signup, on='item_id', how='left')
cnt = data.groupby(by='item_name')['employee_id'].count()
#
print(cnt)
另一种
import pandas as pd
signup = pd.read_csv('signup.csv')
items = pd.read_csv('items.csv')
df = items.set_index('item_id').join(signup.set_index('item_id'),
on='item_id', how='outer')
print(df.groupby('item_name')['name'].count())
- 上下拼接
append():
一般来说它们会有相同的列名,
拼接之后的索引并没有随新表更新,
可以通过设置参数ignore_index=True来解决
concat():
默认axis=0,若为1实现左右拼接
- 左右拼接
merge():
类似SQL的join
join()
主要是列索引上的合并,
默认为左连接
import pandas as pd
signup = pd.read_csv('signup.csv')
signup1 = pd.read_csv('signup1.csv')
items = pd.read_csv('items.csv')
df1 = signup.append(signup1,ignore_index=True)
df = items.merge(df1,on='item_id',how='inner')
print(df.groupby('item_name').employee_id.count())
import pandas as pd
signup = pd.read_csv('signup.csv')
items = pd.read_csv('items.csv')
t1=pd.merge(items,signup,on='item_id',how='inner')
print(t1.query("department=='functional'&item_name=='javelin'")[['employee_id','name','sex']].reset_index(drop=True))
#reset_index表示重置索引,原来的索引会作为数据列保留下来,如果不想保留就加上drop=True
import pandas as pd
items = pd.read_csv('items.csv')
signup = pd.read_csv('signup.csv')
#合并
data = pd.merge(signup, items, on="item_id", how="inner")
#透视表
result = data.pivot_table(
['employee_id'], #列表形式会作为列名输出到结果
index = ['sex','department'],
columns = 'item_name',
aggfunc = 'count',
fill_value = 0 #对空的组合,填充值为0
)
print(result)
import pandas as pd
Nowcoder1 = pd.read_csv('Nowcoder1.csv', sep=',')
Nowcoder2 = pd.read_csv('Nowcoder2.csv', sep=',')
m = pd.merge(Nowcoder1,Nowcoder2,on='Nowcoder_ID')
print(m[['Name','Num_of_exercise','Number_of_submissions']])
排序取前三个
import pandas as pd
sales = pd.read_csv('sales.csv')
df = sales.sort_values(by='monetary',ascending=False,inplace=False).reset_index(drop=True)[:3]
print(df)
升序
df = Nowcoder.sort_values(by='Level',ascending=True)
RFM分类
import pandas as pd
sales = pd.read_csv('sales.csv')
# 按照结果要求转换类型
sales[['monetary']] = sales[['monetary']].astype('float32')
# 求百分位
des = sales[['recency', 'frequency', 'monetary']].describe().loc['25%':'75%']
# 计算RFM
sales['R_Quartile'] = sales['recency'].apply(lambda x: 4 if x <= des.iloc[0,0] else (3 if x <= des.iloc[1,0] else (2 if x <= des.iloc[2,0] else 1)))
sales['F_Quartile'] = sales['frequency'].apply(lambda x: 1 if x <= des.iloc[0,1] else (2 if x <= des.iloc[1,1] else (3 if x <= des.iloc[2,1] else 4)))
sales['M_Quartile'] = sales['monetary'].apply(lambda x: 1 if x <= des.iloc[0,2] else (2 if x <= des.iloc[1,2] else (3 if x <= des.iloc[2,2] else 4)))
#
print(sales.head())
RFM前5
import pandas as pd
sales = pd.read_csv('sales.csv')
# 按照结果要求转换类型
sales[['monetary']] = sales[['monetary']].astype('float32')
# 求百分位
des = sales[['recency', 'frequency', 'monetary']].describe().loc['25%':'75%']
# 计算RFM
R = sales['recency'].apply(lambda x: 4 if x <= des.iloc[0,0] else (3 if x <= des.iloc[1,0] else (2 if x <= des.iloc[2,0] else 1))).astype('str')
F = sales['frequency'].apply(lambda x: 1 if x <= des.iloc[0,1] else (2 if x <= des.iloc[1,1] else (3 if x <= des.iloc[2,1] else 4))).astype('str')
M = sales['monetary'].apply(lambda x: 1 if x <= des.iloc[0,2] else (2 if x <= des.iloc[1,2] else (3 if x <= des.iloc[2,2] else 4))).astype('str')
# 合并RFM
sales['RFMClass'] = R+F+M
#
print(sales.head())
# 筛选444用户
sales1 = sales[sales['RFMClass'] == '444'].sort_values(by='monetary', ascending=False).reset_index(drop=True)
#
print(sales1.head(5))