Правки к аналитике

This commit is contained in:
KharchenkoVV 2021-07-20 11:24:57 +05:00
parent faaa4bedda
commit 28c42da58a
4 changed files with 83 additions and 75 deletions

View File

@ -14,6 +14,6 @@ namespace AsbCloudApp.Services
DateTime begin = default, DateTime end = default);
IEnumerable<OperationInfoDto> GetOperationsToInterval(int wellId,
int intervalHoursTimestamp, int workBeginTimestamp);
TelemetryAnalysis GetDrillingAnalysis(IEnumerable<DataSaubBase> dataSaubBases);
void SaveAnalytics(DataSaubBase dataSaub);
}
}

View File

@ -12,14 +12,17 @@ namespace AsbCloudInfrastructure.Services
{
private readonly IAsbCloudDbContext db;
private readonly ITelemetryService telemetryService;
private readonly ISaubDataCache saubDataCache;
private readonly CacheTable<Operation> cacheOperations;
private readonly OperationDetectorService operationDetectorService;
private readonly IEnumerable<Operation> operations;
public AnalyticsService(IAsbCloudDbContext db, ITelemetryService telemetryService, CacheDb cacheDb)
public AnalyticsService(IAsbCloudDbContext db, ITelemetryService telemetryService,
ISaubDataCache saubDataCache, CacheDb cacheDb)
{
this.db = db;
this.telemetryService = telemetryService;
this.saubDataCache = saubDataCache;
cacheOperations = cacheDb.GetCachedTable<Operation>((AsbCloudDbContext)db);
operations = cacheOperations.Select(c => true);
operationDetectorService = new OperationDetectorService(operations);
@ -146,7 +149,36 @@ namespace AsbCloudInfrastructure.Services
return operationsGroupedByInterval;
}
public TelemetryAnalysis GetDrillingAnalysis(IEnumerable<DataSaubBase> dataSaubBases)
public void SaveAnalytics(DataSaubBase dataSaub)
{
saubDataCache.AddData(dataSaub);
if (saubDataCache.GetOrCreateCache(dataSaub.IdTelemetry).Count() > 1)
{
var dataSaubs = saubDataCache.GetOrCreateCache(dataSaub.IdTelemetry)
.OrderBy(d => d.Date);
var telemetryAnalysis = GetDrillingAnalysis(dataSaubs);
if (saubDataCache.CurrentAnalysis is null)
saubDataCache.CurrentAnalysis = telemetryAnalysis;
if (saubDataCache.CurrentAnalysis.IdOperation == telemetryAnalysis.IdOperation)
{
saubDataCache.CurrentAnalysis.Duration +=
telemetryAnalysis.Duration;
saubDataCache.CurrentAnalysis.OperationEndDepth = dataSaub.WellDepth;
}
else
{
db.TelemetryAnalysis.Add(saubDataCache.CurrentAnalysis);
saubDataCache.CurrentAnalysis = telemetryAnalysis;
saubDataCache.CurrentAnalysis.OperationStartDepth = dataSaub.WellDepth;
}
}
}
private TelemetryAnalysis GetDrillingAnalysis(IEnumerable<DataSaubBase> dataSaubBases)
{
var lastSaubDate = dataSaubBases.Last().Date;
@ -169,16 +201,16 @@ namespace AsbCloudInfrastructure.Services
.Select(s => (Value: (double)s.HookWeight,
(s.Date - dataSaubBases.First().Date).TotalSeconds));
var wellDepthChangingIndex = LinearFunctionCalculator.GetAForLinearFormula(saubWellDepths);
var bitPositionChangingIndex = LinearFunctionCalculator.GetAForLinearFormula(saubBitDepths);
var blockPositionChangingIndex = LinearFunctionCalculator.GetAForLinearFormula(saubBlockPositions);
var rotorSpeedChangingIndex = LinearFunctionCalculator.GetAForLinearFormula(saubRotorSpeeds);
var pressureChangingIndex = LinearFunctionCalculator.GetAForLinearFormula(saubPressures);
var hookWeightChangingIndex = LinearFunctionCalculator.GetAForLinearFormula(saubHookWeights);
var wellDepthChangingIndex = new InterpolationLine(saubWellDepths).GetAForLinearFormula();
var bitPositionChangingIndex = new InterpolationLine(saubBitDepths).GetAForLinearFormula();
var blockPositionChangingIndex = new InterpolationLine(saubBlockPositions).GetAForLinearFormula();
var rotorSpeedChangingIndex = new InterpolationLine(saubRotorSpeeds).GetAForLinearFormula();
var pressureChangingIndex = new InterpolationLine(saubPressures).GetAForLinearFormula();
var hookWeightChangingIndex = new InterpolationLine(saubHookWeights).GetAForLinearFormula();
var IsBlockRising = LinearFunctionCalculator.IsValueGoesDown(blockPositionChangingIndex, -0.0001);
var IsBlockGoesDown = LinearFunctionCalculator.IsValueGoesUp(blockPositionChangingIndex, 0.0001);
var IsBlockStandsStill = LinearFunctionCalculator.IsValueNotChanges(blockPositionChangingIndex, (0.0001, -0.0001));
var IsBlockRising = InterpolationLine.IsValueDecreases(blockPositionChangingIndex, -0.0001);
var IsBlockGoesDown = InterpolationLine.IsValueIncreases(blockPositionChangingIndex, 0.0001);
var IsBlockStandsStill = InterpolationLine.IsValueNotChanges(blockPositionChangingIndex, (0.0001, -0.0001));
var drillingAnalysis = new TelemetryAnalysis
{
@ -187,19 +219,19 @@ namespace AsbCloudInfrastructure.Services
Duration = (int)(dataSaubBases.Last().Date - dataSaubBases.ElementAt(dataSaubBases.Count() - 2).Date).TotalSeconds,
OperationStartDepth = null,
OperationEndDepth = null,
IsWellDepthDecreasing = LinearFunctionCalculator.IsValueGoesDown(wellDepthChangingIndex, -0.0001),
IsWellDepthIncreasing = LinearFunctionCalculator.IsValueGoesUp(wellDepthChangingIndex, 0.0001),
IsBitPositionDecreasing = LinearFunctionCalculator.IsValueGoesDown(bitPositionChangingIndex, -0.0001),
IsBitPositionIncreasing = LinearFunctionCalculator.IsValueGoesUp(bitPositionChangingIndex, 0.0001),
IsBitDepthLess20 = LinearFunctionCalculator.IsAverageLessThanBound(saubBitDepths, 20),
IsBlockPositionDecreasing = LinearFunctionCalculator.IsValueGoesDown(blockPositionChangingIndex, -0.0001),
IsBlockPositionIncreasing = LinearFunctionCalculator.IsValueGoesUp(blockPositionChangingIndex, 0.0001),
IsRotorSpeedLt3 = LinearFunctionCalculator.IsAverageLessThanBound(saubRotorSpeeds, 3),
IsRotorSpeedGt3 = LinearFunctionCalculator.IsAverageMoreThanBound(saubRotorSpeeds, 3),
IsPressureLt20 = LinearFunctionCalculator.IsAverageLessThanBound(saubPressures, 20),
IsPressureGt20 = LinearFunctionCalculator.IsAverageMoreThanBound(saubPressures, 20),
IsHookWeightNotChanges = LinearFunctionCalculator.IsValueNotChanges(hookWeightChangingIndex, (0.0001, -0.0001)),
IsHookWeightLt3 = LinearFunctionCalculator.IsAverageLessThanBound(saubHookWeights, 3),
IsWellDepthDecreasing = InterpolationLine.IsValueDecreases(wellDepthChangingIndex, -0.0001),
IsWellDepthIncreasing = InterpolationLine.IsValueIncreases(wellDepthChangingIndex, 0.0001),
IsBitPositionDecreasing = InterpolationLine.IsValueDecreases(bitPositionChangingIndex, -0.0001),
IsBitPositionIncreasing = InterpolationLine.IsValueIncreases(bitPositionChangingIndex, 0.0001),
IsBitDepthLess20 = InterpolationLine.IsAverageLessThanBound(saubBitDepths, 20),
IsBlockPositionDecreasing = InterpolationLine.IsValueDecreases(blockPositionChangingIndex, -0.0001),
IsBlockPositionIncreasing = InterpolationLine.IsValueIncreases(blockPositionChangingIndex, 0.0001),
IsRotorSpeedLt3 = InterpolationLine.IsAverageLessThanBound(saubRotorSpeeds, 3),
IsRotorSpeedGt3 = InterpolationLine.IsAverageMoreThanBound(saubRotorSpeeds, 3),
IsPressureLt20 = InterpolationLine.IsAverageLessThanBound(saubPressures, 20),
IsPressureGt20 = InterpolationLine.IsAverageMoreThanBound(saubPressures, 20),
IsHookWeightNotChanges = InterpolationLine.IsValueNotChanges(hookWeightChangingIndex, (0.0001, -0.0001)),
IsHookWeightLt3 = InterpolationLine.IsAverageLessThanBound(saubHookWeights, 3),
IdOperation = 1
};

View File

@ -99,31 +99,7 @@ namespace AsbCloudInfrastructure.Services
dataSaub.IdTelemetry = telemetryId;
db.DataSaubBases.Add(dataSaub);
saubDataCache.AddData(dataSaub);
if (saubDataCache.GetOrCreateCache(dataSaub.IdTelemetry).Count() > 1)
{
var dataSaubs = saubDataCache.GetOrCreateCache(dataSaub.IdTelemetry)
.OrderBy(d => d.Date);
var telemetryAnalysis = analyticsService.GetDrillingAnalysis(dataSaubs);
if(saubDataCache.CurrentAnalysis is null)
saubDataCache.CurrentAnalysis = telemetryAnalysis;
if (saubDataCache.CurrentAnalysis.IdOperation == telemetryAnalysis.IdOperation)
{
saubDataCache.CurrentAnalysis.Duration +=
telemetryAnalysis.Duration;
saubDataCache.CurrentAnalysis.OperationEndDepth = item.WellDepth;
}
else
{
db.TelemetryAnalysis.Add(saubDataCache.CurrentAnalysis);
saubDataCache.CurrentAnalysis = telemetryAnalysis;
saubDataCache.CurrentAnalysis.OperationStartDepth = item.WellDepth;
}
}
analyticsService.SaveAnalytics(dataSaub);
}
db.SaveChanges();

View File

@ -3,22 +3,38 @@ using System.Linq;
namespace AsbCloudInfrastructure.Services
{
public static class LinearFunctionCalculator
public class InterpolationLine
{
public static double GetAForLinearFormula(IEnumerable<(double value, double timestamp)> rawData)
{
var (xSum, ySum, xySum, x2Sum) = GetFormulaVariables(rawData);
private readonly decimal xSum;
private readonly decimal ySum;
private readonly decimal xySum;
private readonly decimal x2Sum;
private readonly IEnumerable<(double value, double timestamp)> rawData = new List<(double value, double timestamp)>();
public InterpolationLine(IEnumerable<(double value, double timestamp)> rawData)
{
var data = rawData.Select((d) => new
{
X = d.timestamp,
Y = d.value
});
xSum = (decimal)data.Sum(d => d.X);
ySum = (decimal)data.Sum(d => d.Y);
xySum = (decimal)data.Sum(d => d.X * d.Y);
x2Sum = (decimal)data.Sum(d => d.X * d.X);
this.rawData = rawData;
}
public double GetAForLinearFormula()
{
var result = (xSum * ySum - rawData.Count() * xySum) /
(xSum * xSum - rawData.Count() * x2Sum);
return (double)result;
}
public static double GetBForLinearFormula(IEnumerable<(double value, double timestamp)> rawData)
public double GetBForLinearFormula()
{
var (xSum, ySum, xySum, x2Sum) = GetFormulaVariables(rawData);
var result = (xSum * xySum - x2Sum * ySum) /
(xSum * xSum - rawData.Count() * x2Sum);
@ -29,10 +45,10 @@ namespace AsbCloudInfrastructure.Services
(double upperBound, double lowerBound) bounds) =>
value < bounds.upperBound && value > bounds.lowerBound;
public static bool IsValueGoesUp(double value, double bound) =>
public static bool IsValueIncreases(double value, double bound) =>
value > bound;
public static bool IsValueGoesDown(double value, double bound) =>
public static bool IsValueDecreases(double value, double bound) =>
value < bound;
public static bool IsAverageLessThanBound(IEnumerable<(double Value, double TotalSeconds)> values,
@ -42,21 +58,5 @@ namespace AsbCloudInfrastructure.Services
public static bool IsAverageMoreThanBound(IEnumerable<(double Value, double TotalSeconds)> values,
double bound) =>
(values.Sum(s => s.Value) / values.Count()) >= bound;
private static (decimal xSum, decimal ySum, decimal xySum, decimal x2Sum) GetFormulaVariables(
IEnumerable<(double value, double timestamp)> rawData)
{
var data = rawData.Select((d) => new
{
X = d.timestamp,
Y = d.value
});
var xSum = (decimal)data.Sum(d => d.X);
var ySum = (decimal)data.Sum(d => d.Y);
var xySum = (decimal)data.Sum(d => d.X * d.Y);
var x2Sum = (decimal)data.Sum(d => d.X * d.X);
return (xSum, ySum, xySum, x2Sum);
}
}
}