71 lines
3.1 KiB
C#
71 lines
3.1 KiB
C#
using System.Collections.Generic;
|
||
using CounterDrone.Core.Algorithms;
|
||
using CounterDrone.Core.Models;
|
||
using Xunit;
|
||
|
||
namespace CounterDrone.Core.Tests
|
||
{
|
||
/// <summary>验证三阶段扩散模型下推荐算法的参数合理性</summary>
|
||
public class DispersionAdvisorRealityTests
|
||
{
|
||
private ThreatProfile CreatePistonThreat(float speed = 200, float length = 20000)
|
||
{
|
||
return new ThreatProfile
|
||
{
|
||
Environment = new CombatScene { WindSpeed = 3, WindDirection = (int)WindDirection.W },
|
||
Targets = new List<TargetConfig>
|
||
{
|
||
new TargetConfig { PowerType = (int)PowerType.Piston, Quantity = 1,
|
||
TypicalSpeed = speed, TypicalAltitude = 500 },
|
||
},
|
||
Route = new RoutePlan { FormationMode = (int)FormationMode.Single },
|
||
Waypoints = new List<Waypoint>
|
||
{
|
||
new Waypoint { PosX = 0, PosY = 500, PosZ = 0 },
|
||
new Waypoint { PosX = length, PosY = 500, PosZ = 0 },
|
||
},
|
||
};
|
||
}
|
||
|
||
[Fact]
|
||
public void Piston_200kmh_20km_ProducesReasonableSalvo()
|
||
{
|
||
var advisor = new DefaultDefenseAdvisor(DefaultAmmunition.GetAll());
|
||
var rec = advisor.Recommend(CreatePistonThreat());
|
||
|
||
// 基本断言
|
||
Assert.Equal(AerosolType.InertGas, rec.Best.RecommendedAerosolType);
|
||
Assert.True(rec.Best.SalvoRounds >= 1, $"齐射数={rec.Best.SalvoRounds},应≥1");
|
||
Assert.True(rec.Best.SalvoSpacing > 0, $"间隔={rec.Best.SalvoSpacing}m,应>0");
|
||
Assert.True(rec.Best.RecommendedCloud.RecommendedTiming > 0,
|
||
$"推荐时机={rec.Best.RecommendedCloud.RecommendedTiming}s,应>0");
|
||
|
||
// 检查膨胀时间
|
||
var ammo = DefaultAmmunition.GetByType(AerosolType.InertGas);
|
||
var r0 = 3.3f * System.Math.Pow(ammo.BurstChargeKg, 0.32);
|
||
var k = ammo.TurbulentExpansionK;
|
||
var halfTime = 20000f / (200f / 3.6f) / 2f;
|
||
var effectiveR = r0 + k * System.Math.Sqrt(System.Math.Min(halfTime, 30));
|
||
if (halfTime > 30) effectiveR += k * System.Math.Sqrt(halfTime - 30) * 0.3f;
|
||
|
||
// 膨胀应在合理范围
|
||
Assert.True(effectiveR > 10, $"有效半径={effectiveR:F1}m,应>10m(初始{r0:F1}m)");
|
||
Assert.True(effectiveR < 200, $"有效半径={effectiveR:F1}m,应<200m");
|
||
}
|
||
|
||
[Fact]
|
||
public void Timing_AccountsForExpansion()
|
||
{
|
||
var advisor = new DefaultDefenseAdvisor(DefaultAmmunition.GetAll());
|
||
var rec = advisor.Recommend(CreatePistonThreat());
|
||
|
||
var timing = rec.Best.RecommendedCloud.RecommendedTiming!.Value;
|
||
var halfTime = 20000f / (200f / 3.6f) / 2f;
|
||
|
||
// 推荐时机应明显早于无人机到达中点(因为有飞行时间和膨胀时间)
|
||
Assert.True(timing < halfTime - 5,
|
||
$"推荐时机={timing:F1}s 应早于中点={halfTime:F1}s(预留飞行+膨胀时间)");
|
||
}
|
||
}
|
||
}
|