You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

344 lines
14 KiB

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace SmartAquaViewer.DataAnalisys
{
using System;
10 months ago
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
10 months ago
using System.Security.Policy;
10 months ago
[Table("WaterQuality")]
public class WaterQualityVO
{
10 months ago
[Key]
[DatabaseGenerated(DatabaseGeneratedOption.Identity)] // 자동 증가
public int Id { get; set; } // PK, Auto Increment
/// <summary>
10 months ago
/// 저수조
/// </summary>
10 months ago
public WaterTank WaterTank { get; set; }
/// <summary>
10 months ago
/// 여과 시스템
/// </summary>
10 months ago
public FilteringSystem FilteringSystem { get; set; }
/// <summary>
10 months ago
/// 살균 시스템
/// </summary>
10 months ago
public SterilizingSystem SterilizingSystem { get; set; }
/// <summary>
/// 측정 시각
/// </summary>
public DateTime Timestamp { get; set; }
public WaterQualityVO() { }
10 months ago
public WaterQualityVO(
int waterTankNum, double waterTankDOValue, double waterTankPh, double waterTankORP, double waterTankTemperature, double waterTankFlowRate,
bool sandFilterPower,
double sumpPH, double sumpORP, double sumpWaterLevel, double sumpFlowRate, double sumpTemperature,
bool circulationPumpPower, string? inverterControllerStatus, double flowRate,
bool heatPumpPower, double heatPumpTemperature, bool airBlowerPower,
bool ozoneGeneratorPower,
string uvSterilizerId, bool uvSterilizerPower,
bool ozoneDissolverPower, double ozoneDissolverPressure,
bool excessOzoneDestroyerPower,
DateTime timestamp)
{
10 months ago
WaterTank = new WaterTank(waterTankNum, waterTankDOValue, waterTankPh, waterTankORP, waterTankTemperature, waterTankFlowRate);
FilteringSystem = new FilteringSystem(sandFilterPower, sumpPH, sumpORP, sumpWaterLevel, sumpFlowRate, sumpTemperature,
circulationPumpPower, inverterControllerStatus, flowRate,
heatPumpPower, heatPumpTemperature, airBlowerPower);
SterilizingSystem = new SterilizingSystem(ozoneGeneratorPower, uvSterilizerId, uvSterilizerPower,
ozoneDissolverPower, ozoneDissolverPressure, excessOzoneDestroyerPower);
}
public override string ToString()
{
10 months ago
//return $"Tank#{WaterTankNum} [{Timestamp}] DO: {DO} mg/L, pH: {PH}, Temp: {Temperature}°C, " +
// $"Level: {WaterLevel} m, Flow: {FlowRate} m³/s, EC: {ElectricalConductivity} µS/cm, " +
// $"Turbidity: {Turbidity} NTU, Salinity: {Salinity} ppt, ORP: {ORP} mV, " +
// $"TSS: {TSS} mg/L, TN: {TotalNitrogen} mg/L, TP: {TotalPhosphorus} mg/L";
return $"[{Timestamp}] " +
$"[Tank#{WaterTank.WaterTankNum}, DO: {WaterTank.DO} mg/L, pH: {WaterTank.PH}, ORP: {WaterTank.ORP} mV, Temp: {WaterTank.Temperature}°C, FlowRate: {WaterTank.FlowRate} m³/s]" +
$"[SandFilter: {(FilteringSystem.SandFilterPower ? "ON" : "OFF")}, " +
$"(SumpTank) pH: {FilteringSystem.SumpPH}, ORP: {FilteringSystem.SumpORP} mV, WaterLevel: {FilteringSystem.SumpWaterLevel} m, FlowRate: {FilteringSystem.SumpFlowRate} m³/s, Temperature: {FilteringSystem.SumpTemperature}°C," +
$"HeatPump: {(FilteringSystem.HeatPumpPower ? "ON" : "OFF")}, HeatPumpTemperature: {FilteringSystem.HeatPumpTemperature}°C, AirBlower: {(FilteringSystem.AirBlowerPower ? "ON" : "OFF")}]" +
$"[OzoneGenerator: {(SterilizingSystem.OzoneGeneratorPower ? "ON" : "OFF")}," +
$"UVSterilizerId: {SterilizingSystem.UVSterilizerId}, UVSterilizer: {(SterilizingSystem.UVSterilizerPower ? "ON" : "OFF")}," +
$"OzoneDissolver: {SterilizingSystem.OzoneDissolverPower}, OzoneDissolverPressure: {SterilizingSystem.OzoneDissolverPressure} kPa," +
$"ExcessOzoneDestroyer: {(SterilizingSystem.ExcessOzoneDestroyerPower ? "ON" : "OFF")}]";
}
/// <summary>
/// 지정 기간 동안 임의의 수질 데이터를 생성합니다.
/// </summary>
public static List<WaterQualityVO> GetSampleData(DateTime start, DateTime end, int totalRowsCount)
{
var list = new List<WaterQualityVO>();
var rand = new Random();
if (totalRowsCount <= 0) return list;
double totalSeconds;
if (start == end)
{
// 같은 날짜면 하루(24시간) 기준으로 균등 분할
totalSeconds = 24 * 60 * 60; // 86,400초
}
else
{
totalSeconds = (end - start).TotalSeconds;
if (totalSeconds < 0) throw new ArgumentException("end 날짜는 start 날짜보다 같거나 커야 합니다.");
}
double stepSeconds = totalSeconds / totalRowsCount;
for (int i = 0; i < totalRowsCount; i++)
{
DateTime ts = start.AddSeconds(stepSeconds * i);
10 months ago
//var vo = new WaterQualityVO
//{
// WaterTankNum = rand.Next(1, 6), // 1~5번 탱크
// DO = Math.Round(rand.NextDouble() * 5 + 5, 2), // 5~10 mg/L
// PH = Math.Round(rand.NextDouble() * 2 + 6, 2), // 6~8
// Temperature = Math.Round(rand.NextDouble() * 10 + 15, 2), // 15~25°C
// WaterLevel = Math.Round(rand.NextDouble() * 2 + 1, 2), // 1~3 m
// FlowRate = Math.Round(rand.NextDouble() * 5 + 1, 2), // 1~6 m³/s
// ElectricalConductivity = Math.Round(rand.NextDouble() * 500 + 200, 2), // 200~700 µS/cm
// Turbidity = Math.Round(rand.NextDouble() * 5 + 1, 2), // 1~6 NTU
// Salinity = Math.Round(rand.NextDouble() * 5, 2), // 0~5 ppt
// ORP = Math.Round(rand.NextDouble() * 200 + 100, 2), // 100~300 mV
// TSS = Math.Round(rand.NextDouble() * 20 + 5, 2), // 5~25 mg/L
// TotalNitrogen = Math.Round(rand.NextDouble() * 2 + 0.5, 2), // 0.5~2.5 mg/L
// TotalPhosphorus = Math.Round(rand.NextDouble() * 0.5 + 0.05, 3), // 0.05~0.55 mg/L
// Timestamp = ts
//};
var vo = new WaterQualityVO
{
10 months ago
WaterTank = new WaterTank(
waterTankNum: rand.Next(1, 6), // 1~5번 탱크
doValue: Math.Round(rand.NextDouble() * 5 + 5, 2), // 5~10 mg/L
ph: Math.Round(rand.NextDouble() * 2 + 6, 2), // 6~8
orp: Math.Round(rand.NextDouble() * 200 + 100, 2), // 100~300 mV
temperature: Math.Round(rand.NextDouble() * 10 + 15, 2), // 15~25°C
flowRate: Math.Round(rand.NextDouble() * 5 + 1, 2) // 1~6 m³/s
),
FilteringSystem = new FilteringSystem(
sandFilterPower: rand.Next(0, 2) == 1, // true or false
sumpPH: Math.Round(rand.NextDouble() * 2 + 6, 2), // 6~8
sumpORP: Math.Round(rand.NextDouble() * 200 + 100, 2), // 100~300 mV
sumpWaterLevel: Math.Round(rand.NextDouble() * 2 + 1, 2), // 1~3 m
sumpFlowRate: Math.Round(rand.NextDouble() * 5 + 1, 2), // 1~6 m³/s
sumpTemperature: Math.Round(rand.NextDouble() * 10 + 15, 2), // 15~25°C
circulationPumpPower: rand.Next(0, 2) == 1, // true or false
inverterControllerStatus: rand.Next(0, 2) == 1 ? "Normal" : "Error", // "Normal" or "Error"
flowRate: Math.Round(rand.NextDouble() * 5 + 1, 2), // 1~6 m³/s
heatPumpPower: rand.Next(0, 2) == 1, // true or false
heatPumpTemperature: Math.Round(rand.NextDouble() * 10 + 15, 2), // 15~25°C
airBlowerPower: rand.Next(0, 2) == 1 // true or false
),
SterilizingSystem = new SterilizingSystem(
ozoneGeneratorPower: rand.Next(0, 2) == 1, // true or false
uvSterilizerId: "UV" + rand.Next(1, 100), // UV1, UV2, ...
uvSterilizerPower: rand.Next(0, 2) == 1, // true or false
ozoneDissolverPower: rand.Next(0, 2) == 1, // true or false
ozoneDissolverPressure: Math.Round(rand.NextDouble() * 100 + 50, 2), // 50~150 kPa
excessOzoneDestroyerPower: rand.Next(0, 2) == 1 // true or false
)
};
list.Add(vo);
}
return list;
}
}
10 months ago
public class WaterTank
{
/// <summary>
/// 저수조 번호
/// </summary>
public int WaterTankNum { get; set; }
10 months ago
/// <summary>
/// Dissolved Oxygen (mg/L)
/// </summary>
public double DO { get; set; }
10 months ago
/// <summary>
/// pH (산도)
/// </summary>
public double PH { get; set; }
/// <summary>
/// 산화환원전위 (mV)
/// </summary>
public double ORP { get; set; }
/// <summary>
/// 수온 (°C)
/// </summary>
public double Temperature { get; set; }
/// <summary>
/// 유량 (m³/s)
/// </summary>
public double FlowRate { get; set; }
public WaterTank(int waterTankNum, double doValue, double ph, double orp, double temperature, double flowRate)
{
WaterTankNum = waterTankNum;
DO = doValue;
PH = ph;
ORP = orp;
Temperature = temperature;
FlowRate = flowRate;
}
}
public class FilteringSystem
{
/// <summary>
/// 모래여과기 전원 (true: ON, false: OFF)
/// </summary>
public bool SandFilterPower { get; set; }
/// <summary>
/// 섬프탱크 pH (산도)
/// </summary>
public double SumpPH { get; set; }
/// <summary>
/// 섬프탱크 산화환원전위 (mV)
/// </summary>
public double SumpORP { get; set; }
/// <summary>
/// 섬프탱크 수위 (m)
/// </summary>
public double SumpWaterLevel { get; set; }
/// <summary>
/// 섬프탱크 유량 (m³/s)
/// </summary>
public double SumpFlowRate { get; set; }
/// <summary>
/// 섬프탱크 수온 (°C)
/// </summary>
public double SumpTemperature { get; set; }
/// <summary>
/// 순환펌프 전원 (true: ON, false: OFF)
/// </summary>
public bool CirculationPumpPower { get; set; }
/// <summary>
/// 인버터 제어기 상태
/// </summary>
public string? InverterControllerStatus { get; set; }
/// <summary>
/// 순환펌프 유량 (m³/s)
/// </summary>
public double FlowRate { get; set; }
/// <summary>
/// 히트펌프 전원 (true: ON, false: OFF)
/// </summary>
public bool HeatPumpPower { get; set; }
/// <summary>
/// 히트펌프 온도 (°C)
/// </summary>
public double HeatPumpTemperature { get; set; }
/// <summary>
/// 에어브로와 전원 (true: ON, false: OFF)
/// </summary>
public bool AirBlowerPower { get; set; }
public FilteringSystem(bool sandFilterPower,
double sumpPH, double sumpORP, double sumpWaterLevel, double sumpFlowRate, double sumpTemperature,
bool circulationPumpPower, string? inverterControllerStatus, double flowRate,
bool heatPumpPower, double heatPumpTemperature, bool airBlowerPower)
{
SandFilterPower = sandFilterPower;
SumpPH = sumpPH;
SumpORP = sumpORP;
SumpWaterLevel = sumpWaterLevel;
SumpFlowRate = sumpFlowRate;
SumpTemperature = sumpTemperature;
CirculationPumpPower = circulationPumpPower;
InverterControllerStatus = inverterControllerStatus;
FlowRate = flowRate;
HeatPumpPower = heatPumpPower;
HeatPumpTemperature = heatPumpTemperature;
AirBlowerPower = airBlowerPower;
}
}
public class SterilizingSystem
{
/// <summary>
/// 오존 발생기 전원 (true: ON, false: OFF)
/// </summary>
public bool OzoneGeneratorPower { get; set; }
/// <summary>
/// 자외선 살균기 ID
/// </summary>
public string UVSterilizerId { get; set; }
/// <summary>
/// 자외선 살균기 전원 (true: ON, false: OFF)
/// </summary>
public bool UVSterilizerPower { get; set; }
/// <summary>
/// 오존용해장치 전원 (true: ON, false: OFF)
/// </summary>
public bool OzoneDissolverPower { get; set; }
/// <summary>
/// 오존용해장치 압력 (kPa)
/// </summary>
public double OzoneDissolverPressure { get; set; }
/// <summary>
/// 배오존장치 전원 (true: ON, false: OFF)
/// </summary>
public bool ExcessOzoneDestroyerPower { get; set; }
public SterilizingSystem(bool ozoneGeneratorPower,
string uvSterilizerId, bool uvSterilizerPower,
bool ozoneDissolverPower, double ozoneDissolverPressure,
bool excessOzoneDestroyerPower)
{
OzoneGeneratorPower = ozoneGeneratorPower;
UVSterilizerId = uvSterilizerId;
UVSterilizerPower = uvSterilizerPower;
OzoneDissolverPower = ozoneDissolverPower;
OzoneDissolverPressure = ozoneDissolverPressure;
ExcessOzoneDestroyerPower = excessOzoneDestroyerPower;
}
}
}