Python数据科学生态:NumPy基础、Pandas基础、Matplotlib基础、Scikit-learn简介

各位同学好,我是老张。今天咱们聊聊Python数据科学生态里的四个核心库。说实话,这四样东西就像储能工程师的瑞士军刀——缺了哪把都不顺手。

我刚开始做储能数据分析那会儿,还傻乎乎地用Excel处理几万条电池充放电数据。结果呢?电脑卡死三次,我差点把咖啡泼键盘上。后来转用Python这套工具,才算是真正解放了生产力。

先给大家画个知识地图,看看这四个库到底怎么分工协作的:

Python数据科学生态系统 储能数据分析 NumPy 数值计算基础 Pandas 数据处理框架 Matplotlib 数据可视化 Scikit-learn 机器学习 数组运算、矩阵计算 数据清洗、聚合分析 曲线绘制、趋势展示 聚类、分类、回归 数据流方向:原始数据 → NumPy处理 → Pandas清洗 → Matplotlib可视化 → Scikit-learn建模

NumPy基础:一切计算的基石

NumPy,全称是Numerical Python。说白了,它就是Python里的数组计算引擎。我习惯叫它「数组界的瑞士军刀」。

为什么储能数据分析离不开NumPy?你想想看,一块电池的充放电数据,少说几千条,多则上百万条。用Python原生列表去算?那速度慢得能让你怀疑人生。

核心概念:ndarray(N维数组)

NumPy的核心就是ndarray对象。它比Python列表快几十倍,原因在于底层用C语言实现,而且支持向量化运算。

import numpy as np

# 创建一个一维数组
battery_voltages = np.array([3.7, 3.8, 3.9, 4.0, 4.1])
print(battery_voltages)

# 创建二维数组(模拟多块电池的电压数据)
battery_data = np.array([
    [3.7, 3.8, 3.9],
    [4.0, 4.1, 4.2],
    [3.6, 3.7, 3.8]
])
print(battery_data.shape)  # 输出:(3, 3)

我的小习惯:创建数组时,尽量指定dtype类型。比如np.array(data, dtype=np.float32)。这样能省内存,处理大数据时特别管用。

NumPy的向量化运算,是我最喜欢的特性。举个例子,你要计算所有电池电压的平均值,用原生Python得写循环,用NumPy一行搞定:

# 向量化运算示例
voltages = np.array([3.7, 3.8, 3.9, 4.0, 4.1])
mean_voltage = np.mean(voltages)  # 一行搞定
print(f"平均电压:{mean_voltage}V")

# 条件筛选(找出电压异常的电池)
abnormal = voltages[voltages < 3.8]
print(f"低压电池:{abnormal}")

我曾经在一个储能电站项目里,需要处理200万条电池温度数据。用原生Python跑了半小时没出结果,换成NumPy后,3秒搞定。嗯,这就是差距。

Pandas基础:数据处理的瑞士军刀

Pandas,说白了就是「Python界的Excel」。但它比Excel强太多了——能处理百万级数据,还能自动对齐索引。

我个人习惯把Pandas的DataFrame想象成一个电子表格。每一列是一个Series,整个表是一个DataFrame。这样理解起来特别直观。

import pandas as pd

# 创建DataFrame(模拟电池充放电数据)
data = {
    '电池编号': ['B001', 'B002', 'B003', 'B004'],
    '电压(V)': [3.85, 3.92, 3.78, 4.01],
    '电流(A)': [10.5, 9.8, 11.2, 8.9],
    '温度(°C)': [25.3, 26.1, 24.8, 27.0],
    'SOC(%)': [85, 92, 78, 95]
}
df = pd.DataFrame(data)
print(df)

注意:Pandas读取CSV文件时,如果文件编码不是UTF-8,记得指定encoding参数。我吃过这个亏,读了一堆乱码数据,排查了半天才发现是编码问题。

数据清洗是Pandas的强项。我经常遇到电池数据里有空值或者异常值,用Pandas处理起来特别顺手:

# 检查缺失值
print(df.isnull().sum())

# 填充缺失值(用均值填充)
df['电压(V)'].fillna(df['电压(V)'].mean(), inplace=True)

# 删除重复行
df.drop_duplicates(inplace=True)

# 条件筛选(找出温度过高的电池)
high_temp = df[df['温度(°C)'] > 26]
print(f"温度异常电池:\n{high_temp}")

分组聚合也是家常便饭。比如按电池型号统计平均电压:

# 假设有型号列
# df.groupby('型号')['电压(V)'].mean()

# 实际项目中,我经常这样分析不同批次的电池一致性
batch_stats = df.groupby('电池编号').agg({
    '电压(V)': ['mean', 'std'],
    '温度(°C)': 'max'
})
print(batch_stats)

