当前位置: 首页 > news >正文

锂离子电池健康状态预测(Part1,Python)

所用数据集:Oxford
dataset:https://ora.ox.ac.uk/objects/uuid:03ba4b01-cfed-46d3-9b1a-7d4a7bdf6fac/files/m5ac36a1e2073852e4f1f7dee647909a7

# importing libraries
import matplotlib.pyplot as plt
import pandas as pd
import scipy.io
import math
import numpy as np
from scipy.ndimage import gaussian_filter1d , gaussian_filterfrom sktime.classification.feature_based import RandomIntervalClassifier
from sktime.performance_metrics.forecasting import mean_absolute_error,mean_absolute_percentage_error
from sktime.transformations.panel.padder import PaddingTransformer
# Time series Extraction with label(SoH), from Oxford dataset#import Oxford Dataset nad remove metadata
oxford_dataset = scipy.io.loadmat('dataset/Oxford/Oxford_Battery_Degradation_Dataset_1.mat', simplify_cells=True)
del oxford_dataset["__header__"]
del oxford_dataset["__version__"]
del oxford_dataset["__globals__"]# extraction of capacity q for every battery
capacity={}          
for ox_key, ox_value in oxford_dataset.items():capacity[ox_key] = []for value in ox_value:last = ox_value[value]['C1ch']['q'].shape[0] - 1capacity[ox_key].append(ox_value[value]['C1ch']['q'][last])# From capacity to SoH 
# SoH = q_k / q_0
y={}
for id_battery, values_battery in capacity.items():y[id_battery]=[]for key, value in enumerate(values_battery):y[id_battery].append(  capacity[id_battery][key] / capacity[id_battery][0] ) # CREO IL PANDA DATAFRAME#Crete a dictionary with this structure: {"num ciclo _ num batteria (id)": , "voltage (v)": , "temperature (T)": }
# For every multivariate time series, there is a label (the SoH)dict_oxford={}
for i, cell in enumerate(['Cell1','Cell2','Cell3','Cell4','Cell5','Cell6','Cell7','Cell8']):int_idch = 0for idch_key, idch_value in oxford_dataset[cell].items():dict_oxford[str(idch_key) + '_'+cell] = {'v' : pd.Series(idch_value['C1ch']['v']),'T' : pd.Series(idch_value['C1ch']['T']),'SoH' : round(y[cell][int_idch]*100)}int_idch += 1#from dict to dataframe 
df= pd.DataFrame.from_dict(dict_oxford).transpose()
df.head()

# divide dataframe into train set e validation setnp.random.seed(2)
msk = np.random.rand(len(df)) < 0.85x_train = df[msk]
y_train = x_train['SoH'].copy().astype('int')
x_train = x_train.drop(columns=['SoH'])x_test = df[~msk]
y_test = x_test['SoH'].copy().astype('int') 
x_test = x_test.drop(columns=['SoH'])print(x_train.shape, y_train.shape)
print(x_test.shape, y_test.shape)
(446, 2) (446,)
(73, 2) (73,)
padded_clf = PaddingTransformer() * RandomIntervalClassifier(n_intervals=5, random_state=1)
padded_clf.fit(x_train, y_train)y_pred = padded_clf.predict(x_test)

# plot "real vs pred" and metrics result MAEP = mean_absolute_percentage_error(y_test, y_pred)
MAE = mean_absolute_error(y_test, y_pred)
RMSE = np.sqrt(np.square(np.subtract(y_test,y_pred)).mean())plt.title(" SoH real vs pred")
plt.plot(y_test.values)
plt.plot( y_pred)
plt.show()print("MAEP = " + str(MAEP))
print("MAE = " + str(MAE))
print("RMSE = " + str(RMSE))

