Python数据分析:Pandas与NumPy结合,实现高效数值计算,提升数据分析效率的最佳实践

目前小编的借调任务已经完成,借调到其他组完成了自己的工作,有需要的同学可以看下相关的文章:**Python(Flask)+ React && Golang(Gin)+ Vue(Element),**然后小编认为可以回到原来的组继续phper的工作,没想到,刚做完支持工作,现在又被借调到了Python项目部RolePlay数据组,目前的情况是需要做数据分析并培训相关人员,所以小编不得已又开始了紧张的复习工作已经培训文档得撰写工作,有需要的小伙伴自取。

前面已经给他们培训过Flask框架的相关知识,现在做数据分的话,个人认为技术点不难,但是比较繁复,所以需要培训NumPy和Pandas组件无论是NumPy还是Pandas,个人经验:只要掌握好了key、value、Indexes(索引),以及对象,这个就是很简单的一个东西。

NumPy:

1.强大的n维数组结构

2.线性代数、傅里叶变换和随机数特征

3.速度:基于NumPy的算法要比纯Python快10到100倍(甚至更快),并且使用的内存更少

属性:

ndarray.ndim:数组的维数,在Python中叫做rank

ndarray.shape: 数组的维数。它是一组长度由数组维数(ndim)决定的数字。例如,长度为n的一维数组的形状是n,而n行m列的数组的形状shape是(n,m)。

ndarray.size:数组中所有元素的数量。

ndarray.dtype:数组中元素的类型,如numpy.int32、numpy.int16或numpy.float64。

ndarray.itemsize:数组中每个元素的大小,以字节为单位

ndarray.data:用于存储数组元素的缓冲。通常我们只需要通过下标来访问元素,而不需要访问缓冲区。

指定维度:

 初始化:2表示数组数据维度,3表示单一维度的数据个数;
data = np.random.randn(2, 3)
输出data: array([[-0.2047,  0.4789, -0.5194],[-0.5557,  1.9658,  1.3934]])

数据获取:

数据计算:data * 10
输出:array([[ -2.0471,   4.7894,  -5.1944],[ -5.5573,  19.6578,  13.9341]])

数据计算: data + data
输出:array([[-0.4094,  0.9579, -1.0389],[-1.1115,  3.9316,  2.7868]])

函数:

函数:shape(一个表示各维度大小的元组)
data.shape
输出: (2, 3)

函数:dtype(一个用于说明数组数据类型的对象):
data.dtype
输出: dtype('float64')

唯一化以及其它的集合逻辑
names = np.array(['Bob', 'Joe', 'Will', 'Bob', 'Will', 'Joe', 'Joe'])

np.unique(names)
输出:array(['Bob', 'Joe', 'Will'],
      dtype='<U4')

ints = np.array([3, 3, 3, 2, 2, 1, 1, 4, 4])
np.unique(ints)
输出array([1, 2, 3, 4]) 

创建:

创建一维数组:

data1 = [6, 7.5, 8, 0, 1]
arr1 = np.array(data1)
输出:array([ 6. ,  7.5,  8. ,  0. ,  1. ])

创建二维数组:

data2 = [[1, 2, 3, 4], [5, 6, 7, 8]]
arr2 = np.array(data2)
输出:array([[1, 2, 3, 4],[5, 6, 7, 8]])

zeros和ones分别可以创建指定长度或形状的全0或全1数组

np.zeros(10)
输出:array([ 0.,  0.,  0.,  0.,  0.,  0.,  0.,  0.,  0.,  0.])

np.zeros((3, 6))
输出array([[ 0.,  0.,  0.,  0.,  0.,  0.],[ 0.,  0.,  0.,  0.,  0.,  0.],[ 0.,  0.,  0.,  0.,  0.,  0.]])

np.empty((2, 3, 2))
输出:array([[[ 0.,  0.],[ 0.,  0.],[ 0.,  0.]],[[ 0.,  0.],[ 0.,  0.],[ 0.,  0.]]])

创建递增数组:

np.arange(15)
输出:array([ 0,  1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11, 12, 13, 14]) 

切片(左包括,右开放):

arr = np.arange(10)
输出:array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])

arr[5]
输出:5

切片:arr[5:8]
输出:array([5, 6, 7])

修改:arr[5:8] = 12
输出 array([ 0,  1,  2,  3,  4, 12, 12, 12,  8,  9])


切片修改值,会影响到原数组
arr_slice = arr[5:8]
输出:array([12, 12, 12])

