文章背景
FJ的现场有个区域的位置的超短期预测出现断点的状况,需要解决,似乎过程记录如下。
目录
[TOC]
原因分析
通过分析发回来的现场的日志信息,发现缺少的超短期预测的部分,是因为一些预测的时间超过一分钟导致的,然后导致一个状态位没有重置,因此跳过了那个区间。
部分日志摘要如下:
INFO [2018-10-12 16:30:13:750] [超短期预测线程] (FuJian_EFile.java:296)
-生成超短期预测功率E文本成功!
DEBUG [2018-10-12 16:30:13:750] [超短期预测线程] (FuJian_EFile.java:297)
-<!Entity=福建 type=新能源 time='2018-10-12 16:30:13'>
<system>
@ 序号 地区 系统 可读时间
# 0 '福建' 'd5000' '2018-10-12 16:30:13'
</system>
<EFJ_CDQ_RESULT_UP>
@ 序号 标识ID 风场ID 上报日期 预测时间 值 值 值 值 值 值 值 值 值 值 值 值 值 值 值 值 SYS_DATE
# 1 1 113997366155018556 2018-10-12 2018-10-12 16:45:00 24.7757 24.9615 25.1913 25.4290 25.6678 25.9056 25.8834 25.8101 25.7369 25.6637 25.5085 25.3382 25.1670 24.9968 24.6356 24.2354 SYSDATE
</EFJ_CDQ_RESULT_UP>
####
INFO [2018-10-12 16:30:25:177] [超短期预测线程] (FuJian_EFile.java:296)
-生成超短期预测功率E文本成功!
DEBUG [2018-10-12 16:30:25:177] [超短期预测线程] (FuJian_EFile.java:297)
-<!Entity=福建 type=新能源 time='2018-10-12 16:30:25'>
<system>
@ 序号 地区 系统 可读时间
# 0 '福建' 'd5000' '2018-10-12 16:30:25'
</system>
<EFJ_CDQ_RESULT_UP>
@ 序号 标识ID 风场ID 上报日期 预测时间 值 值 值 值 值 值 值 值 值 值 值 值 值 值 值 值 SYS_DATE
# 1 1 113997366155018556 2018-10-12 2018-10-12 16:45:00 24.7757 24.9615 25.1913 25.4290 25.6678 25.9056 25.8834 25.8101 25.7369 25.6637 25.5085 25.3382 25.1670 24.9968 24.6356 24.2354 SYSDATE
</EFJ_CDQ_RESULT_UP>
####
INFO [2018-10-12 16:30:43:052] [超短期预测线程] (FuJianOld_EFile.java:378)
-生成超短期预测功率E文本成功!
DEBUG [2018-10-12 16:30:43:053] [超短期预测线程] (FuJianOld_EFile.java:379)
-<UltraShortTermForcast::梅岭 time='2018-10-12_16:45' cap='48.0'>
@顺序 预测出力值 开机容量
#1 24.776 48.000
#2 24.961 48.000
#3 25.191 48.000
#4 25.429 48.000
#5 25.668 48.000
#6 25.906 48.000
#7 25.883 48.000
#8 25.810 48.000
#9 25.737 48.000
#10 25.664 48.000
#11 25.508 48.000
#12 25.338 48.000
#13 25.167 48.000
#14 24.997 48.000
#15 24.636 48.000
#16 24.235 48.000
</UltraShortTermForcast::梅岭>
####
INFO [2018-10-12 16:30:59:030] [超短期预测线程] (UltraShortPlanThread.java:91)
-本次超短期计算成功,耗时:178756毫秒
问题代码
代码接下来附上,从代码可以看到,计算时候,是通过获取时间时间的分钟数是否小于1重置标志位,然后到达指定时刻之后,来进行计算的,由于一些原因,不能整体更换代码,只能做一些小修改了。
while (Application.IsRunning()) {
try {
Calendar CurrentTime = Calendar.getInstance();
int nCurrentMinute = CurrentTime.get(Calendar.MINUTE);
int nMinuteOff = nCurrentMinute % CDQTIMEINTERVAL;
if (nMinuteOff < 1) {
m_UsCalced = false;
}
// 从第12分钟开始功率预测
if (!(nMinuteOff < calculateOffsetTime) && (false == m_UsCalced)) {
Application.m_Logger.info("开始进行超短期计算");
StringList stringList = new StringList();
WindFarmList farmList = ConfigMng.GetInstance().m_WindFarmList;
for (WindFarm windfarm : farmList) {
// 如果该风电场采用Wpfs解析的方式接入测风塔数据
if (true == windfarm.towerFileCfgList.fileCheckOn) {
for (FileNameCfg fileNameCfg : windfarm.towerFileCfgList) {
String temp = "";
int hour = CurrentTime.get(Calendar.HOUR);
if (hour < 10)
temp = "0" + hour;
else
temp = String.valueOf(hour);
nCurrentMinute = (nCurrentMinute/CDQTIMEINTERVAL+1)*CDQTIMEINTERVAL -
RealtimeTowerThread.CFTTIMEINTERVAL*2;
if (nCurrentMinute < 10)
temp = temp + "0" + nCurrentMinute;
else
temp += String.valueOf(nCurrentMinute);
stringList.add(fileNameCfg.strPreName + temp);
}
if (false == Application.isImportDataBase(stringList)) {
Application.m_Logger.error("测风塔文件未入库: " + stringList);
}
}
}
long startTime = System.nanoTime();
nCurrentMinute = CurrentTime.get(Calendar.MINUTE);
CurrentTime.set(Calendar.MINUTE, 0);
CurrentTime.set(Calendar.SECOND, 0);
CurrentTime.set(Calendar.MILLISECOND, 0);
if (true==advanceCalc) {
CurrentTime.add(Calendar.MINUTE, (nCurrentMinute/CDQTIMEINTERVAL+1)*CDQTIMEINTERVAL);
} else {
CurrentTime.add(Calendar.MINUTE, (nCurrentMinute/CDQTIMEINTERVAL)*CDQTIMEINTERVAL);
}
m_UsCalced = Calculate(CurrentTime);
long estimatedTime = (System.nanoTime() - startTime) / 1000000L;
if (m_UsCalced) {
Application.m_Logger.info("本次超短期计算成功,耗时:"
+ estimatedTime + "毫秒");
} else {
Application.m_Logger.info("本次超短期计算失败,耗时:"
+ estimatedTime + "毫秒");
}
}
Application.ThreadSleep(10000);
} catch (Exception e) {
e.printStackTrace();
Application.m_Logger.error(e, e);
this.checkAccess();
}
}
解决方案
看懂了代码,想要解决这个问题,其实只要更改一个参数就行,把1分钟那儿改成,计算之前的时间都给重置标志位就行,
不过,和经理商讨之后,这段代码还是有点绕,让人难以理解,稍微改动了下,容易理解一些。
最后的代码如下:
while (Application.IsRunning()) {
try {
Calendar CurrentTime = Calendar.getInstance();
int nCurrentMinute = CurrentTime.get(Calendar.MINUTE);
int nMinuteOff = nCurrentMinute % CDQTIMEINTERVAL;
if (nMinuteOff < 1 ||nMinuteOff < calculateOffsetTime) {//"第一分钟做标记"
//if (nMinuteOff < 1) {//"第一分钟做标记"
m_UsCalced = false;
}
// 从第12分钟开始功率预测
if (!(nMinuteOff < calculateOffsetTime) && (false == m_UsCalced)) {
Application.m_Logger.info("开始进行超短期计算");
StringList stringList = new StringList();
WindFarmList farmList = ConfigMng.GetInstance().m_WindFarmList;
for (WindFarm windfarm : farmList) {
// 如果该风电场采用Wpfs解析的方式接入测风塔数据
if (true == windfarm.towerFileCfgList.fileCheckOn) {
for (FileNameCfg fileNameCfg : windfarm.towerFileCfgList) {
String temp = "";
int hour = CurrentTime.get(Calendar.HOUR);
if (hour < 10)
temp = "0" + hour;
else
temp = String.valueOf(hour);
nCurrentMinute = (nCurrentMinute/CDQTIMEINTERVAL+1)*CDQTIMEINTERVAL -
RealtimeTowerThread.CFTTIMEINTERVAL*2;
if (nCurrentMinute < 10)
temp = temp + "0" + nCurrentMinute;
else
temp += String.valueOf(nCurrentMinute);
stringList.add(fileNameCfg.strPreName + temp);
}
if (false == Application.isImportDataBase(stringList)) {
Application.m_Logger.error("测风塔文件未入库: " + stringList);
}
}
}
long startTime = System.nanoTime();
nCurrentMinute = CurrentTime.get(Calendar.MINUTE);
CurrentTime.set(Calendar.MINUTE, 0);
CurrentTime.set(Calendar.SECOND, 0);
CurrentTime.set(Calendar.MILLISECOND, 0);
if (true==advanceCalc) {
CurrentTime.add(Calendar.MINUTE, (nCurrentMinute/CDQTIMEINTERVAL+1)*CDQTIMEINTERVAL);
} else {
CurrentTime.add(Calendar.MINUTE, (nCurrentMinute/CDQTIMEINTERVAL)*CDQTIMEINTERVAL);
}
m_UsCalced = Calculate(CurrentTime);
long estimatedTime = (System.nanoTime() - startTime) / 1000000L;
if (m_UsCalced) {
Application.m_Logger.info("本次超短期计算成功,耗时:"
+ estimatedTime + "毫秒");
} else {
Application.m_Logger.info("本次超短期计算失败,耗时:"
+ estimatedTime + "毫秒");
}
}
Application.ThreadSleep(10000);
} catch (Exception e) {
e.printStackTrace();
Application.m_Logger.error(e, e);
this.checkAccess();
}
}
测试
测试就只是烤机了,毕竟逻辑上面是通的,也不应该有异常数据了。
然而不行的是10.24,10.25,烤机是从10.23开始的,这个是什么鬼?
结果分析日志发现,24和25中午莫名所有程序停止,下意识的问下是不是谁在中午休息时候懂了电脑的休眠按钮。 一问还真是。。。然后发现还有一段时间也存在休眠的状况,然后其他时间一切正常了。
测试基本这样子就完毕了,只等测试到最后时间发到现场了。
说明
这份程序不是最新版本的程序,一些老的需要优化的就没动了,毕竟已经在新版本上面弄了,重复劳动太心累了。
此次更新对应版本号为wpfs1.44_20181019,对应相同问题的光伏片区为ppfs1.24_20170622,建议所有片区如果存在老版本,根据实际考核情况考虑是否更新程序,同时如果更新则需要开二次开发单记录下升级状况。
参考文章
无
版本记录
20181023 完成文章
20181026 添加测试部分