@@ -48,8 +48,9 @@ public class WaveFileComponent {
ComtradeCfgDTO comtradeCfgDTO = getComtradeCfg ( cfgStream ) ;
// 为空或者未找到结束符号
if ( comtradeCfgDTO = = null | | ! " BINARY " . equalsIgnoreCase ( comtradeCfgDTO . getStrBinType ( ) ) ) {
return waveDataDTO ;
throw new BusinessException ( WaveFileResponseEnum . CFG_DATA_ERROR ) ;
}
/*****根据通道号计算相别** add by yexb -----Start****
* 1、判断是否是3的倍数, 是3的倍数则是3相
* 2、假如不是3的倍数 , 是1的倍数则是单相
@@ -59,16 +60,22 @@ public class WaveFileComponent {
} else {
comtradeCfgDTO . setNPhasic ( 1 ) ;
}
// 给相别幅值
// 给相别数量赋值
waveDataDTO . setIPhasic ( comtradeCfgDTO . getNPhasic ( ) ) ;
// 组装解析抬头
getWaveTitle ( waveDataDTO , comtradeCfgDTO ) ;
getWaveTitle ( waveDataDTO , comtradeCfgDTO ) ;
// 解析.dat文件
List < List < Float > > listWaveData = getComtradeDat ( comtradeCfgDTO , datStream , iType ) ;
waveDataDTO . setComtradeCfgDTO ( comtradeCfgDTO ) ;
waveDataDTO . setListWaveData ( listWaveData ) ;
//add by hongawen,将暂态触发起始时间记录下来
waveDataDTO . setTime ( DateUtil . format ( comtradeCfgDTO . getFirstTim e ( ) , DatePattern . NORM_DATETIME_PATTERN ) . concat ( StrPool . DOT ) + comtradeCfgDTO . getFirstMs ( ) );
waveDataDTO . setTime ( DateUtil . format ( comtradeCfgDTO . getTimeTrig e ( ) , DatePattern . NORM_DATETIME_MS_ PATTERN ) ) ;
/*****根据通道号计算相别** add by yexb -----end****/
return waveDataDTO ;
@@ -298,7 +305,7 @@ public class WaveFileComponent {
// 瞬时波形值
List < List < Float > > lstWave = waveDataDTO . getListWaveData ( ) ;
//获取最终采样率
Long finalSampleRate = comtradeCfgDTO . getFinalSampleRate ( ) ;
int finalSampleRate = comtradeCfgDTO . getFinalSampleRate ( ) ;
// 返回值
List < EigenvalueDTO > lstEigenvalueDTO = new ArrayList < > ( ) ;
@@ -321,7 +328,7 @@ public class WaveFileComponent {
* @author hongawen
* @date 2023/3/3 14:03
*/
public InputStream getFileInputStreamByFilePath ( String filePath ) {
public InputStream getFileInputStreamByFilePath ( String filePath ) {
File file = new File ( filePath ) ;
if ( file . isFile ( ) & & file . exists ( ) ) {
InputStream inputStream ;
@@ -346,41 +353,25 @@ public class WaveFileComponent {
**********************************/
private ComtradeCfgDTO getComtradeCfg ( InputStream cfgStream ) {
ComtradeCfgDTO comtradeCfgDTO = new ComtradeCfgDTO ( ) ;
InputStreamReader read = null ;
BufferedReader bufferedReader = null ;
try {
// 将.cfg文件转换为管道流
read = new InputStreamReader ( cfgStream , CharsetUtil . CHARSET_GBK ) ;
bufferedReader = new BufferedReader ( read ) ;
//WW 2019-11-14
float nFreq ;
try (
InputStreamReader read = new InputStreamReader ( cfgStream , CharsetUtil . CHARSET_GBK ) ;
BufferedReader bufferedReader = new BufferedReader ( read ) ;
) {
// 第一行不关心仅仅是一些描述类的信息
String strFileLine = bufferedReader . readLine ( ) ;
// 第二行需要关心第二个(模拟量的个数)和第三个参数(开关量的个数)
strFileLine = bufferedReader . readLine ( ) ;
// 按“,”进行分割
String [ ] strTempArray = strFileLine . split ( StrUtil . COMMA ) ;
// 按“,”进行分割
for ( int i = 0 ; i < strTempArray . length ; i + + ) {
switch ( i ) {
// 总个数
case 0 :
comtradeCfgDTO . setNChanne lNum ( Integer . parseInt ( strTempArray [ i ] ) ) ;
break ;
// 模拟量的个数
case 1 :
comtradeCfgDTO . setNAnalogNum ( Integer . parseInt ( strTempArray [ i ] . substring ( 0 , strTempArray [ i ] . length ( ) - 1 ) ) ) ;
break ;
// 开关量的个数
case 2 :
comtradeCfgDTO . setNDigitalNum ( Integer . parseInt ( strTempArray [ i ] . substring ( 0 , strTempArray [ i ] . length ( ) - 1 ) ) ) ;
break ;
default :
break ;
}
}
// 总个数
comtradeCfgDTO . setNChannelNum ( Integer . parseInt ( strTempArray [ 0 ] ) ) ;
// 模拟量的个数
comtradeCfgDTO . setNAnalogNum ( Integer . parseInt ( strTempArray [ 1 ] . substring ( 0 , strTempArray [ 1 ] . length ( ) - 1 ) ) ) ;
// 开关量的个数
comtradeCfgDTO . setNDigita lNum ( Integer . parseInt ( strTempArray [ 2 ] . substring ( 0 , strTempArray [ 2 ] . length ( ) - 1 ) ) ) ;
// 从第三行到第 ComtradeCfg.nChannelNum + 3 行是模拟量通道和数字量通道
// 从第三行开始的 ComtradeCfg.nChannelNum行是模拟量通道和数字量通道
List < AnalogDTO > lstAnalogDTO = new ArrayList < > ( ) ;
comtradeCfgDTO . setLstAnalogDTO ( lstAnalogDTO ) ;
for ( int i = 0 ; i < comtradeCfgDTO . getNChannelNum ( ) ; i + + ) {
@@ -388,104 +379,76 @@ public class WaveFileComponent {
lstAnalogDTO . add ( analogDTO ) ;
strFileLine = bufferedReader . readLine ( ) ;
strTempArray = strFileLine . split ( StrUtil . COMMA ) ;
// 配置总共13项
for ( int j = 0 ; j < strTempArray . length ; j + + ) {
switch ( j ) {
// 通道序号
case 0 :
analogDTO . setNIndex ( Integer . parseInt ( strTempArray [ j ] ) ) ;
break ;
// 通道名称
case 1 :
analogDTO . setSzChannle Name ( strTempArray [ j ] ) ;
break ;
// 相位名称
case 2 :
analogDTO . setSzPhasicName ( strTempArray [ j ] ) ;
break ;
// 监视的通道名称
case 3 :
analogDTO . setSzMonitoredChannleName ( strTempArray [ j ] ) ;
break ;
// 通道的单位
case 4 :
analogDTO . setSzUnitName ( strTempArray [ j ] ) ;
break ;
// 通道的系数
case 5 :
analogDTO . setFCoefficent ( Float . parseFloat ( strTempArray [ j ] ) ) ;
break ;
// 通道的偏移量
case 6 :
analogDTO . setFOffset ( Float . parseFloat ( strTempArray [ j ] ) ) ;
break ;
// 起始采样时间的偏移量
case 7 :
analogDTO . setFTimeOffset ( Float . parseFloat ( strTempArray [ j ] ) ) ;
break ;
// 采样值的最小值
case 8 :
analogDTO . setNMin ( Integer . parseInt ( strTempArray [ j ] ) ) ;
break ;
// 采样值的最大值
case 9 :
analogDTO . setNMax ( Integer . parseInt ( strTempArray [ j ] ) ) ;
break ;
// 一次变比
case 10 :
analogDTO . setFPrimary ( Float . parseFloat ( strTempArray [ j ] ) ) ;
break ;
// 二次变比
case 11 :
analogDTO . setFSecondary ( Float . parseFloat ( strTempArray [ j ] ) ) ;
break ;
// 一次值还是二次值标志
case 12 :
analogDTO . setSzValueType ( strTempArray [ j ] ) ;
break ;
default :
break ;
}
}
//通道序号
analogDTO . setNIndex ( Integer . parseInt ( strTempArray [ 0 ] ) ) ;
// 通道名称
analogDTO . setSzChannleName ( strTempArray [ 1 ] ) ;
// 相位名称
analogDTO . setSzPhasicName ( strTempArray [ 2 ] ) ;
// 监视的通道名称
analogDTO . setSzMonitoredChannleName ( strTempArray [ 3 ] ) ;
// 通道的单位
analogDTO . setSzUnit Name ( strTempArray [ 4 ] ) ;
// 通道的系数
analogDTO . setFCoefficent ( Float . parseFloat ( strTempArray [ 5 ] ) ) ;
// 通道的偏移量
analogDTO . setFOffset ( Float . parseFloat ( strTempArray [ 6 ] ) ) ;
// 起始采样时间的偏移量
analogDTO . setFTimeOffset ( Float . parseFloat ( strTempArray [ 7 ] ) ) ;
// 采样值的最小值
analogDTO . setNMin ( Integer . parseInt ( strTempArray [ 8 ] ) ) ;
// 采样值的最大值
analogDTO . setNMax ( Integer . parseInt ( strTempArray [ 9 ] ) ) ;
// 一次变比
analogDTO . setFPrimary ( Float . parseFloat ( strTempArray [ 10 ] ) ) ;
// 二次变比
analogDTO . setFSecondary ( Float . parseFloat ( strTempArray [ 11 ] ) ) ;
// 一次值还是二次值标志
analogDTO . setSzValueType ( strTempArray [ 12 ] ) ;
}
//WW 2019-11-14 // 采样频率
nFreq = Float . parseFloa t ( bufferedReader . readLine ( ) ) ;
int nFreq = Integer . parseIn t ( bufferedReader . readLine ( ) ) ;
// 获取采样段数
strFileLine = bufferedReader . readLine ( ) ;
int nRates = Integer . parseInt ( strFileLine ) ;
comtradeCfgDTO . setNRates ( nRates ) ;
// 获得每段的采样率 //采样率
List < RateDTO > lstRate = new ArrayList < > ( ) ;
long nOffset = 0 ;
int nOffset = 0 ;
for ( int i = 0 ; i < nRates ; i + + ) {
strFileLine = bufferedReader . readLine ( ) ;
strTempArray = strFileLine . split ( StrUtil . COMMA ) ;
RateDTO rateDTO = new RateDTO ( ) ;
// 单周波采样点数 //WW 2019-11-14
rateDTO . setNOneSample ( ( long ) ( Float . parseFloa t ( strTempArray [ 0 ] ) / nFreq ) ) ;
rateDTO . setNOneSample ( ( Integer . parseIn t ( strTempArray [ 0 ] ) / nFreq ) ) ;
// 总点数 //这里的strTemp是一个偏移量
rateDTO . setNSampleNum ( ( long ) ( Float . parseFloa t ( strTempArray [ 1 ] ) - nOffset ) ) ;
rateDTO . setNSampleNum ( ( Integer . parseIn t ( strTempArray [ 1 ] ) - nOffset ) ) ;
lstRate . add ( rateDTO ) ;
}
comtradeCfgDTO . setLstRate ( lstRate ) ;
// 增加读取波形起始时间个结束时间
SimpleDateFormat sdf = new SimpleDateFormat ( " dd/MM/yyyy HH:mm:ss.SSS " ) ;
String timeFormat = " dd/MM/yyyy, HH:mm:ss.SSS " ;
// 波形起始时间
strFileLine = bufferedReader . readLine ( ) ;
strFileLine = strFileLine . substring ( 0 , strFileLine . length ( ) - 3 ) . replace ( StrUtil . COMMA , StrUtil . SPACE ) ;
comtradeCfgDTO . setTimeStart ( sdf . parse ( strFileLine ) ) ;
strFileLine = strFileLine . substring ( 0 , strFileLine . length ( ) - 3 ) ;
comtradeCfgDTO . setTimeStart ( DateUtil . parse ( strFileLine , timeFormat )) ;
// 暂态触发时间
strFileLine = bufferedReader . readLine ( ) ;
strFileLine = strFileLine . substring ( 0 , strFileLine . length ( ) - 3 ) . replace ( StrUtil . COMMA , StrUtil . SPACE ) ;
comtradeCfgDTO . setTimeTrige ( sdf . parse ( strFileLine ) ) ;
strFileLine = strFileLine . substring ( 0 , strFileLine . length ( ) - 3 ) ;
comtradeCfgDTO . setTimeTrige ( DateUtil . parse ( strFileLine , timeFormat )) ;
// 获取触发时间的时间 + 毫秒
Calendar calendar = Calendar . getInstanc e( ) ;
calendar . setTime ( comtradeCfgDTO . getTimeTrige ( ) ) ;
Calendar calendar = DateUtil . calendar ( comtradeCfgDTO . getTimeTrig e( ) ) ;
comtradeCfgDTO . setFirstMs ( calendar . get ( Calendar . MILLISECOND ) ) ;
comtradeCfgDTO . setFirstTime ( calendar . getTime ( ) ) ;
long a = comtradeCfgDTO . getTimeStart ( ) . getTime ( ) ;
long b = comtradeCfgDTO . getTimeTrige ( ) . getTime ( ) ;
int c = ( int ) ( b - a ) ;
if ( c > = 90 & & c < = 110 ) {
comtradeCfgDTO . setNPush ( 100 ) ;
@@ -497,17 +460,6 @@ public class WaveFileComponent {
} catch ( Exception e ) {
// 解析.cfg文件出错
comtradeCfgDTO = null ;
} finally {
try {
bufferedReader . close ( ) ;
} catch ( IOException e ) {
throw new BusinessException ( CommonResponseEnum . CLOSE_RESOURCE_ERROR ) ;
}
try {
read . close ( ) ;
} catch ( IOException e ) {
throw new BusinessException ( CommonResponseEnum . CLOSE_RESOURCE_ERROR ) ;
}
}
return comtradeCfgDTO ;
}
@@ -520,9 +472,8 @@ public class WaveFileComponent {
* List<List<Float>> 返回波形瞬时值
**********************************/
private List < List < Float > > getComtradeDat ( ComtradeCfgDTO comtradeCfgDTO , InputStream datStream , int iType ) {
//返回数据
//返回数据, 如果仅仅做展示后期考虑换String类型, 降低内存开销
List < List < Float > > listWaveData = new ArrayList < > ( ) ;
// 波形文件路径由 .cfg 换成 .dat
//初始化xValue的值
float xValueAll = 0 ;
//判断是否首次登陆
@@ -531,23 +482,24 @@ public class WaveFileComponent {
try {
datArray = IoUtil . readBytes ( datStream ) ;
if ( ArrayUtil . isEmpty ( datArray ) ) {
return listWaveData ;
throw new BusinessException ( WaveFileResponseEnum . DAT_DATA_ERROR ) ;
}
// 计算每个单独的数据块的大小 4个字节的序号 4个字节的时间 2个字节的值
// 示例中的排布是 4个字节的序号 4个字节的时间 UA(2字节) UB(2字节) UC(2字节) IA(2字节) IB(2字节) IC(2字节)
int nDigSize = ( comtradeCfgDTO . getNDigitalNum ( ) % 16 ) > 0 ? ( comtradeCfgDTO . getNDigitalNum ( ) / 16 + 1 ) * 2 : comtradeCfgDTO . getNDigitalNum ( ) / 16 * 2 ;
int nBlockSize = 2 * Integer . SIZE / 8 + comtradeCfgDTO . getNAnalogNum ( ) * 2 + nDigSize ;
// 总长度除以每个快 的大小
// 总长度除以每个块 的大小
int nBlockNum = datArray . length / nBlockSize ;
// 获取采样率
long finalSampleRate = getFinalWaveSample ( comtradeCfgDTO . getLstRate ( ) , iType ) ;
int finalSampleRate = getFinalWaveSample ( comtradeCfgDTO . getLstRate ( ) , iType ) ;
if ( finalSampleRate ! = - 1 ) {
//设置最终采样率
comtradeCfgDTO . setFinalSampleRate ( finalSampleRate ) ;
// 计算转换后的采样率
int nnInd = 0 ;
// 抽点后总共多少点数据
long nWaveNum ;
int nWaveNum ;
//抽点后新的的采样率
List < RateDTO > newLstRate = new ArrayList < > ( ) ;
for ( int iRate = 0 ; iRate < comtradeCfgDTO . getNRates ( ) ; iRate + + ) {
@@ -689,14 +641,14 @@ public class WaveFileComponent {
* @param lstRate cfg中关于采样率参数
* @return 返回最小采样率
**********************************/
private long getFinalWaveSample ( List < RateDTO > lstRate , int iType ) {
private int getFinalWaveSample ( List < RateDTO > lstRate , int iType ) {
// 最终返回采样率
long nFinalOneSample = - 1 ;
int nFinalOneSample = - 1 ;
// 最小采样率
long nMinOneSample = - 1 ;
int nMinOneSample = - 1 ;
if ( lstRate . size ( ) > 0 ) {
nMinOneSample = lstRate . get ( 0 ) . getNOneSample ( ) ;
long tmpOneSample ;
int tmpOneSample ;
for ( RateDTO rateDTO : lstRate ) {
tmpOneSample = rateDTO . getNOneSample ( ) ;
if ( tmpOneSample > = 32 ) {
@@ -1276,7 +1228,7 @@ public class WaveFileComponent {
InputStream cfgStream = waveFileComponent . getFileInputStreamByFilePath ( " D: \\ comtrade \\ 00-B7-8D-00-B7-25 \\ 1_20200629_164016_234.CFG " ) ;
InputStream datStream = waveFileComponent . getFileInputStreamByFilePath ( " D: \\ comtrade \\ 00-B7-8D-00-B7-25 \\ 1_20200629_164016_234.DAT " ) ;
// 获取瞬时波形 //获取原始波形值
WaveDataDTO waveDataDTO = waveFileComponent . getComtrade ( cfgStream , datStream , 1 ) ;
WaveDataDTO waveDataDTO = waveFileComponent . getComtrade ( cfgStream , datStream , 1 ) ;
d = new Date ( ) ;
s = sdf . format ( d ) ;
System . out . println ( s ) ;