arr_slice[1] = 12345
输出:array([    0,     1,     2,     3,     4,    12, 12345,    12,     8,   9])

索引:

布尔型索引:

names = np.array(['Bob', 'Joe', 'Will', 'Bob', 'Will', 'Joe', 'Joe'])

data = np.random.randn(7, 4)
输出:array([[ 0.0929,  0.2817,  0.769 ,  1.2464],[ 1.0072, -1.2962,  0.275 ,  0.2289],[ 1.3529,  0.8864, -2.0016, -0.3718],[ 1.669 , -0.4386, -0.5397,  0.477 ],[ 3.2489, -1.0212, -0.5771,  0.1241],[ 0.3026,  0.5238,  0.0009,  1.3438],[-0.7135, -0.8312, -2.3702, -1.8608]])

names == 'Bob'
输出:array([ True, False, False,  True, False, False, False], dtype=bool)


data[names == 'Bob']
输出:array([[ 0.0929,  0.2817,  0.769 ,  1.2464],[ 1.669 , -0.4386, -0.5397,  0.477 ]])

子集索引:

arr = np.empty((8, 4))

for i in range(8):
    arr[i] = i

输出:array([[ 0.,  0.,  0.,  0.],[ 1.,  1.,  1.,  1.],[ 2.,  2.,  2.,  2.],[ 3.,  3.,  3.,  3.],[ 4.,  4.,  4.,  4.],[ 5.,  5.,  5.,  5.],[ 6.,  6.,  6.,  6.],[ 7.,  7.,  7.,  7.]])

arr[[4, 3, 0, 6]]
输出:array([[ 4.,  4.,  4.,  4.],[ 3.,  3.,  3.,  3.],[ 0.,  0.,  0.,  0.],[ 6.,  6.,  6.,  6.]])


arr[[-3, -5, -7]]
输出:array([[ 5.,  5.,  5.,  5.],[ 3.,  3.,  3.,  3.],[ 1.,  1.,  1.,  1.]]) 

数组转置和轴对换:

arr = np.arange(15).reshape((3, 5))
输出:array([[ 0,  1,  2,  3,  4],[ 5,  6,  7,  8,  9],[10, 11, 12, 13, 14]])

arr.T
输出:array([[ 0,  5, 10],[ 1,  6, 11],[ 2,  7, 12],[ 3,  8, 13],[ 4,  9, 14]])

排序:

arr = np.random.randn(6)
输出:array([ 0.6095, -0.4938,  1.24  , -0.1357,  1.43  , -0.8469])

arr.sort()
输出:array([-0.8469, -0.4938, -0.1357,  0.6095,  1.24  ,  1.43  ])

Pandas:

Pandas提供了快速便捷处理结构化数据的大量数据结构和函数。

Series 该结构能够存储各种数据类型,比如字符数、整数、浮点数、Python 对象等,Series 用 name 和 index 属性来描述 数据值。Series 是一维数据结构,因此其维数不可以改变。

DataFrame 表格型数据结构,DataFrame 是一种二维表格型数据的结构,既有行索引,也有列索引。行索引是 index,列索引是 columns。在创建该结构时,可以指定相应的索引值。

Panel 可以理解为DataFrame的容器。

默认索引从(从0开始):

obj = pd.Series([4, 7, -5, 3])
输出:
0    4
1    7
2   -5
3    3
dtype: int64

输出value值:
obj.values
输出:array([ 4,  7, -5,  3])

输出索引:
obj.index
输出:Index([ 0,  1, 2,  3])

指定索引(使用index指定):

obj2 = pd.Series([4, 7, -5, 3], index=['d', 'b', 'a', 'c'])
输出:
d    4
b    7
a   -5
c    3
dtype: int64


输出index值:
obj2.index
输出:Index(['d', 'b', 'a', 'c'], dtype='object')


指定输出:
obj2['a']
输出: -5


修改值:
obj2['d'] = 6
obj2[['c', 'a', 'd']]
输出:
c    3
a   -5
d    6
dtype: int64


指定输出:
obj2[obj2 > 0]
输出:
d    6
b    7
c    3
dtype: int64


计算:
obj2 * 2
输出
d    12
b    14
a   -10
c     6
dtype: int64


判断:
'b' in obj2
输出: True

'e' in obj2
输出: False

缺失值补全:

sdata = {'Ohio': 35000, 'Texas': 71000, 'Oregon': 16000, 'Utah': 5000}
obj3 = pd.Series(sdata)