MAEP = 0.005482782571159821
MAE = 0.4657534246575342
RMSE = 0.6824612990181452
#PLOTTINGimport pandas as pd
import seaborn as sns
from matplotlib.ticker import MaxNLocator
import matplotlib.pyplot as pltreal_pred = {'real':y_test.values,'pred':y_pred
}
df_plot = pd.DataFrame(real_pred)colors = ["#F0741E", "#276CB3"]class_names = np.union1d(np.unique(df_plot['real']), (np.unique(df_plot['pred'])))g = sns.jointplot(x="pred", y="real", data=df_plot, kind="hist", marginal_kws={"color": colors[0], "bins":len(class_names)},joint_kws={"color": colors[1], "bins": len(class_names)} )g.ax_joint.tick_params(axis="both", which="major", labelsize=20)
ticks = np.arange(75, 100, 10)
labels = [f'{x}' for x in ticks]
g.ax_joint.set_xlim([min(class_names),max(class_names)])
#g.ax_joint.xaxis.set_major_locator(MaxNLocator(nbins=3))  # Auto tick locator
#g.ax_joint.yaxis.set_major_locator(MaxNLocator(nbins=3))  #
g.ax_joint.set_yticks(ticks,labels=labels)
g.ax_joint.set_xticks(ticks,labels=labels)g.set_axis_labels('SoH Predicted Value [%]', 'SoH True Value [%]' ,fontsize=20
)plt.savefig('plot/cell1_100_oxford_8515.png', dpi=300, bbox_inches="tight")

import numpy as np
import matplotlib.pyplot as plt# Genera un array di esempio di lunghezza 1000
data0000 = dict_oxford['cyc0000_Cell1']['T']# Calcola la media e la deviazione standard ogni 50 punti
window_size = 100
means0000 = []
std_devs0000 = []
for i in range(0, len(data0000), window_size):window = data0000[i:i + window_size]means0000.append(np.mean(window))std_devs0000.append(np.std(window))data1000 = dict_oxford['cyc1000_Cell1']['T']
# Calcola la media e la deviazione standard ogni 50 punti
window_size = 100
means1000 = []
std_devs1000 = []
for i in range(0, len(data1000), window_size):window = data1000[i:i + window_size]means1000.append(np.mean(window))std_devs1000.append(np.std(window))data3000 = dict_oxford['cyc3000_Cell1']['T']
# Calcola la media e la deviazione standard ogni 50 punti
window_size = 100
means3000 = []
std_devs3000 = []
for i in range(0, len(data3000), window_size):window = data3000[i:i + window_size]means3000.append(np.mean(window))std_devs3000.append(np.std(window))data5000 = dict_oxford['cyc5000_Cell1']['T']
# Calcola la media e la deviazione standard ogni 50 punti
window_size = 100
means5000 = []
std_devs5000 = []
for i in range(0, len(data5000), window_size):window = data5000[i:i + window_size]means5000.append(np.mean(window))std_devs5000.append(np.std(window))# Crea gli intervalli per l'asse x
x0000 = np.arange(0, len(data0000), window_size)
x1000 = np.arange(0, len(data1000), window_size)
x3000 = np.arange(0, len(data3000), window_size)
x5000 = np.arange(0, len(data5000), window_size)# Plot della media e della deviazione standard
plt.figure(figsize=(10, 5))
plt.errorbar(x0000, means0000, std_devs0000, linestyle='None', marker='^', label='SoH 100%' )
plt.errorbar(x1000, means1000, std_devs1000, linestyle='None', marker='^', label='SoH 92% ')
plt.errorbar(x3000, means3000, std_devs3000, linestyle='None', marker='^', label='SoH 85%' )
plt.errorbar(x5000, means5000, std_devs5000, linestyle='None', marker='^', label='SoH 80%')#plt.title('Media e Deviazione Standard Temperatura ogni 100 punti - Oxford Dataset')
plt.xlabel('Time of Charging [sec]',fontsize=16)
plt.ylabel('Temperature measured [°C]',fontsize=16)
plt.legend(fontsize=12)
plt.grid(True)
#plt.show()
plt.savefig('plot/Temperature_Measured_oxford.png', dpi=300, bbox_inches="tight")