Matplotlib基础:让数据说话

数据不可视化,就像电池没有BMS——你根本不知道里面发生了什么。Matplotlib就是Python里最经典的可视化工具。

我刚开始用Matplotlib时,总觉得画出来的图丑。后来发现,只要掌握几个核心参数,就能画出专业级的图表。

import matplotlib.pyplot as plt

# 设置中文字体(解决乱码问题)
plt.rcParams['font.sans-serif'] = ['SimHei']
plt.rcParams['axes.unicode_minus'] = False

# 绘制电池充放电曲线
time = np.arange(0, 10, 0.1)
voltage = 3.7 + 0.3 * np.sin(time * 0.5)  # 模拟充放电

plt.figure(figsize=(10, 6))
plt.plot(time, voltage, 'b-', linewidth=2, label='电压曲线')
plt.xlabel('时间 (h)')
plt.ylabel('电压 (V)')
plt.title('电池充放电电压曲线')
plt.grid(True, alpha=0.3)
plt.legend()
plt.show()

避坑指南:我曾经在画多子图时,忘记调用plt.tight_layout(),结果标签重叠在一起,被领导批评「图都画不清楚」。现在每次画图,我都会加上这一行。

实际项目中,我经常用Matplotlib做对比分析。比如比较不同电池的SOC-OCV曲线:

# 多曲线对比
soc = np.array([0, 20, 40, 60, 80, 100])
ocv_battery1 = np.array([3.0, 3.3, 3.6, 3.8, 3.95, 4.1])
ocv_battery2 = np.array([2.9, 3.2, 3.5, 3.7, 3.9, 4.05])

plt.figure(figsize=(8, 5))
plt.plot(soc, ocv_battery1, 'ro-', label='电池A')
plt.plot(soc, ocv_battery2, 'bs--', label='电池B')
plt.xlabel('SOC (%)')
plt.ylabel('OCV (V)')
plt.title('SOC-OCV曲线对比')
plt.legend()
plt.grid(True, linestyle='--', alpha=0.6)
plt.show()

Scikit-learn简介:机器学习的入门利器

Scikit-learn,简称sklearn,是Python里最友好的机器学习库。为什么说它友好?因为API设计得特别统一——fit、predict、transform,三件套走天下。

在储能领域,我主要用它做两件事:聚类分析和异常检测。比如根据电池的电压、内阻、容量等特征,把电池分成不同的健康等级。

from sklearn.cluster import KMeans
from sklearn.preprocessing import StandardScaler
import numpy as np

# 模拟电池特征数据
battery_features = np.array([
    [3.8, 0.05, 95],   # 电压, 内阻, 容量
    [3.9, 0.04, 98],
    [3.7, 0.08, 85],
    [4.0, 0.03, 100],
    [3.6, 0.12, 70]
])

# 标准化(重要!不同量纲的特征需要统一尺度)
scaler = StandardScaler()
features_scaled = scaler.fit_transform(battery_features)

# KMeans聚类(分成3类)
kmeans = KMeans(n_clusters=3, random_state=42)
labels = kmeans.fit_predict(features_scaled)

print(f"聚类结果:{labels}")
# 输出:[0 0 1 0 2] 表示第3块和第5块电池属于不同类别

核心要点:Scikit-learn的标准化步骤不能省。我见过太多人直接拿原始数据跑聚类,结果因为电压和容量的量纲差异太大,聚类效果一塌糊涂。

除了聚类,分类和回归也很常用。比如预测电池的剩余寿命(RUL):

from sklearn.linear_model import LinearRegression
from sklearn.model_selection import train_test_split

# 假设有历史数据
X = np.array([[100], [200], [300], [400], [500]])  # 循环次数
y = np.array([95, 90, 85, 80, 75])  # 容量保持率

# 划分训练集和测试集
X_train, X_test, y_train, y_test = train_test_split(
    X, y, test_size=0.2, random_state=42
)

# 训练线性回归模型
model = LinearRegression()
model.fit(X_train, y_train)

# 预测
pred = model.predict(X_test)
print(f"预测容量保持率:{pred}")

注意:Scikit-learn的模型默认参数不一定适合你的数据。我建议每次建模前,先看看数据分布,再选择合适的算法和参数。别偷懒,调参是必经之路。

好了,这四个库的基础就讲到这里。NumPy管计算,Pandas管数据,Matplotlib管展示,Scikit-learn管建模。四者配合,储能数据分析的活基本都能拿下。

记住,工具是死的,思路是活的。多动手敲代码,多拿真实数据练手,比看一百遍教程都管用。


专注资料整理