输出: 
Ohio      35000
Oregon    16000
Texas     71000
Utah       5000
dtype: int64

states = ['California', 'Ohio', 'Oregon', 'Texas']
obj4 = pd.Series(sdata, index=states)

输出
California        NaN
Ohio          35000.0
Oregon        16000.0
Texas         71000.0
dtype: float64


pd.isnull(obj4)
输出:
California     True
Ohio          False
Oregon        False
Texas         False
dtype: bool

pd.notnull(obj4)
输出:
California    False
Ohio           True
Oregon         True
Texas          True
dtype: bool 

DataFrame:

data = {'state': ['Ohio', 'Ohio', 'Ohio', 'Nevada', 'Nevada', 'Nevada'],
        'year': [2000, 2001, 2002, 2001, 2002, 2003],
        'pop': [1.5, 1.7, 3.6, 2.4, 2.9, 3.2]}
frame = pd.DataFrame(data)
输出:
   pop   state  year
0  1.5    Ohio  2000
1  1.7    Ohio  2001
2  3.6    Ohio  2002
3  2.4  Nevada  2001
4  2.9  Nevada  2002
5  3.2  Nevada  2003


输出前五行:
frame.head()
输出:
   pop   state  year
0  1.5    Ohio  2000
1  1.7    Ohio  2001
2  3.6    Ohio  2002
3  2.4  Nevada  2001
4  2.9  Nevada  2002

缺失值补全:

frame2 = pd.DataFrame(data, columns=['year', 'state', 'pop', 'debt'],
                            'five', 'six'])
输出:
       year   state  pop debt
one    2000    Ohio  1.5  NaN
two    2001    Ohio  1.7  NaN
three  2002    Ohio  3.6  NaN
four   2001  Nevada  2.4  NaN
five   2002  Nevada  2.9  NaN
six    2003  Nevada  3.2  NaN


取值:
frame2['state']
输出: 
one        Ohio
two        Ohio
three      Ohio
four     Nevada
five     Nevada
six      Nevada
Name: state, dtype: object


取值:
frame2.year
输出: 
one      2000
two      2001
three    2002
four     2001
five     2002
six      2003
Name: year, dtype: int64


取值: 
frame2.loc['three']
输出: 
year     2002
state    Ohio
pop       3.6
debt      NaN
Name: three, dtype: object


赋值: 
frame2['debt'] = 16.5
输出: 
       year   state  pop  debt
one    2000    Ohio  1.5  16.5
two    2001    Ohio  1.7  16.5
three  2002    Ohio  3.6  16.5
four   2001  Nevada  2.4  16.5
five   2002  Nevada  2.9  16.5
six    2003  Nevada  3.2  16.5

赋值:
val = pd.Series([-1.2, -1.5, -1.7], index=['two', 'four', 'five'])
frame2['debt'] = val
输出: 
       year   state  pop  debt
one    2000    Ohio  1.5   NaN
two    2001    Ohio  1.7  -1.2
three  2002    Ohio  3.6   NaN
four   2001  Nevada  2.4  -1.5
five   2002  Nevada  2.9  -1.7
six    2003  Nevada  3.2   NaN

缺值补全:

pop = {'Nevada': {2001: 2.4, 2002: 2.9},'Ohio': {2000: 1.5, 2001: 1.7, 2002: 3.6}}
frame3 = pd.DataFrame(pop)
输出: 
      Nevada  Ohio
2000     NaN   1.5
2001     2.4   1.7
2002     2.9   3.6

行列置换:frame3.T

输出: 
        2000  2001  2002
Nevada   NaN   2.4   2.9
Ohio     1.5   1.7   3.6

设置值,自动补全:

pd.DataFrame(pop, index=[2001, 2002, 2003])
输出: 
      Nevada  Ohio
2001     2.4   1.7
2002     2.9   3.6
2003     NaN   NaN

设置索引:

obj = pd.Series([4.5, 7.2, -5.3, 3.6], index=['d', 'b', 'a', 'c'])
输出:
d    4.5
b    7.2
a   -5.3
c    3.6
dtype: float64

设置值,自动补全:

obj2 = obj.reindex(['a', 'b', 'c', 'd', 'e'])
输出: 
a   -5.3
b    7.2
c    3.6
d    4.5
e    NaN
dtype: float64

根据前面一个值补全:

obj3 = pd.Series(['blue', 'purple', 'yellow'], index=[0, 2, 4])
输出: 
0      blue
2    purple
4    yellow
dtype: object