# Genera un array di esempio di lunghezza 1000
data0000 = dict_oxford['cyc0000_Cell1']['v']
# Calcola la media e la deviazione standard ogni 50 punti
window_size = 100
means0000 = []
std_devs0000 = []
for i in range(0, len(data0000), window_size):window = data0000[i:i + window_size]means0000.append(np.mean(window))std_devs0000.append(np.std(window))data1000 = dict_oxford['cyc1000_Cell1']['v']
# Calcola la media e la deviazione standard ogni 50 punti
means1000 = []
std_devs1000 = []
for i in range(0, len(data1000), window_size):window = data1000[i:i + window_size]means1000.append(np.mean(window))std_devs1000.append(np.std(window))data3000 = dict_oxford['cyc3000_Cell1']['v']
# Calcola la media e la deviazione standard ogni 50 punti
means3000 = []
std_devs3000 = []
for i in range(0, len(data3000), window_size):window = data3000[i:i + window_size]means3000.append(np.mean(window))std_devs3000.append(np.std(window))data5000 = dict_oxford['cyc5000_Cell1']['v']
# Calcola la media e la deviazione standard ogni 50 punti
means5000 = []
std_devs5000 = []
for i in range(0, len(data5000), window_size):window = data5000[i:i + window_size]means5000.append(np.mean(window))std_devs5000.append(np.std(window))# Crea gli intervalli per l'asse x
x0000 = np.arange(0, len(data0000), window_size)
x1000 = np.arange(0, len(data1000), window_size)
x3000 = np.arange(0, len(data3000), window_size)
x5000 = np.arange(0, len(data5000), window_size)# Plot della media e della deviazione standard
plt.figure(figsize=(10, 5))
plt.errorbar(x0000, means0000, std_devs0000, linestyle='None', marker='^', label='SoH 100%' )
plt.errorbar(x1000, means1000, std_devs1000, linestyle='None', marker='^', label='SoH 92%')
plt.errorbar(x3000, means3000, std_devs3000, linestyle='None', marker='^', label='SoH 85%' )
plt.errorbar(x5000, means5000, std_devs5000, linestyle='None', marker='^', label='SoH 80%')#plt.title('Media e Deviazione Standard Voltage_measured ogni 200 misurazioni - Oxford Dataset')
plt.xlabel('Time of Charging [sec]',fontsize=16)
plt.ylabel('Voltage Measured [volt]',fontsize=16)
plt.legend(fontsize=12)
plt.grid(True)
plt.savefig('plot/Voltage_measured_Oxford.png', dpi=300, bbox_inches="tight")
plt.show()

# Genera un array di esempio di lunghezza 1000
data0000 = dict_oxford['cyc0000_Cell1']['q']
# Calcola la media e la deviazione standard ogni 50 punti
window_size = 200
means0000 = []
std_devs0000 = []
for i in range(0, len(data0000), window_size):window = data0000[i:i + window_size]means0000.append(np.mean(window))std_devs0000.append(np.std(window))data1000 = dict_oxford['cyc1000_Cell1']['q']
# Calcola la media e la deviazione standard ogni 50 punti
means1000 = []
std_devs1000 = []
for i in range(0, len(data1000), window_size):window = data1000[i:i + window_size]means1000.append(np.mean(window))std_devs1000.append(np.std(window))data3000 = dict_oxford['cyc3000_Cell1']['q']
# Calcola la media e la deviazione standard ogni 50 punti
means3000 = []
std_devs3000 = []
for i in range(0, len(data3000), window_size):window = data3000[i:i + window_size]means3000.append(np.mean(window))std_devs3000.append(np.std(window))data5000 = dict_oxford['cyc5000_Cell1']['q']
# Calcola la media e la deviazione standard ogni 50 punti
means5000 = []
std_devs5000 = []
for i in range(0, len(data5000), window_size):window = data5000[i:i + window_size]means5000.append(np.mean(window))std_devs5000.append(np.std(window))# Crea gli intervalli per l'asse x
x0000 = np.arange(0, len(data0000), window_size)
x1000 = np.arange(0, len(data1000), window_size)
x3000 = np.arange(0, len(data3000), window_size)
x5000 = np.arange(0, len(data5000), window_size)# Plot della media e della deviazione standard
plt.figure(figsize=(10, 5))
plt.errorbar(x0000, means0000, std_devs0000, linestyle='None', marker='^', label='0000' )
plt.errorbar(x1000, means1000, std_devs1000, linestyle='None', marker='^', label='1000')
plt.errorbar(x3000, means3000, std_devs3000, linestyle='None', marker='^', label='3000' )
plt.errorbar(x5000, means5000, std_devs5000, linestyle='None', marker='^', label='5000')plt.title('Media e Deviazione Standard q ogni 100 punti')
plt.xlabel('Time - Charging')
plt.ylabel('Quantity of Energy')
plt.legend()
plt.grid(True)
plt.show()

