83 lines
2.4 KiB
C#
83 lines
2.4 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.Linq;
|
|
|
|
namespace HydraulicSimulator.Models
|
|
{
|
|
/// <summary>
|
|
/// Rama (elementos en serie)
|
|
/// </summary>
|
|
public class Branch
|
|
{
|
|
public string N1 { get; set; }
|
|
public string N2 { get; set; }
|
|
public List<Element> Elements { get; set; }
|
|
public string Name { get; set; }
|
|
public double Q { get; set; } = 0.0; // caudal actual (signo n1->n2)
|
|
|
|
public Branch(string n1, string n2, List<Element> elements, string name = "")
|
|
{
|
|
N1 = n1;
|
|
N2 = n2;
|
|
Elements = new List<Element>(elements);
|
|
Name = string.IsNullOrEmpty(name) ? $"{n1}->{n2}" : name;
|
|
}
|
|
|
|
public double Dp(double q, Fluid fluid)
|
|
{
|
|
return Elements.Sum(e => e.Dp(q, fluid));
|
|
}
|
|
|
|
public double DdpDq(double q, Fluid fluid)
|
|
{
|
|
return Elements.Sum(e => e.DdpDq(q, fluid));
|
|
}
|
|
|
|
/// <summary>
|
|
/// Resuelve ΔP(q) = dpTarget por Newton 1D con amortiguación.
|
|
/// </summary>
|
|
public double SolveFlowGivenDp(double dpTarget, Fluid fluid)
|
|
{
|
|
var q = Q;
|
|
var qMax = 1.0; // m³/s máximo razonable
|
|
|
|
for (int i = 0; i < 50; i++) // más iteraciones
|
|
{
|
|
var f = Dp(q, fluid) - dpTarget;
|
|
var df = DdpDq(q, fluid);
|
|
|
|
// Verificar división por cero
|
|
if (Math.Abs(df) < 1e-20)
|
|
df = 1e-10;
|
|
|
|
var step = f / df;
|
|
|
|
// Limitar el paso para estabilidad
|
|
var maxStep = Math.Min(0.1, Math.Abs(q) * 0.5 + 0.01);
|
|
if (Math.Abs(step) > maxStep)
|
|
step = Math.Sign(step) * maxStep;
|
|
|
|
var qNew = q - step;
|
|
|
|
// Limitar caudal dentro de rango razonable
|
|
qNew = Math.Max(-qMax, Math.Min(qMax, qNew));
|
|
|
|
// Amortiguación más conservadora
|
|
var relax = i < 10 ? 0.3 : 0.1;
|
|
q = (1 - relax) * q + relax * qNew;
|
|
|
|
// Criterio de convergencia más estricto
|
|
if (Math.Abs(f) < 1e-1) // Pa
|
|
break;
|
|
|
|
// Debug: evitar divergencia extrema
|
|
if (Math.Abs(q) > qMax)
|
|
q = Math.Sign(q) * qMax * 0.1;
|
|
}
|
|
|
|
Q = q;
|
|
return q;
|
|
}
|
|
}
|
|
}
|