obj3.reindex(range(6), method='ffill')
输出: 
0      blue
1      blue
2    purple
3    purple
4    yellow
5    yellow
dtype: object

删除指定值:

obj = pd.Series(np.arange(5.), index=['a', 'b', 'c', 'd', 'e'])
输出: 
a    0.0
b    1.0
c    2.0
d    3.0
e    4.0
dtype: float64

删除c以及对应值:

new_obj = obj.drop('c')
输出: 
a    0.0
b    1.0
d    3.0
e    4.0
dtype: float64

删除d以及对应值、删除c以及对应值:

obj.drop(['d', 'c'])
输出: 
a    0.0
b    1.0
e    4.0
dtype: float64

索引选取和过滤:

obj = pd.Series(np.arange(4.), index=['a', 'b', 'c', 'd'])
输出: 
a    0.0
b    1.0
c    2.0
d    3.0
dtype: float64

obj['b']
输出: 1.0

obj[1]
输出: 1.0

obj[2:4]
输出: 
c    2.0
d    3.0
dtype: float64

obj[['b', 'a', 'd']]
输出:
b    1.0
a    0.0
d    3.0
dtype: float64

obj[[1, 3]]
输出: 
b    1.0
d    3.0
dtype: float64

obj[obj < 2]
输出: 
a    0.0
b    1.0
dtype: float64 

用loc和iloc进行选取

data = pd.DataFrame(np.arange(16).reshape((4, 4)),index=['Ohio', 'Colorado', 'Utah', 'New York'],columns=['one', 'two', 'three', 'four'])
输出:          one  two  three  four
Ohio        0    1      2     3
Colorado    4    5      6     7
Utah        8    9     10    11
New York   12   13     14    15
     
data.loc['Colorado', ['two', 'three']]
输出: 
two      5
three    6
Name: Colorado, dtype: int64


data.iloc[2, [3, 0, 1]]
输出: 
four    11
one      8
two      9
Name: Utah, dtype: int64


data.loc[:'Utah', 'two']
输出: 
Ohio        0
Colorado    5
Utah        9
Name: two, dtype: int64

data.iloc[:, :3][data.three > 5]
输出: 
          one  two  three
Colorado    0    5      6
Utah        8    9     10
New York   12   13     14

运算:

s1 = pd.Series([7.3, -2.5, 3.4, 1.5], index=['a', 'c', 'd', 'e'])
输出: 
a    7.3
c   -2.5
d    3.4
e    1.5
dtype: float64

s2 = pd.Series([-2.1, 3.6, -1.5, 4, 3.1],index=['a', 'c', 'e', 'f', 'g'])
输出: 
a   -2.1
c    3.6
e   -1.5
f    4.0
g    3.1
dtype: float64


s1 + s2
输出: 
a    5.2
c    1.1
d    NaN
e    0.0
f    NaN
g    NaN
dtype: float64 

排序和排名:

obj = pd.Series(range(4), index=['d', 'a', 'b', 'c'])
obj.sort_index()
输出:
a    1
b    2
c    3
d    0
dtype: int64

frame = pd.DataFrame(np.arange(8).reshape((2, 4)),index=['three', 'one'],columns=['d', 'a', 'b', 'c'])
frame.sort_index()
输出: 
       d  a  b  c
one    4  5  6  7
three  0  1  2  3

带有重复标签的轴索引:

obj = pd.Series(range(5), index=['a', 'a', 'b', 'b', 'c'])
输出: 
a    0
a    1
b    2
b    3
c    4
dtype: int64


obj.index.is_unique
输出:False

自计算:

In [230]: df = pd.DataFrame([[1.4, np.nan], [7.1, -4.5],[np.nan, np.nan], [0.75, -1.3]],index=['a', 'b', 'c', 'd'],columns=['one', 'two'])
输出: 
    one  two
a  1.40  NaN
b  7.10 -4.5
c   NaN  NaN
d  0.75 -1.3


df.sum()
输出: 
one    9.25
two   -5.80
dtype: float64

唯一值、值计数以及成员资格:

obj = pd.Series(['c', 'a', 'd', 'a', 'a', 'b', 'b', 'c', 'c'])
obj.value_counts()
输出: 
c    3
a    3
b    2
d    1
dtype: int64

基础讲解到此为止:代码示例中还增加了统计图的输出,大家可以拷贝下来到自己的机器上跑一边,多动动手就知道是什么意思了

代码示例:

# pandas和numpy常常结合在一起使用,导入numpy库
import numpy as np
# 导入pandas库
import pandas as pd
# 引入库matplotlib
import matplotlib.pyplot as plot


# 统计数据图(Display the image);
# plot.title(设置名字需要是英文)

# kind类型
# 'line':线形图,这是默认的图表类型。
# 'bar':条形图,垂直条形。
# 'barh':水平条形图。
# 'hist':直方图,用于展示数据分布。
# 'box':箱形图,用于显示数据的五数概括和异常值。
# 'kde' 或 'density':核密度估计图,用于估计连续随机变量的概率密度函数。
# 'area':区域图,显示随时间变化的数据趋势。
# 'pie':饼图,用于显示比例或组成。
# 'scatter':散点图,用于查看两个变量之间的关系。
# 'hexbin':六边形箱图,用于表示两个变量的分布密度。
# 'hist2d':二维直方图,类似于 hexbin,但使用矩形箱。
# 'contour' 或 'contourf':等高线图,用于显示三维数据的等高线。
# 'polar':极坐标图,适用于极坐标系中的数据。

S12 = pd.DataFrame({"name":['toms',"jays"],'age':[12,21]})
S12.plot(kind='pie', x='name', y='age')
plot.title("name-age")
plot.show()


#透视表
s17 = pd.DataFrame({'Year': ['2019', '2019', '2020', '2020'],
                      'Quarter': ['Q1', 'Q2', 'Q1', 'Q2'],
                      'Product': ['A', 'B', 'A', 'B'],
                      'Sales': [100, 200, 150, 250]})

#源数据
#      Year  Quarter  Product   Sales
# 0    2019    Q1       A         100
# 1    2019    Q2    B         200
# 2    2020    Q1       A         150
# 3    2020    Q2       B         250

# 创建透视表(index表示key,colums表示统计维度,values表示value,aggfunc: 聚合函数,用于处理重复的数据。常见的有sum、mean、count等)
pivot_table = s17.pivot_table(index='Year', columns='Quarter', values='Sales', aggfunc='sum')
# 打印透视表
print(f"透视表行维度:\n{pivot_table}")

# 透视表
# Quarter   Q1   Q2
# Year
# 2019     100  200
# 2020     150  250


# 计算交叉表(pd.crosstab,与piovt_table统计维度是列,cross_table统计维度是行,根据需求选择使用)
s18 = pd.DataFrame({
    'Sex': ['M', 'F', 'M', 'F', 'M', 'F', 'M', 'F'],
    'Smoker': ['Yes', 'No', 'Yes', 'No', 'Yes', 'No', 'No', 'Yes'],
    'HeartDisease': ['Yes', 'No', 'Yes', 'No', 'Yes', 'Yes', 'No', 'No']
})
print(f"透视表列表:\n{s18}")

#    Sex Smoker HeartDisease
# 0   M    Yes          Yes
# 1   F     No           No
# 2   M    Yes          Yes
# 3   F     No           No
# 4   M    Yes          Yes
# 5   F     No          Yes
# 6   M     No           No
# 7   F    Yes           No

s19 = pd.crosstab(s18['Sex'], s18['Smoker'], margins=True)
print(f"透视表列统计:\n{s19}")

# Smoker     No  Yes  All
# Sex                    
# F          1    1    2
# M          2    2    4
# All        3    3    6
相关推荐
Q_19284999065 分钟前
基于Spring Boot的摄影器材租赁回收系统
java·spring boot·后端
qq_433554546 分钟前
C++ 面向对象编程:+号运算符重载,左移运算符重载
开发语言·c++
良许Linux9 分钟前
0.96寸OLED显示屏详解
linux·服务器·后端·互联网
求知若饥22 分钟前
NestJS 项目实战-权限管理系统开发(六)
后端·node.js·nestjs
qq_5290252924 分钟前
Torch.gather
python·深度学习·机器学习
数据小爬虫@25 分钟前
如何高效利用Python爬虫按关键字搜索苏宁商品
开发语言·爬虫·python
ZJ_.27 分钟前
WPSJS:让 WPS 办公与 JavaScript 完美联动
开发语言·前端·javascript·vscode·ecmascript·wps
Narutolxy32 分钟前
深入探讨 Go 中的高级表单验证与翻译:Gin 与 Validator 的实践之道20241223
开发语言·golang·gin
Hello.Reader40 分钟前
全面解析 Golang Gin 框架
开发语言·golang·gin
禁默1 小时前
深入浅出:AWT的基本组件及其应用
java·开发语言·界面编程