担任《Mechanical System and Signal Processing》审稿专家,担任《中国电机工程学报》,《控制与决策》等EI期刊审稿专家,擅长领域:现代信号处理,机器学习,深度学习,数字孪生,时间序列分析,设备缺陷检测、设备异常检测、设备智能故障诊断与健康管理PHM等。知乎学术咨询:https://www.zhihu.com/consult/people/792359672131756032?isMe=1

 

相关文章:

  • 北京网站建设多少钱?
  • 辽宁网页制作哪家好_网站建设
  • 高端品牌网站建设_汉中网站制作
  • Unity Shader unity文档学习笔记(十八):unity雾效原理
  • 算法板子:树形DP、树的DFS——树的重心
  • 除湿机的标准
  • 深入探究CSRF与SSRF漏洞复现:从原理到实践
  • 智能驾驶学习笔记,第一天
  • opencascade AIS_ViewCube源码学习小方块
  • Linux中栈的大小的修改
  • vue3+element-plus实现table表格整列的拖拽
  • 函数对象/仿函数
  • 【机器学习】逻辑回归的梯度下降以及在一变量数据集、两变量数据集下探索优化的梯度下降算法
  • 26.9 Django书籍管理练习
  • vue实现简易的全局加载动画效果
  • 2.回文数
  • Python使用内置logging模块打印日志
  • 主动学习实现领域自适应语义分割
  • 【笔记】你不知道的JS读书笔记——Promise
  • android百种动画侧滑库、步骤视图、TextView效果、社交、搜房、K线图等源码
  • Java到底能干嘛?
  • log4j2输出到kafka
  • Octave 入门
  • SpiderData 2019年2月16日 DApp数据排行榜
  • 机器人定位导航技术 激光SLAM与视觉SLAM谁更胜一筹?
  • 简单基于spring的redis配置(单机和集群模式)
  • 今年的LC3大会没了?
  • 普通函数和构造函数的区别
  • 前端性能优化——回流与重绘
  • 使用权重正则化较少模型过拟合
  • 运行时添加log4j2的appender
  • 东超科技获得千万级Pre-A轮融资,投资方为中科创星 ...
  • 智能情侣枕Pillow Talk,倾听彼此的心跳
  • ​LeetCode解法汇总2182. 构造限制重复的字符串
  • #1014 : Trie树
  • $分析了六十多年间100万字的政府工作报告,我看到了这样的变迁
  • (20)docke容器
  • (9)YOLO-Pose:使用对象关键点相似性损失增强多人姿态估计的增强版YOLO
  • (Demo分享)利用原生JavaScript-随机数-实现做一个烟花案例
  • (PHP)设置修改 Apache 文件根目录 (Document Root)(转帖)
  • (顶刊)一个基于分类代理模型的超多目标优化算法
  • (转)chrome浏览器收藏夹(书签)的导出与导入
  • .NET Core、DNX、DNU、DNVM、MVC6学习资料
  • .NET Standard 的管理策略
  • .Net 高效开发之不可错过的实用工具
  • .NET 解决重复提交问题
  • .NET精简框架的“无法找到资源程序集”异常释疑
  • @EnableAsync和@Async开始异步任务支持
  • [ Linux 长征路第五篇 ] make/Makefile Linux项目自动化创建工具
  • [ 云计算 | AWS 实践 ] 基于 Amazon S3 协议搭建个人云存储服务
  • [04]Web前端进阶—JS伪数组
  • [2013][note]通过石墨烯调谐用于开关、传感的动态可重构Fano超——
  • [2016.7 test.5] T1
  • [Angular] 笔记 20:NgContent
  • [C/C++] C/C++中数字与字符串之间的转换
  • [CTF]2022美团CTF WEB WP
  • [dts]Device Tree机制
  • [JAVA] 什么是Java线程同步机制?