diff --git a/HealthMonitor.Service/Resolver/PregnancyHeartRateResolver.cs b/HealthMonitor.Service/Resolver/PregnancyHeartRateResolver.cs index 6ef835f..5f941f6 100644 --- a/HealthMonitor.Service/Resolver/PregnancyHeartRateResolver.cs +++ b/HealthMonitor.Service/Resolver/PregnancyHeartRateResolver.cs @@ -433,34 +433,37 @@ namespace HealthMonitor.Service.Resolver // 高频不停,15分钟内只下发一条 if (string.IsNullOrEmpty(freqSaveAndPushFetalHeartRate)) { - heartRate.HeartRate = (int)avgPhr; - // 最后一条高频心率 - var lastFreqHr = lastPhr.First(); - var ts = DateTimeUtil.GetTimeDifferenceInSeconds((DateTime)lastFreqHr.LastUpdate!, phrFreqstatus!.LastUpdate); - // 判断是否够highFreqSampleTimes,540s - if (ts < highFreqSampleTimes) - { - /// 不够10分钟最近12个数据生成胎心值 - //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); - int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); - heartRate.HeartRate = selectedHrValue; - _logger.LogInformation($"{heartRate.Serialno} 不够10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); - - heartRate.LastUpdate = lastFreqHr.LastUpdate; - } - else - { - - /// 超过10分钟最近12个数据生成胎心值 - //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); - int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + //heartRate.HeartRate = (int)avgPhr; + //// 最后一条高频心率 + //var lastFreqHr = lastPhr.First(); + //var ts = DateTimeUtil.GetTimeDifferenceInSeconds((DateTime)lastFreqHr.LastUpdate!, phrFreqstatus!.LastUpdate); + //// 判断是否够highFreqSampleTimes,540s + //if (ts < highFreqSampleTimes) + //{ + // /// 不够10分钟最近12个数据生成胎心值 + // //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); + // int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + // heartRate.HeartRate = selectedHrValue; + // _logger.LogInformation($"{heartRate.Serialno} 不够10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); + + // heartRate.LastUpdate = lastFreqHr.LastUpdate; + //} + //else + //{ + + // /// 超过10分钟最近12个数据生成胎心值 + // //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); + // int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + + // heartRate.HeartRate = selectedHrValue; + // _logger.LogInformation($"{heartRate.Serialno} 超过10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); + //} + + //_logger.LogInformation($"{heartRate.Serialno} 高频数据触发连续12个值都是正常的的高频心率处理"); + //await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR,highFreqSampleTimes ,upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); - heartRate.HeartRate = selectedHrValue; - _logger.LogInformation($"{heartRate.Serialno} 超过10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); - } _logger.LogInformation($"{heartRate.Serialno} 高频数据触发连续12个值都是正常的的高频心率处理"); - await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR,highFreqSampleTimes ,upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); - + await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd, lastPhr, triggerHighFreqHigh, triggerHighFreqLow); // 删除高频状态的首条记录 await _deviceCacheMgr.DelPregnancyHeartRateFreqStatusAsync(heartRate.Serialno); // 设置15分的SaveAndPushFetalHeartRate业务间隔 @@ -508,36 +511,37 @@ namespace HealthMonitor.Service.Resolver //await SaveAndPushFreqFetalHeartRateAsync(heartRate, commonPHR, upperAlarmThreshold, lowerAlarmThreshold, avgPhr, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString()); //await SaveAndPushFetalHeartRateAsync(heartRate, commonPHR, upperAlarmThreshold, lowerAlarmThreshold, avgPhr, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); - heartRate.HeartRate = (int)avgPhr; - //await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); - // 最后一条高频心率 - var lastFreqHr = lastPhr.First(); - - var ts = DateTimeUtil.GetTimeDifferenceInSeconds((DateTime)lastFreqHr.LastUpdate!, phrFreqstatus!.LastUpdate); - // 判断是否够highFreqSampleTimes,540s - if (ts < highFreqSampleTimes) - { - /// 不够10分钟最近12个数据生成胎心值 - //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); - int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + //heartRate.HeartRate = (int)avgPhr; + //// 最后一条高频心率 + //var lastFreqHr = lastPhr.First(); + + //var ts = DateTimeUtil.GetTimeDifferenceInSeconds((DateTime)lastFreqHr.LastUpdate!, phrFreqstatus!.LastUpdate); + //// 判断是否够highFreqSampleTimes,540s + //if (ts < highFreqSampleTimes) + //{ + // /// 不够10分钟最近12个数据生成胎心值 + // //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); + // int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + + // heartRate.HeartRate = selectedHrValue; + // _logger.LogInformation($"{heartRate.Serialno} 不够10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); + + // heartRate.LastUpdate = lastFreqHr.LastUpdate; + //} + //else + //{ + // //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); + // int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + + // heartRate.HeartRate = selectedHrValue; + // /// 超过10分钟最近12个数据生成胎心值 + // _logger.LogInformation($"{heartRate.Serialno} 超过10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); + //} + //_logger.LogInformation($"{heartRate.Serialno} 高频结束后的highFreqSampleTimes=0的高频心率处理"); + //await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); - heartRate.HeartRate = selectedHrValue; - _logger.LogInformation($"{heartRate.Serialno} 不够10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); - - heartRate.LastUpdate = lastFreqHr.LastUpdate; - } - else - { - //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); - int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); - - heartRate.HeartRate = selectedHrValue; - /// 超过10分钟最近12个数据生成胎心值 - _logger.LogInformation($"{heartRate.Serialno} 超过10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); - } _logger.LogInformation($"{heartRate.Serialno} 高频结束后的highFreqSampleTimes=0的高频心率处理"); - await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); - + await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd, lastPhr, triggerHighFreqHigh, triggerHighFreqLow); } /// 在highFreqSampleTimes>0一直异常(大于等于triggerHighFreqLow,少于等于triggerHighFreqHig), @@ -568,40 +572,42 @@ namespace HealthMonitor.Service.Resolver //计算高频 //await SaveAndPushFetalHeartRateAsync(heartRate, commonPHR, upperAlarmThreshold, lowerAlarmThreshold, avgPhr, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); heartRate.HeartRate = (int)avgPhr; - //await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); // 判断是否够highFreqSampleTimes,540s var lastPhr = filterPhr .OrderByDescending(i => i.LastUpdate) .Take(stopHighFreqSampleCount).ToList(); - // 最后一条高频心率 - var lastFreqHr = lastPhr.First(); + //// 最后一条高频心率 + //var lastFreqHr = lastPhr.First(); - var ts = DateTimeUtil.GetTimeDifferenceInSeconds((DateTime)lastFreqHr.LastUpdate!, phrFreqstatus!.LastUpdate); + //var ts = DateTimeUtil.GetTimeDifferenceInSeconds((DateTime)lastFreqHr.LastUpdate!, phrFreqstatus!.LastUpdate); - if (ts < highFreqSampleTimes) - { - /// 不够10分钟最近12个数据的成胎心值 - //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); - int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); - - heartRate.HeartRate = selectedHrValue; - _logger.LogInformation($"{heartRate.Serialno} 不够10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); + //if (ts < highFreqSampleTimes) + //{ + // /// 不够10分钟最近12个数据的成胎心值 + // //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); + // int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + + // heartRate.HeartRate = selectedHrValue; + // _logger.LogInformation($"{heartRate.Serialno} 不够10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); - heartRate.LastUpdate = lastFreqHr.LastUpdate; - } - else - { - //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); - int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + // heartRate.LastUpdate = lastFreqHr.LastUpdate; + //} + //else + //{ + // //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); + // int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + + // heartRate.HeartRate = selectedHrValue; + // /// 超过10分钟最近12个数据的生成胎心值 + // _logger.LogInformation($"{heartRate.Serialno} 超过10分钟最近12个数据的中取 {heartRate.HeartRate} 生成胎心值"); + //} + //_logger.LogInformation($"{heartRate.Serialno} 高频结束后的在highFreqSampleTimes>0 正常心率(通常情况)触发的高频心率处理"); + //await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); - heartRate.HeartRate = selectedHrValue; - /// 超过10分钟最近12个数据的生成胎心值 - _logger.LogInformation($"{heartRate.Serialno} 超过10分钟最近12个数据的中取 {heartRate.HeartRate} 生成胎心值"); - } _logger.LogInformation($"{heartRate.Serialno} 高频结束后的在highFreqSampleTimes>0 正常心率(通常情况)触发的高频心率处理"); - await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); + await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd, lastPhr, triggerHighFreqHigh, triggerHighFreqLow); } else { @@ -643,39 +649,41 @@ namespace HealthMonitor.Service.Resolver .Select(i => i.PregnancyHeartRate).Average(); heartRate.HeartRate = (int)avgPhr; - // await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); - //_logger.LogInformation($"{heartRate.Serialno} 高频数据个数{freqCollection.Count},触发高频开始时间{phrFreqstatus!.LastUpdate},高频心率平均值:{(int)avgPhr}"); // 判断是否够highFreqSampleTimes,540s var lastPhr = freqCollection .OrderByDescending(i => i.LastUpdate) .Take(stopHighFreqSampleCount) .ToList(); - // 最后一条高频心率 - var lastFreqHr = lastPhr.First(); + //// 最后一条高频心率 + //var lastFreqHr = lastPhr.First(); + + //var ts = DateTimeUtil.GetTimeDifferenceInSeconds((DateTime)lastFreqHr.LastUpdate!, phrFreqstatus!.LastUpdate); + //if (ts < highFreqSampleTimes) + //{ + // /// 不够10分钟最近12个数据生成胎心值 + // //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); + // int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + + // heartRate.HeartRate = selectedHrValue; + // _logger.LogInformation($"{heartRate.Serialno} 不够10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); + + // heartRate.LastUpdate = lastFreqHr.LastUpdate; + //} + //else + //{ + // //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); + // int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + // heartRate.HeartRate = selectedHrValue; + // /// 超过10分钟最近12个数据生成胎心值 + // _logger.LogInformation($"{heartRate.Serialno} 超过10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); + //} + //_logger.LogInformation($"{heartRate.Serialno} 高频结束后的时间倒序的正常心率触发的高频心率处理"); + //await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); - var ts = DateTimeUtil.GetTimeDifferenceInSeconds((DateTime)lastFreqHr.LastUpdate!, phrFreqstatus!.LastUpdate); - if (ts < highFreqSampleTimes) - { - /// 不够10分钟最近12个数据生成胎心值 - //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); - int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); - heartRate.HeartRate = selectedHrValue; - _logger.LogInformation($"{heartRate.Serialno} 不够10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); - - heartRate.LastUpdate = lastFreqHr.LastUpdate; - } - else - { - //int selectedHrValue = SelectValueFromFreqHeartRate(heartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); - int selectedHrValue = SelectValueFromFreqHeartRate(heartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); - heartRate.HeartRate = selectedHrValue; - /// 超过10分钟最近12个数据生成胎心值 - _logger.LogInformation($"{heartRate.Serialno} 超过10分钟最近12个数据中取 {heartRate.HeartRate} 生成胎心值"); - } _logger.LogInformation($"{heartRate.Serialno} 高频结束后的时间倒序的正常心率触发的高频心率处理"); - await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); + await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(heartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd, lastPhr, triggerHighFreqHigh, triggerHighFreqLow); _logger.LogInformation($"{heartRate.Serialno} 高频数据个数{freqCollection.Count},触发高频开始时间{phrFreqstatus!.LastUpdate},时间倒叙"); } @@ -810,40 +818,7 @@ namespace HealthMonitor.Service.Resolver } - /// - /// 从高频心率数据中取心率值计算胎心值 - /// - /// - /// - /// - /// - /// - private int SelectValueFromFreqHeartRate(HisGpsHeartRate heartRate, int triggerHighFreqHigh, int triggerHighFreqLow, List lastPhr) - { - // 连续12个心率的值的最小值 - var selectedHrValue = lastPhr.Select(i => i.PregnancyHeartRate).Min(); - _logger.LogInformation($"{heartRate.Serialno} 最近12个数据的最小值 {selectedHrValue}"); - /// 高频状态下,取值心率低于高频最小值阀值,则需要取最大值进行计算。刚好跟大于高频最大值阀值刚好相反 - if (selectedHrValue < triggerHighFreqLow) - { - // 低于高频最小值阀值,则需要取最大值 - var selectedHrMax = lastPhr.Select(i => i.PregnancyHeartRate).Max(); - _logger.LogInformation($"{heartRate.Serialno} 最近12个数据的最小值 {selectedHrValue},低于高频最小值阀值 {triggerHighFreqLow},取最近12个数据的最大值{selectedHrMax}作为心率"); - selectedHrValue = selectedHrMax; - } - - if (selectedHrValue > triggerHighFreqHigh) - { - var selectedHrMin = lastPhr.Select(i => i.PregnancyHeartRate).Min(); - _logger.LogInformation($"{heartRate.Serialno} 最近12个数据的最小值 {selectedHrValue},低于高频最大值阀值 {triggerHighFreqHigh},最近12个数据的最小值{selectedHrMin}作为心率"); - selectedHrValue = selectedHrMin; - } - - - - return selectedHrValue; - } - + /// /// 从高频心率数据中取心率值计算胎心值 /// @@ -916,62 +891,7 @@ namespace HealthMonitor.Service.Resolver } - /// - /// 从高频心率数据中取心率值计算胎心值 - /// - /// - /// - /// - /// - /// - private async Task SelectValueFromFreqHeartRateAsync(HisGpsHeartRate heartRate, int triggerHighFreqHigh, int triggerHighFreqLow, List lastPhr) - { - // 连续12个心率的值的最小值 - var selectedHrValue = lastPhr.Select(i => i.PregnancyHeartRate).Min(); - _logger.LogInformation($"{heartRate.Serialno} 最近12个数据的最小值 {selectedHrValue}"); - /// 高频状态下,取值心率低于高频最小值阀值,则需要取最大值进行计算。刚好跟大于高频最大值阀值刚好相反 - if (selectedHrValue < triggerHighFreqLow) - { - // 低于高频最小值阀值,则需要取最大值 - var selectedHrMax = lastPhr.Select(i => i.PregnancyHeartRate).Max(); - _logger.LogInformation($"{heartRate.Serialno} 最近12个数据的最小值 {selectedHrValue},低于高频最小值阀值 {triggerHighFreqLow},取最近12个数据的最大值{selectedHrMax}作为心率"); - selectedHrValue = selectedHrMax; - } - - if (selectedHrValue > triggerHighFreqHigh) - { - var selectedHrMin = lastPhr.Select(i => i.PregnancyHeartRate).Min(); - _logger.LogInformation($"{heartRate.Serialno} 最近12个数据的最小值 {selectedHrValue},低于高频最大值阀值 {triggerHighFreqHigh},最近12个数据的最小值{selectedHrMin}作为心率"); - selectedHrValue = selectedHrMin; - } - - #region 判断是否有低于低频阀值引起的高频 - /// 低频阀值引起的高频情况下,选择的心率值是正常心率的最小值,之后的区间选择的心率值是正常心率的最小值,不足10分钟没有正常值取最小阀值,超过10分钟没有正常值取最大 阀值 - var phrFreqstatus = await _deviceCacheMgr.GetPregnancyHeartRateFreqStatusAsync(heartRate.Serialno); - - if (phrFreqstatus?.PregnancyHeartRate < triggerHighFreqLow) - { - _logger.LogInformation($"{heartRate.Serialno} 低频阀值引起的高频,低频心率引起值 {phrFreqstatus?.PregnancyHeartRate}"); - - var phr = lastPhr.Where(i => i.PregnancyHeartRate <= triggerHighFreqHigh && i.PregnancyHeartRate >= triggerHighFreqLow); - - if (!phr.Any()) - { - selectedHrValue = triggerHighFreqLow; - } - else - { - selectedHrValue = lastPhr.Where(i => i.PregnancyHeartRate <= triggerHighFreqHigh && i.PregnancyHeartRate >= triggerHighFreqLow) - .ToList() - .Select(i => i.PregnancyHeartRate).Min(); - } - - } - #endregion - - return selectedHrValue; - } - + /// /// 高频胎心处理 /// 1. 高频数据触发连续12个值都是正常的的高频心率处理 @@ -990,103 +910,10 @@ namespace HealthMonitor.Service.Resolver /// /// /// - private async Task SaveAndPushFetalHeartRateEndFreqHeartRateAsyncOld(HisGpsHeartRate heartRate, PregnancyCommonHeartRateModel commonPHR, int highFreqSampleTimes, int upperAlarmThreshold, int lowerAlarmThreshold, string sampleTime, DateTime statStartTime, DateTime statEndTime) + private async Task SaveAndPushFetalHeartRateEndFreqHeartRateAsync(HisGpsHeartRate heartRate, PregnancyCommonHeartRateModel commonPHR, int highFreqSampleTimes, int upperAlarmThreshold, int lowerAlarmThreshold, string sampleTime, DateTime statStartTime, DateTime statEndTime) { - // 计算胎心=孕妇心率*系数 - - #region 胎心系数使用基于心率与众数对比 - var coefficient = 0f; - /** - // 孕妇心率少于众数,取StatMinValueFprCoefficient - if (heartRate.HeartRate < commonPHR!.Mode) - { - coefficient = commonPHR.StatMinValueFprCoefficient!; - _logger.LogInformation($"{heartRate.Serialno} 孕妇心率少于众数,使用最小值系数 {coefficient}"); - } - // 孕妇心率大于众数,取StatMaxValueFprCoefficient与StatModeAvgFprCoefficient中少的那个 - else if (heartRate.HeartRate > commonPHR.Mode) - { - if (commonPHR.StatModeAvgFprCoefficient > commonPHR.StatMaxValueFprCoefficient) - { - coefficient = commonPHR.StatMaxValueFprCoefficient!; - _logger.LogInformation($"{heartRate.Serialno} 孕妇心率大于众数,使用最大值系数 {coefficient}"); - } - else - { - coefficient = commonPHR.StatModeAvgFprCoefficient!; - _logger.LogInformation($"{heartRate.Serialno} 孕妇心率大于众数,使用均值系数 {coefficient}"); - } - } - else - { - coefficient = commonPHR.StatModeAvgFprCoefficient; - _logger.LogInformation($"{heartRate.Serialno} 孕妇心率等于众数,使用均值系数 {coefficient}"); - } - */ - - - ///1、高频最小值>心率,取高频最小值系数 - ///2、高频最小值 < 心率 < 众数,取众数系数与高频最小值系数较小值 - ///3、众数 < 心率 < 高频最大值,取众数系数与高频最大值系数较小值 - ///4、心率 > 高频最大值,取高频最大值系数 - - // 1、高频最小值>心率,取高频最小值系数 - if (commonPHR.MinValue > heartRate.HeartRate) - { - coefficient = commonPHR.StatMinValueFprCoefficient!; - _logger.LogInformation($"{heartRate.Serialno} 高频最小值>心率,取高频最小值系数 {coefficient}"); - } - - // 2、高频最小值 < 心率 < 众数,取众数系数与高频最小值系数较小值 - if (commonPHR.MinValue < heartRate.HeartRate && heartRate.HeartRate < commonPHR.Mode) - { - if (commonPHR.StatModeAvgFprCoefficient > commonPHR.StatMinValueFprCoefficient) - { - coefficient = commonPHR.StatMinValueFprCoefficient!; - _logger.LogInformation($"{heartRate.Serialno} 高频最小值 < 心率 < 众数,平均值系数大于最小值系数,使用最小值系数 {coefficient}"); - } - else - { - coefficient = commonPHR.StatModeAvgFprCoefficient!; - _logger.LogInformation($"{heartRate.Serialno} 高频最小值 < 心率 < 众数,平均值系数小于最小值系数,使用均值系数 {coefficient}"); - } - } - - // 3、众数 < 心率 < 高频最大值,取众数系数与高频最大值系数较小值 - if (commonPHR.Mode < heartRate.HeartRate && heartRate.HeartRate < commonPHR.MaxValue) - { - if (commonPHR.StatModeAvgFprCoefficient > commonPHR.StatMaxValueFprCoefficient) - { - coefficient = commonPHR.StatMaxValueFprCoefficient!; - _logger.LogInformation($"{heartRate.Serialno} 众数 < 心率 < 高频最大值,平均值系数大于最最大值系数,使用最大值系数 {coefficient}"); - } - else - { - coefficient = commonPHR.StatModeAvgFprCoefficient!; - _logger.LogInformation($"{heartRate.Serialno} 众数 < 心率 < 高频最大值,平均值系数小于最小值系数,使用均值系数 {coefficient}"); - } - } - - // 4、心率 > 高频最大值,取高频最大值系数 - - if (heartRate.HeartRate > commonPHR.MaxValue) - { - coefficient = commonPHR.StatMaxValueFprCoefficient!; - _logger.LogInformation($"{heartRate.Serialno} 心率 > 高频最大值,取高频最大值系数 {coefficient}"); - } - - if (heartRate.HeartRate == commonPHR.Mode) - { - coefficient = commonPHR.StatModeAvgFprCoefficient!; - - _logger.LogInformation($"{heartRate.Serialno} 心率 == 众数,取均值系数 {coefficient}"); - } - #endregion - - var fetalHeartRate = SafeType.SafeInt(heartRate.HeartRate! * coefficient); - // 胎心的最大值调整为220,超过都按该值220输出 - // fetalHeartRate = fetalHeartRate>= 220 ? 220 : fetalHeartRate; + var fetalHeartRate = await _serviceTDengine.GetFetalHeartRateAsync(heartRate.Serialno, (int)heartRate.HeartRate!); var phrFreqstatus = await _deviceCacheMgr.GetPregnancyHeartRateFreqStatusAsync(heartRate.Serialno); var isAbnormal = 0; @@ -1122,14 +949,14 @@ namespace HealthMonitor.Service.Resolver if (fetalHeartRate > 220) { fetalHeartRate = 220; - _logger.LogWarning($"{heartRate.Serialno} 大于220,按220输出,计算因子:孕妇心率 {heartRate.HeartRate},系数 {coefficient},周期 周期:{statStartTime.ToString("yyyy-MM-dd HH:mm:ss")}----{statEndTime.ToString("yyyy-MM-dd HH:mm:ss")}"); + _logger.LogWarning($"{heartRate.Serialno} 大于220,按220输出,计算因子:孕妇心率 {heartRate.HeartRate},周期:{statStartTime.ToString("yyyy-MM-dd HH:mm:ss")}----{statEndTime.ToString("yyyy-MM-dd HH:mm:ss")}"); } // 胎心的最小值调整为90,超过都按该值90 if (fetalHeartRate < 90) { fetalHeartRate = 90; - _logger.LogWarning($"{heartRate.Serialno} 小于90,按90输出,计算因子:孕妇心率 {heartRate.HeartRate},系数 {coefficient},周期 周期:{statStartTime.ToString("yyyy-MM-dd HH:mm:ss")}----{statEndTime.ToString("yyyy-MM-dd HH:mm:ss")}"); + _logger.LogWarning($"{heartRate.Serialno} 小于90,按90输出,计算因子:孕妇心率 {heartRate.HeartRate}, 周期:{statStartTime.ToString("yyyy-MM-dd HH:mm:ss")}----{statEndTime.ToString("yyyy-MM-dd HH:mm:ss")}"); } isAbnormal = fetalHeartRate > upperAlarmThreshold ? 1 : (fetalHeartRate < lowerAlarmThreshold ? 2 : 0); } @@ -1137,10 +964,7 @@ namespace HealthMonitor.Service.Resolver - //if (phrFreqstatus == null) isAbnormal = 0; - //var statsusDesc = (phrFreqstatus == null) ? "常规" : "高频"; - var statsusDesc = "高频"; - _logger.LogInformation($"{heartRate.Serialno} 在 {statsusDesc} 状态,生成胎心值:{fetalHeartRate},统计周期:{statStartTime.ToString("yyyy-MM-dd HH:mm:ss")}----{statEndTime.ToString("yyyy-MM-dd HH:mm:ss")}"); + _logger.LogInformation($"{heartRate.Serialno} 在 高频 状态,生成胎心值:{fetalHeartRate},统计周期:{statStartTime.ToString("yyyy-MM-dd HH:mm:ss")}----{statEndTime.ToString("yyyy-MM-dd HH:mm:ss")}"); // 保存到 数据服务 MySQL 数据库 HisGpsFetalHeartRate gpsFetalHeartRate = new() { @@ -1215,6 +1039,8 @@ namespace HealthMonitor.Service.Resolver } } + + /// /// 高频胎心处理 /// 1. 高频数据触发连续12个值都是正常的的高频心率处理 @@ -1233,13 +1059,70 @@ namespace HealthMonitor.Service.Resolver /// /// /// - private async Task SaveAndPushFetalHeartRateEndFreqHeartRateAsync(HisGpsHeartRate heartRate, PregnancyCommonHeartRateModel commonPHR, int highFreqSampleTimes, int upperAlarmThreshold, int lowerAlarmThreshold, string sampleTime, DateTime statStartTime, DateTime statEndTime) + private async Task SaveAndPushFetalHeartRateEndFreqHeartRateAsync( + HisGpsHeartRate heartRate, + PregnancyCommonHeartRateModel commonPHR, + int highFreqSampleTimes, + int upperAlarmThreshold, + int lowerAlarmThreshold, + string sampleTime, + DateTime statStartTime, + DateTime statEndTime, + List lastPhr, + int triggerHighFreqHigh, + int triggerHighFreqLow) { + #region 选择心率值计算胎心 - var fetalHeartRate = await _serviceTDengine.GetFetalHeartRateAsync(heartRate.Serialno, (int)heartRate.HeartRate!); + /// 12个心率数据判定上限处理模式还是下限处理模式: + /// 1、12个数据的最大值 > 高频上限阀值,则按上限模式进行计算。取12个值的最小值心率值转换为胎心值。 + /// + /// 2、12个数据的最小值 < 高频下限阀值,则按下限模式进行计算。取正常范围内的最小值心率值转换为胎心值,不产生告警。 + /// 如果正常范围内没有值,则取异常范围最大值心率值转换为胎心值,并产生胎心过缓告警。 + + var phrFreqstatus = await _deviceCacheMgr.GetPregnancyHeartRateFreqStatusAsync(heartRate.Serialno); var isAbnormal = 0; + + //取正常范围内的最小值心率值转换为胎心值,不产生告警。 + var lastNormalPhr = lastPhr.Where(i => i.PregnancyHeartRate > triggerHighFreqLow && i.PregnancyHeartRate < triggerHighFreqHigh); + + int selectedHrValue = (int)heartRate.HeartRate!; + + if (lastPhr.Select(i => i.PregnancyHeartRate).Max() > triggerHighFreqHigh) + { + // 取12个值的最小值心率值转换为胎心值。 + selectedHrValue = lastPhr.Select(i => i.PregnancyHeartRate).Min(); + } + + if (lastPhr.Select(i => i.PregnancyHeartRate).Min() < triggerHighFreqLow) + { + // 有正常值 + if (lastNormalPhr.Any()) + { + // 2个数据的最小值 < 高频下限阀值,则按下限模式进行计算。取正常范围内的最小值心率值转换为胎心值,不产生告警 + selectedHrValue = lastPhr + .Where(i => i.PregnancyHeartRate > triggerHighFreqLow && i.PregnancyHeartRate < triggerHighFreqHigh) + .Select(i => i.PregnancyHeartRate) + .Min(); + } + // 无正常值 + if (!lastNormalPhr.Any()) + { + selectedHrValue = lastPhr + .Where(i => i.PregnancyHeartRate > triggerHighFreqLow && i.PregnancyHeartRate < triggerHighFreqHigh) + .Select(i => i.PregnancyHeartRate) + .Max(); + } + + } + _logger.LogInformation($"{heartRate.Serialno} 高频选择心率值:{selectedHrValue}"); + + var fetalHeartRate = await _serviceTDengine.GetFetalHeartRateAsync(heartRate.Serialno, selectedHrValue); + + #endregion + #region 判断是否够highFreqSampleTimes,540s var ts = DateTimeUtil.GetTimeDifferenceInSeconds((DateTime)heartRate.LastUpdate!, phrFreqstatus!.LastUpdate); // 判断是否够highFreqSampleTimes,540s @@ -1264,7 +1147,7 @@ namespace HealthMonitor.Service.Resolver { _logger.LogWarning($"{heartRate.Serialno} 高频持续不足10分钟,在高频警告下限阀值 {lowerAlarmThreshold} 和 高频警告上限阀值:{upperAlarmThreshold}之间,最后胎心值{fetalHeartRate},并且不告警"); } - + isAbnormal = 0; } // 超过highFreqSampleTimes,540s else @@ -1282,6 +1165,12 @@ namespace HealthMonitor.Service.Resolver _logger.LogWarning($"{heartRate.Serialno} 小于90,按90输出,计算因子:孕妇心率 {heartRate.HeartRate}, 周期:{statStartTime.ToString("yyyy-MM-dd HH:mm:ss")}----{statEndTime.ToString("yyyy-MM-dd HH:mm:ss")}"); } isAbnormal = fetalHeartRate > upperAlarmThreshold ? 1 : (fetalHeartRate < lowerAlarmThreshold ? 2 : 0); + + if (!lastNormalPhr.Any()) + { + // 偏低(过缓) + isAbnormal = 2; + } } #endregion @@ -1362,6 +1251,8 @@ namespace HealthMonitor.Service.Resolver } } + + private async Task SetIntervalTriggerAsync(string key, string imei, long interval, HisGpsHeartRate heartRate) { // var key = $"health_monitor/schedule_push/{type}/imei/{imei}"; diff --git a/HealthMonitor.WebApi/Worker.cs b/HealthMonitor.WebApi/Worker.cs index a56e971..de5b0b0 100644 --- a/HealthMonitor.WebApi/Worker.cs +++ b/HealthMonitor.WebApi/Worker.cs @@ -352,42 +352,46 @@ namespace HealthMonitor.WebApi _logger.LogInformation($"延时计算,{imeiDel} 高频状态持续{(FreqStatsEnd - phrFreqstatus!.LastUpdate).TotalSeconds} 秒,统计周期:{phrFreqstatus!.LastUpdate.ToString("yyyy-MM-dd HH:mm:ss")}----{FreqStatsEnd.ToString("yyyy-MM-dd HH:mm:ss")},高频心率平均值:{(int)avgPhr},将下发指令"); //await SaveAndPushFetalHeartRateAsync(triggerHeartRate, commonPHR, upperAlarmThreshold, lowerAlarmThreshold, avgPhr, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); - triggerHeartRate.HeartRate = (int)avgPhr; - //await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(triggerHeartRate, commonPHR, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); + //triggerHeartRate.HeartRate = (int)avgPhr; + ////await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(triggerHeartRate, commonPHR, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); - // 判断是否够highFreqSampleTimes,540s - var lastPhr = phrInFreqstatus; - // 最后一条高频心率 - var lastFreqHr = phrInFreqstatus.First(); - var ts = DateTimeUtil.GetTimeDifferenceInSeconds((DateTime)lastFreqHr.LastUpdate!, phrFreqstatus!.LastUpdate); - if (ts < highFreqSampleTimes) - { - //triggerHeartRate.HeartRate = lastPhr.Select(i => i.PregnancyHeartRate).Min(); - /// 不够10分钟最近12个数据生成胎心值 - - //int selectedHrValue = SelectValueFromFreqHeartRate(triggerHeartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); - int selectedHrValue = SelectValueFromFreqHeartRate(triggerHeartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); - triggerHeartRate.HeartRate = selectedHrValue; - _logger.LogInformation($"{triggerHeartRate.Serialno} 不够10分钟最近12个数据数据中取 {triggerHeartRate.HeartRate} 生成胎心值"); - } - else - { - //triggerHeartRate.HeartRate = lastPhr.Select(i => i.PregnancyHeartRate).Min(); - //int selectedHrValue = SelectValueFromFreqHeartRate(triggerHeartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); - int selectedHrValue = SelectValueFromFreqHeartRate(triggerHeartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); - triggerHeartRate.HeartRate = selectedHrValue; - /// 超过10分钟最近12个数据生成胎心值 - _logger.LogInformation($"{triggerHeartRate.Serialno} 超过10分钟最近12个数据数据中取 {triggerHeartRate.HeartRate} 生成胎心值"); - - } - + //// 判断是否够highFreqSampleTimes,540s + //var lastPhr = phrInFreqstatus; + //// 最后一条高频心率 + //var lastFreqHr = phrInFreqstatus.First(); + //var ts = DateTimeUtil.GetTimeDifferenceInSeconds((DateTime)lastFreqHr.LastUpdate!, phrFreqstatus!.LastUpdate); + //if (ts < highFreqSampleTimes) + //{ + // //triggerHeartRate.HeartRate = lastPhr.Select(i => i.PregnancyHeartRate).Min(); + // /// 不够10分钟最近12个数据生成胎心值 - triggerHeartRate.LastUpdate = lastFreqHr.LastUpdate; + // //int selectedHrValue = SelectValueFromFreqHeartRate(triggerHeartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); + // int selectedHrValue = SelectValueFromFreqHeartRate(triggerHeartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + // triggerHeartRate.HeartRate = selectedHrValue; + // _logger.LogInformation($"{triggerHeartRate.Serialno} 不够10分钟最近12个数据数据中取 {triggerHeartRate.HeartRate} 生成胎心值"); + //} + //else + //{ + // //triggerHeartRate.HeartRate = lastPhr.Select(i => i.PregnancyHeartRate).Min(); + // //int selectedHrValue = SelectValueFromFreqHeartRate(triggerHeartRate, triggerHighFreqHigh, triggerHighFreqLow, lastPhr); + // int selectedHrValue = SelectValueFromFreqHeartRate(triggerHeartRate.Serialno, triggerHighFreqHigh, triggerHighFreqLow, highFreqSampleTimes, phrFreqstatus, lastPhr); + // triggerHeartRate.HeartRate = selectedHrValue; + // /// 超过10分钟最近12个数据生成胎心值 + // _logger.LogInformation($"{triggerHeartRate.Serialno} 超过10分钟最近12个数据数据中取 {triggerHeartRate.HeartRate} 生成胎心值"); + //} + + + //triggerHeartRate.LastUpdate = lastFreqHr.LastUpdate; - _logger.LogInformation($"{triggerHeartRate.Serialno} 高频结束后计算胎心数据,防止结束后与常规心理的胎心处理过长,定时器时长highFreqSampleInterval触发的高频心率处理"); - await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(triggerHeartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); + //_logger.LogInformation($"{triggerHeartRate.Serialno} 高频结束后计算胎心数据,防止结束后与常规心理的胎心处理过长,定时器时长highFreqSampleInterval触发的高频心率处理"); + + //await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(triggerHeartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd); + + var lastPhr = phrInFreqstatus; + _logger.LogInformation($"{triggerHeartRate.Serialno} 高频结束后计算胎心数据,防止结束后与常规心理的胎心处理过长,定时器时长highFreqSampleInterval触发的高频心率处理"); + await SaveAndPushFetalHeartRateEndFreqHeartRateAsync(triggerHeartRate, commonPHR, highFreqSampleTimes, upperAlarmThreshold, lowerAlarmThreshold, DateTimeUtil.ConvertToTimeStamp(phrFreqstatus!.LastUpdate).ToString(), phrFreqstatus!.LastUpdate, FreqStatsEnd, lastPhr, triggerHighFreqHigh, triggerHighFreqLow); } else { @@ -2270,6 +2274,215 @@ namespace HealthMonitor.WebApi } } + /// + /// 高频胎心处理 + /// 1. 高频数据触发连续12个值都是正常的的高频心率处理 + /// 2. 高频结束后的highFreqSampleTimes=0的高频心率处理 + /// 3. 高频结束后的在highFreqSampleTimes>0 正常心率触发的高频心率处理(常态) + /// 4. 高频结束后的时间倒序的正常心率触发的高频心率处理 + /// 5. 高频结束后计算胎心数据,防止结束后与常规心理的胎心处理过长,定时器时长highFreqSampleInterval触发的高频心率处理 + /// 高频结束后超过9分钟且不在阈值内才告警 + /// + /// + /// + /// + /// + /// + /// + /// + /// + /// + private async Task SaveAndPushFetalHeartRateEndFreqHeartRateAsync( + HisGpsHeartRate heartRate, + PregnancyCommonHeartRateModel commonPHR, + int highFreqSampleTimes, + int upperAlarmThreshold, + int lowerAlarmThreshold, + string sampleTime, + DateTime statStartTime, + DateTime statEndTime, + List lastPhr, + int triggerHighFreqHigh, + int triggerHighFreqLow) + { + #region 选择心率值计算胎心 + + /// 12个心率数据判定上限处理模式还是下限处理模式: + /// 1、12个数据的最大值 > 高频上限阀值,则按上限模式进行计算。取12个值的最小值心率值转换为胎心值。 + /// + /// 2、12个数据的最小值 < 高频下限阀值,则按下限模式进行计算。取正常范围内的最小值心率值转换为胎心值,不产生告警。 + /// 如果正常范围内没有值,则取异常范围最大值心率值转换为胎心值,并产生胎心过缓告警。 + + + + var phrFreqstatus = await _deviceCacheMgr.GetPregnancyHeartRateFreqStatusAsync(heartRate.Serialno); + var isAbnormal = 0; + + //取正常范围内的最小值心率值转换为胎心值,不产生告警。 + var lastNormalPhr = lastPhr.Where(i => i.PregnancyHeartRate > triggerHighFreqLow && i.PregnancyHeartRate < triggerHighFreqHigh); + + int selectedHrValue = (int)heartRate.HeartRate!; + + if (lastPhr.Select(i => i.PregnancyHeartRate).Max() > triggerHighFreqHigh) + { + // 取12个值的最小值心率值转换为胎心值。 + selectedHrValue = lastPhr.Select(i => i.PregnancyHeartRate).Min(); + } + + if (lastPhr.Select(i => i.PregnancyHeartRate).Min() < triggerHighFreqLow) + { + // 有正常值 + if (lastNormalPhr.Any()) + { + // 2个数据的最小值 < 高频下限阀值,则按下限模式进行计算。取正常范围内的最小值心率值转换为胎心值,不产生告警 + selectedHrValue = lastPhr + .Where(i => i.PregnancyHeartRate > triggerHighFreqLow && i.PregnancyHeartRate < triggerHighFreqHigh) + .Select(i => i.PregnancyHeartRate) + .Min(); + } + // 无正常值 + if (!lastNormalPhr.Any()) + { + selectedHrValue = lastPhr + .Where(i => i.PregnancyHeartRate > triggerHighFreqLow && i.PregnancyHeartRate < triggerHighFreqHigh) + .Select(i => i.PregnancyHeartRate) + .Max(); + } + + } + _logger.LogInformation($"{heartRate.Serialno} 高频选择心率值:{selectedHrValue}"); + + var fetalHeartRate = await _serviceTDengine.GetFetalHeartRateAsync(heartRate.Serialno, selectedHrValue); + + #endregion + + #region 判断是否够highFreqSampleTimes,540s + var ts = DateTimeUtil.GetTimeDifferenceInSeconds((DateTime)heartRate.LastUpdate!, phrFreqstatus!.LastUpdate); + // 判断是否够highFreqSampleTimes,540s + ///高频时长不足10分钟停止高频的胎心值生成说明:最近12个数据的最小值生成胎心值, + ///对于小于高频下限阀值取高频下限阀值进行转换; + ///对于高于高频上限阀值取高频上限阀值进行转换。并输出相关日志后续进行数据分析。 + if (ts < highFreqSampleTimes) + { + if (fetalHeartRate > upperAlarmThreshold) + { + _logger.LogWarning($"{heartRate.Serialno} 高频持续不足10分钟,计算胎心值 {fetalHeartRate} 高于高频警告上限阀值{upperAlarmThreshold},最后胎心值{upperAlarmThreshold},并且不告警"); + fetalHeartRate = upperAlarmThreshold; + + + } + else if (fetalHeartRate < lowerAlarmThreshold) + { + _logger.LogWarning($"{heartRate.Serialno} 高频持续不足10分钟,计算胎心值 {fetalHeartRate} 低于高频警告下限阀值 {lowerAlarmThreshold},最后胎心值{lowerAlarmThreshold},并且不告警"); + fetalHeartRate = lowerAlarmThreshold; + } + else + { + _logger.LogWarning($"{heartRate.Serialno} 高频持续不足10分钟,在高频警告下限阀值 {lowerAlarmThreshold} 和 高频警告上限阀值:{upperAlarmThreshold}之间,最后胎心值{fetalHeartRate},并且不告警"); + } + isAbnormal = 0; + } + // 超过highFreqSampleTimes,540s + else + { + if (fetalHeartRate > 220) + { + fetalHeartRate = 220; + _logger.LogWarning($"{heartRate.Serialno} 大于220,按220输出,计算因子:孕妇心率 {heartRate.HeartRate},周期:{statStartTime.ToString("yyyy-MM-dd HH:mm:ss")}----{statEndTime.ToString("yyyy-MM-dd HH:mm:ss")}"); + } + + // 胎心的最小值调整为90,超过都按该值90 + if (fetalHeartRate < 90) + { + fetalHeartRate = 90; + _logger.LogWarning($"{heartRate.Serialno} 小于90,按90输出,计算因子:孕妇心率 {heartRate.HeartRate}, 周期:{statStartTime.ToString("yyyy-MM-dd HH:mm:ss")}----{statEndTime.ToString("yyyy-MM-dd HH:mm:ss")}"); + } + isAbnormal = fetalHeartRate > upperAlarmThreshold ? 1 : (fetalHeartRate < lowerAlarmThreshold ? 2 : 0); + + if (!lastNormalPhr.Any()) + { + // 偏低(过缓) + isAbnormal = 2; + } + } + #endregion + + + + _logger.LogInformation($"{heartRate.Serialno} 在 高频 状态,生成胎心值:{fetalHeartRate},统计周期:{statStartTime.ToString("yyyy-MM-dd HH:mm:ss")}----{statEndTime.ToString("yyyy-MM-dd HH:mm:ss")}"); + // 保存到 数据服务 MySQL 数据库 + HisGpsFetalHeartRate gpsFetalHeartRate = new() + { + FetalHeartRateId = Guid.NewGuid().ToString("D"), + PersonId = commonPHR!.PersonId, + Serialno = heartRate.Serialno, + HeartRate = fetalHeartRate, + SampleTime = sampleTime.Length > 10 ? sampleTime.Substring(0, 10) : sampleTime, + IsAbnormal = isAbnormal, + StatStartTime = statStartTime, + StatEndTime = statEndTime,//commonPHR.StatEndTime, + CreateTime = DateTime.Now, + Method = 1, + IsDisplay = 1, + DeviceKey = commonPHR!.DeviceKey + }; + await _hisFetalHeartApiClient.AddAsync(gpsFetalHeartRate).ConfigureAwait(false); + + #region 高频心率计算胎心数据到iot设备 + + //if (phrFreqstatus != null && isAbnormal != 0) + //{ + // await _serviceIotApi.SetFetalHeartRateConfig(heartRate.Serialno, fetalHeartRate, sampleTime, isAbnormal); + //} + // 高频有数据都推送到iot + + await _serviceIotApi.SetFetalHeartRateConfig(heartRate.Serialno, fetalHeartRate, sampleTime, isAbnormal); + #endregion + var device = await _deviceCacheMgr.GetDeviceBySerialNoAsync(heartRate.Serialno).ConfigureAwait(false); + var fhrMsgId = $"{heartRate.Serialno}-{sampleTime}-{Guid.NewGuid().ToString("D")[^3..]}"; + var fhrMsgTime = DateTimeUtil.GetDateTimeFromUnixTimeMilliseconds(long.Parse(sampleTime.Length < 13 ? sampleTime.PadRight(13, '0') : sampleTime)).ToString("yyyy-MM-dd HH:mm:ss"); + // 胎心数据推送到第三方 + var topic = "topic.push.third"; + var fhrThridMsg = new + { + messageId = fhrMsgId, + topic = topic, + time = fhrMsgTime, + data = new + { + imei = heartRate.Serialno, + value = fetalHeartRate, + isAbnormal, + type = "fetalHeart" + } + }; + await _serviceMqProcess.ProcessIMEIEventMessageAsync(fhrMsgId, topic, 31, fhrThridMsg).ConfigureAwait(false); + + // 胎心数据推送到微信 + if (isAbnormal != 0) + { + + topic = "topic.push.wx"; + var fhrMsg = new + { + messageId = fhrMsgId, + topic = topic, + time = fhrMsgTime, + data = new + { + deviceId = device?.DeviceId, + imei = heartRate.Serialno, + alarmTypeId = 12, + alarmDeviceName = heartRate.Serialno, + alarmRemarks = JsonConvert.SerializeObject(new { fetalHeartValue = fetalHeartRate, isAbnormal = isAbnormal }), + address = string.Empty, + deviceKey = device?.DeviceId + } + }; + await _serviceMqProcess.ProcessIMEIEventMessageAsync(fhrMsgId, topic, fhrMsg).ConfigureAwait(false); + + } + } /// /// 去除高频数据