在数据分析和处理过程中,numpy 和 pandas 经常一起使用。numpy 提供了高效的数值计算和数组操作功能,而 pandas 提供了方便的数据结构(如 DataFrame 和 Series)来处理表格数据。numpy 在一些情况下能优化 pandas 操作的性能,特别是涉及到条件判断、元素级操作时。
numpy 和 pandas 的关系:
pandas的底层实现基于numpy,因此它能够高效处理数值数据。pandas提供了更高层次的操作,简化了常见的数据处理任务,而numpy提供了基本的数值计算和数组操作功能。pandas中的Series和DataFrame其实都是基于numpy数组(ndarray)的封装。因此,许多pandas的操作可以通过numpy来实现,反之亦然。
使用 numpy 和 pandas 实现同样效果的例子
1. 使用 numpy 和 pandas 实现条件赋值
pandas 方法:
df_main.loc[df_main['value'] > 100, 'status'] = 'High'
df_main.loc[df_main['value'] <= 100, 'status'] = 'Low'
numpy 方法:
import numpy as np
df_main['status'] = np.where(df_main['value'] > 100, 'High', 'Low')
这里,numpy.where 简化了 pandas.loc 的操作,条件判断和赋值操作可以通过一行代码完成。
2. 使用 numpy 和 pandas 实现填充缺失值
pandas 方法:
df_main['value'] = df_main['value'].fillna(df_main['value'].mean())
numpy 方法:
import numpy as np
df_main['value'] = np.where(df_main['value'].isna(), df_main['value'].mean(), df_main['value'])
这里,numpy.where 根据条件(是否是缺失值)来填充数据,虽然 pandas.fillna 更简洁,但 numpy 也能实现类似的功能。
3. 使用 numpy 和 pandas 实现按条件更新多列
pandas 方法:
df_main.loc[df_main['categoryCode'] == 'A', ['price', 'quantity']] = [100, 10]
df_main.loc[df_main['categoryCode'] == 'B', ['price', 'quantity']] = [200, 20]
numpy 方法:
import numpy as np
df_main[['price', 'quantity']] = np.where(df_main['categoryCode'] == 'A', [100, 10], [200, 20])
numpy.where 在这种场景下的优势是可以同时更新多个列,避免了重复的 loc 操作。
4. 使用 numpy 和 pandas 实现对多个条件的处理
pandas 方法:
df_main.loc[(df_main['categoryCode'] == 'A') & (df_main['quantity'] > 10), 'status'] = 'Good'
df_main.loc[(df_main['categoryCode'] == 'B') & (df_main['quantity'] <= 10), 'status'] = 'Bad'
numpy 方法:
import numpy as np
df_main['status'] = np.select(
[ (df_main['categoryCode'] == 'A') & (df_main['quantity'] > 10),
(df_main['categoryCode'] == 'B') & (df_main['quantity'] <= 10) ],
['Good', 'Bad'],
default='Unknown'
)
在这种情况下,numpy.select 允许我们处理多个条件,并根据每个条件选择对应的值,比多次使用 pandas.loc 更加简洁。
numpy 和 pandas 在许多情况下可以实现相同的功能,特别是在数值计算、数组操作和数据处理等方面。虽然 pandas 更适用于表格数据(如 DataFrame 和 Series),而 numpy 则专注于数组操作,但它们有许多交集,尤其在数据清洗、统计计算和特征工程等场景中可以互换使用。
1. 计算列的均值、最大值、最小值等
使用 pandas:
# 计算某列的均值
df_main['mean_value'] = df_main['value'].mean()
# 计算某列的最大值
df_main['max_value'] = df_main['value'].max()
# 计算某列的最小值
df_main['min_value'] = df_main['value'].min()
使用 numpy:
import numpy as np
# 计算某列的均值
df_main['mean_value'] = np.mean(df_main['value'])
# 计算某列的最大值
df_main['max_value'] = np.max(df_main['value'])
# 计算某列的最小值
df_main['min_value'] = np.min(df_main['value'])
2. 元素级操作(如加减乘除等)
使用 pandas:
# 对某列进行加法操作
df_main['value_plus_10'] = df_main['value'] + 10
# 对某列进行乘法操作
df_main['value_times_2'] = df_main['value'] * 2
使用 numpy:
import numpy as np
# 对某列进行加法操作
df_main['value_plus_10'] = np.add(df_main['value'], 10)
# 对某列进行乘法操作
df_main['value_times_2'] = np.multiply(df_main['value'], 2)
3. 条件筛选(过滤)数据
使用 pandas:
# 使用 loc 筛选出 value 大于 100 的数据
df_filtered = df_main.loc[df_main['value'] > 100]
# 使用 loc 筛选出 value 小于等于 100 的数据
df_filtered = df_main.loc[df_main['value'] <= 100]
使用 numpy:
import numpy as np
# 使用 np.where 筛选出 value 大于 100 的数据
df_filtered = df_main[np.where(df_main['value'] > 100)]
# 使用 np.where 筛选出 value 小于等于 100 的数据
df_filtered = df_main[np.where(df_main['value'] <= 100)]
4. 缺失值填充
使用 pandas:
# 使用 pandas 填充缺失值
df_main['value'] = df_main['value'].fillna(df_main['value'].mean())
使用 numpy:
import numpy as np
# 使用 numpy 填充缺失值
df_main['value'] = np.nan_to_num(df_main['value'], nan=np.nanmean(df_main['value']))
5. 数据标准化/归一化(Min-Max Scaling)
使用 pandas:
# Min-Max Scaling using pandas
df_main['value_scaled'] = (df_main['value'] - df_main['value'].min()) / (df_main['value'].max() - df_main['value'].min())
使用 numpy:
import numpy as np
# Min-Max Scaling using numpy
df_main['value_scaled'] = np.divide(df_main['value'] - np.min(df_main['value']), np.max(df_main['value']) - np.min(df_main['value']))
6. 处理重复值
使用 pandas:
# 删除重复的行
df_main = df_main.drop_duplicates()
# 查找重复的行
duplicates = df_main[df_main.duplicated()]
使用 numpy:
import numpy as np
# 查找重复的行
_, indices = np.unique(df_main.values, axis=0, return_index=True)
df_main_no_duplicates = df_main.iloc[indices]
7. 计算累积和(Cumulative Sum)
使用 pandas:
# 计算某列的累积和
df_main['cumsum'] = df_main['value'].cumsum()
使用 numpy:
import numpy as np
# 计算某列的累积和
df_main['cumsum'] = np.cumsum(df_main['value'])
8. 合并数据(数据连接)
使用 pandas:
# 使用 pandas 进行连接(merge)
df_merged = pd.merge(df_main, df_other, on='key', how='left')
使用 numpy:
import numpy as np
# 使用 numpy 进行连接(concatenate)
df_merged = np.core.records.fromarrays([df_main['key'], df_other['value']], names='key,value')
9. 分类数据处理(如 one-hot 编码)
使用 pandas:
# 使用 pandas 进行 one-hot 编码
df_main = pd.get_dummies(df_main, columns=['categoryCode'], drop_first=True)
使用 numpy:
import numpy as np
# 使用 numpy 进行 one-hot 编码
categories = np.unique(df_main['categoryCode'])
one_hot = np.array([np.where(categories == x, 1, 0) for x in df_main['categoryCode']])
df_main_one_hot = pd.DataFrame(one_hot, columns=categories)
10. 使用 pandas 和 numpy 计算相关性
使用 pandas:
# 计算两列的皮尔逊相关系数
correlation = df_main['value'].corr(df_main['other_value'])
使用 numpy:
import numpy as np
# 计算两列的皮尔逊相关系数
correlation = np.corrcoef(df_main['value'], df_main['other_value'])[0, 1]
11. 生成随机数据
使用 pandas:
# 使用 pandas 生成随机数据(创建一个有随机数的 DataFrame)
df_random = pd.DataFrame(np.random.randn(100, 3), columns=['A', 'B', 'C'])
使用 numpy:
import numpy as np
# 使用 numpy 生成随机数据(创建一个有随机数的 DataFrame)
df_random = pd.DataFrame(np.random.randn(100, 3), columns=['A', 'B', 'C'])
(这里的 pandas 和 numpy 的方式其实是相同的,都是利用 numpy 生成随机数。)
总结:
pandas提供了更高层次的 API 来处理表格数据,尤其适合有列名和索引的数据结构(如DataFrame和Series)。numpy主要专注于高效的数值计算和数组操作,适用于没有明确列名或索引的矩阵或数组数据结构。- 在许多情况下,
numpy和pandas可以实现相同的功能,尤其是在数值计算、条件筛选、缺失值处理等方面,二者可以互换使用。 - 性能:在进行大规模数据处理时,
numpy的操作通常比pandas更高效,因为numpy直接操作底层数组,而pandas提供的高级功能会有一定的性能开销。
选择使用 pandas 或 numpy 取决于数据的结构、操作的复杂性和性能需求。如果是表格数据,pandas 更加方便;如果是大量的数值计算,numpy 可能更高效。
总结
-
pandas和numpy关系:pandas是基于numpy构建的,利用了numpy的高效数组处理能力。pandas提供了更高级的数据结构(如DataFrame和Series),使得数据处理更加方便,特别是与数据库或表格数据打交道时。numpy提供了底层的数值计算和数组操作,可以在处理大规模数值数据时提供更高的性能。
-
简化方法:
- 在进行条件赋值时,
numpy.where和pandas.loc都是常用的方式,但numpy.where可以简化代码并提升性能。 - 使用
numpy.select和apply等方法,可以进一步简化复杂条件的处理。
- 在进行条件赋值时,
通过这几种方法,你可以在 pandas 的基础上高效地处理数据,并且根据实际需求选择合适的工具。