import sys import numpy as np import pandas as pd import string import os from pandas import Series from matplotlib import pyplot as plt from pandas.core.frame import DataFrame from pandas.core.indexes.base import Index from LIB.BACKEND import DBManager import datetime import time import string class SamplingSafty: def __init__(self): pass def main(sn,param,bms_info,df_Diag_Ram_in): df_Diag_Ram_Update_inside=DataFrame(columns=['start_time', 'end_time', 'product_id', 'code', 'level', 'info','advice']) df_Diag_Ram_Update_inside=df_Diag_Ram_Update_inside.append(df_Diag_Ram_in) global QuitErrCount FltInfo=DataFrame(columns=['start_time', 'end_time', 'product_id', 'code', 'level', 'info','advice']) VolStarkCount=[0 for i in range(param.CellVoltNums)] VolCount=[0 for i in range(param.CellVoltNums)] QuitErrCount=[0 for i in range(param.FaultCount)] #--------------该电池的所有当前故障------------- for i in range(0,len(bms_info)): if i==0: bms_infoP=bms_info.loc[i] elif len(bms_info)>=1: bms_infoP=bms_info.loc[i-1] df_Diag_Ram,VolStarkCount,VolCount=SamplingSafty.VoltSamplingDiag(sn,bms_info.loc[i],bms_infoP,param,VolStarkCount,VolCount,df_Diag_Ram_Update_inside) df_Diag_Ram=SamplingSafty.TempSamplingDiag(sn,bms_info.loc[i],bms_infoP,param,df_Diag_Ram) # FltInfo=SamplingSafty.CrntSamplingDiag(sn,bms_info.loc[i],FltInfo,param) return df_Diag_Ram def VoltSamplingDiag(sn,bms_infoN,bms_infoP,param,VolStarkCount,VolCount,df_Diag_Ram): InVMaxBatNo=[] InVMinBatNo=[] StackVolNo=[] OutlierVolNo=[] maxVolt=0 minVolt=5 ErrorFlg=0 TotalVol=0 #——————————————————————取最高最低电压———————————————————————————————— for t in range(0,param.CellVoltNums): BatNo=['单体电压'+str(t+1)] maxVol=max(maxVolt,float(bms_infoN[BatNo])/1000) if maxVol>maxVolt: MaxBatNo=t+1 maxVolt=maxVol if float(bms_infoN[BatNo])/1000>param.CellOVlmt: InVMaxBatNo.append(t+1) else: pass minVol=min(minVolt,float(bms_infoN[BatNo])/1000) if minVolparam.CellOVlmt: if minVol6: end_time=datetime.datetime.now() end_time=end_time.strftime('%Y-%m-%d %H:%M:%S') df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['code']==10].index,['end_time']]=end_time else: pass else: pass if not 50 in df_Diag_Ram['code'].values.tolist(): df_Diag_Ram.loc[len(df_Diag_Ram)]=[bms_infoN['时间戳'],'0000-00-00 00:00:00',sn,50,3,str(InVMaxBatNo)+'号电压大于{:.2f}V,采样无效'.format(param.CellOVlmt),'返厂维修'] ErrorFlg=1 else: pass elif minVol6: end_time=datetime.datetime.now() end_time=end_time.strftime('%Y-%m-%d %H:%M:%S') df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['code']==50].index,['end_time']]=end_time else: pass else: pass #——————————————————————————————————电压卡滞判断————————————————————————— if ErrorFlg==0: for t in range(0,param.CellVoltNums): BatNo=['单体电压'+str(t+1)] AvgVolGap=abs((float(bms_infoN[BatNo]/1000))-AvgVol) if AvgVolGap>param.AvgVolGap and float(bms_infoN[BatNo]/1000)>param.BLVol and float(bms_infoN[BatNo]/1000)10: OutlierVolNo.append(t+1) else: pass if abs(float(bms_infoN[BatNo])-float(bms_infoP[BatNo]))<=0.0001 and not 52 in df_Diag_Ram['code']: if abs(float(bms_infoN['总电流[A]']))>=10 and not 'PK504' in sn: VolStarkCount[t]=VolStarkCount[t]+1 elif abs(float(bms_infoN['总电流[A]']))>=15 and 'PK504' in sn: VolStarkCount[t]=VolStarkCount[t]+1 else: VolStarkCount[t]=0 if VolStarkCount[t]>10: StackVolNo.append(t+1) else: pass if len(OutlierVolNo)>0: QuitErrCount[51]=0 if not 51 in df_Diag_Ram['code'].values.tolist():#如果故障发生当前故障中没有该故障,则压入该故障 df_Diag_Ram.loc[len(df_Diag_Ram)]=[bms_infoN['时间戳'],'0000-00-00 00:00:00',sn,51,2,str(OutlierVolNo)+'号电池电压离群','技术介入诊断'] ErrorFlg=1 else:#如果故障发生当前故障中有该故障,则不进行操作 pass else: if 51 in df_Diag_Ram['code'].values.tolist(): QuitErrCount[51]=QuitErrCount[51]+1 if QuitErrCount[51]>6: end_time=datetime.datetime.now() end_time=end_time.strftime('%Y-%m-%d %H:%M:%S') df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['code']==51].index,['end_time']]=end_time else: pass else: pass if len(StackVolNo)>0: QuitErrCount[52]=0 if not 52 in df_Diag_Ram['code'].values.tolist():#如果故障发生当前故障中没有该故障,则压入该故障 df_Diag_Ram.loc[len(df_Diag_Ram)]=[bms_infoN['时间戳'],'0000-00-00 00:00:00',sn,52,2,str(StackVolNo)+'号电池电压卡滞','技术介入诊断'] ErrorFlg=1 else:#如果故障发生当前故障中有该故障,则不进行操作 pass else: if 51 in df_Diag_Ram['code'].values.tolist(): QuitErrCount[52]=QuitErrCount[52]+1 if QuitErrCount[52]>6: end_time=datetime.datetime.now() end_time=end_time.strftime('%Y-%m-%d %H:%M:%S') df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['code']==52].index,['end_time']]=end_time else: pass else: pass return df_Diag_Ram,VolStarkCount,VolCount def TempSamplingDiag(sn,bms_infoN,bms_infoP,param,df_Diag_Ram): #——————————————————————————————————CellTemp———————————————————————————————————— InVMaxBatNo=[] InVMinBatNo=[] OutlierTempNo=[] maxCellTempt=-40 minCellTempt=55 ErrorFlg=0 TotalCellTemp=0 for t in range(0,param.CellTempNums): BatNo=['单体温度'+str(t+1)] maxCellTemp=max(maxCellTempt,float(bms_infoN[BatNo])) if maxCellTemp>maxCellTempt: MaxBatNo=t+1 maxCellTempt=maxCellTemp if float(bms_infoN[BatNo])>param.PackOTlmt: InVMaxBatNo.append(t+1) else: pass minCellTemp=min(minCellTempt,float(bms_infoN[BatNo])) if minCellTemp2: AvgCellTemp=(TotalCellTemp-maxCellTemp-minCellTemp)/float(param.CellTempNums-2) else: AvgCellTemp=TotalCellTemp/float(param.CellTempNums) #——————————————————————————————————温度无效,离群和断线判断—————————————————————————————————— if maxCellTemp>param.PackOTlmt: if minCellTemp6: end_time=datetime.datetime.now() end_time=end_time.strftime('%Y-%m-%d %H:%M:%S') df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['code']==53].index,['end_time']]=end_time else: pass else: pass if not 2 in df_Diag_Ram['code'].values.tolist(): df_Diag_Ram.loc[len(df_Diag_Ram)]=[bms_infoN['时间戳'],'0000-00-00 00:00:00',sn,2,3,str(InVMaxBatNo)+'号温度大于{}℃,采样无效'.format(param.PackOTlmt),'返厂维修'] ErrorFlg=1 else: pass elif minCellTemp6: end_time=datetime.datetime.now() end_time=end_time.strftime('%Y-%m-%d %H:%M:%S') df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['code']==2].index,['end_time']]=end_time else: pass else: pass if ErrorFlg==0: if param.CellTempNums>2: for t in range(0,param.CellTempNums): BatNo=['单体温度'+str(t+1)] AvgCellTempGap=abs((float(bms_infoN[BatNo]))-AvgCellTemp) if AvgCellTempGap>param.AvgCellTempGap and float(bms_infoN[BatNo])>param.PackUTlmt and float(bms_infoN[BatNo])param.AvgCellTempGap and minCellTemp>param.PackUTlmt and maxCellTemp0: QuitErrCount[8]=0 if not 8 in df_Diag_Ram['code'].values.tolist():#如果故障发生当前故障中没有该故障,则压入该故障 df_Diag_Ram.loc[len(df_Diag_Ram)]=[bms_infoN['时间戳'],'0000-00-00 00:00:00',sn,8,2,str(OutlierTempNo)+'号电池异常温度离群','技术介入诊断'] ErrorFlg=1 else:#如果故障发生当前故障中有该故障,则不进行操作 pass else: if 8 in df_Diag_Ram['code'].values.tolist(): QuitErrCount[8]=QuitErrCount[8]+1 if QuitErrCount[8]>6: end_time=datetime.datetime.now() end_time=end_time.strftime('%Y-%m-%d %H:%M:%S') df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['code']==8].index,['end_time']]=end_time #df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['sn']==sn and df_Diag_Ram['code']==8].index,['end_time']]=end_time else: pass else: pass #——————————————————————————————————OtherTemp———————————————————————————————————— InVMaxOtherTempBatNo=[] InVMinOtherTempBatNo=[] OutlierOtherTempNo=[] maxOtherTempt=-40 minOtherTempt=91 ErrorFlg=0 TotalOtherTemp=0 MaxOtherBatNo=0 MinOtherBatNo=0 if param.OtherTempNums>0: for t in range(0,param.OtherTempNums): BatNo=['其他温度'+str(t+1)] maxOtherTemp=max(maxOtherTempt,float(bms_infoN[BatNo])) if maxOtherTemp>maxOtherTempt: MaxOtherBatNo=t+1 maxOtherTempt=maxOtherTemp if float(bms_infoN[BatNo])>param.OtherOTlmt: InVMaxOtherTempBatNo.append(t+1) else: pass minOtherTemp=min(minOtherTempt,float(bms_infoN[BatNo])) if minOtherTemp2: AvgOtherTemp=(TotalOtherTemp-maxOtherTemp-minOtherTemp)/float(param.OtherTempNums-2) else: AvgOtherTemp=TotalOtherTemp/float(param.OtherTempNums) #——————————————————————————————————其他温度无效,离群和断线判断—————————————————————————————————— if maxOtherTemp>param.OtherOTlmt: if minOtherTemp6: end_time=datetime.datetime.now() end_time=end_time.strftime('%Y-%m-%d %H:%M:%S') df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['code']==54].index,['end_time']]=end_time else: pass else: pass if not 55 in df_Diag_Ram['code'].values.tolist(): df_Diag_Ram.loc[len(df_Diag_Ram)]=[bms_infoN['时间戳'],'0000-00-00 00:00:00',sn,55,3,str(InVMaxOtherTempBatNo)+'号传感器温度大于{}℃,采样无效'.format(param.OtherOTlmt),'联系用户核实电池情况,并返厂维修'] ErrorFlg=1 else: pass elif minOtherTemp6: end_time=datetime.datetime.now() end_time=end_time.strftime('%Y-%m-%d %H:%M:%S') df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['code']==55].index,['end_time']]=end_time else: pass else: pass if ErrorFlg==0 and param.OtherTempNums>0: if param.OtherTempNums>2: for t in range(0,param.OtherTempNums): BatNo=['其他温度'+str(t+1)] AvgOtherTempGap=abs((float(bms_infoN[BatNo]))-AvgOtherTemp) if AvgOtherTempGap>param.AvgOtherTempGap and float(bms_infoN[BatNo])>param.OtherUTlmt and float(bms_infoN[BatNo])param.AvgOtherTempGap and minOtherTemp>param.OtherUTlmt and maxOtherTemp0: QuitErrCount[56]=0 if not 56 in df_Diag_Ram['code'].values.tolist():#如果故障发生当前故障中没有该故障,则压入该故障 df_Diag_Ram.loc[len(df_Diag_Ram)]=[bms_infoN['时间戳'],'0000-00-00 00:00:00',sn,56,2,str(OutlierOtherTempNo)+'号传感器温度异常离群','技术介入诊断'] ErrorFlg=1 else:#如果故障发生当前故障中有该故障,则不进行操作 pass else: if 56 in df_Diag_Ram['code'].values.tolist(): QuitErrCount[56]=QuitErrCount[56]+1 if QuitErrCount[56]>6: end_time=datetime.datetime.now() end_time=end_time.strftime('%Y-%m-%d %H:%M:%S') df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['code']==56].index,['end_time']]=end_time if (maxOtherTemp-maxCellTemp)>param.AvgOtherTempGap and maxOtherTemp6: end_time=datetime.datetime.now() end_time=end_time.strftime('%Y-%m-%d %H:%M:%S') df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['code']==56].index,['end_time']]=end_time if (maxCellTemp-maxOtherTemp)>param.AvgOtherTempGap and maxOtherTemp6: end_time=datetime.datetime.now() end_time=end_time.strftime('%Y-%m-%d %H:%M:%S') df_Diag_Ram.loc[df_Diag_Ram[df_Diag_Ram['code']==8].index,['end_time']]=end_time return df_Diag_Ram