독립 검증 도구 추가와 앱 상태 책임 분리
This commit is contained in:
@@ -0,0 +1,47 @@
|
||||
using System.Diagnostics;
|
||||
using ProjectQuint.Core.Judgement;
|
||||
|
||||
namespace ProjectQuint.Probes;
|
||||
|
||||
public readonly record struct JudgementSnapshot(int Score, int Combo, int MaxCombo,
|
||||
int MissCount, int KoolCount, int CoolCount, int GoodCount, int JudgedUnits, bool Finished);
|
||||
|
||||
public sealed record ReplayObservation(JudgementSnapshot Judgement, double SetupMilliseconds,
|
||||
double ReplayMilliseconds, long SetupAllocatedBytes, long ReplayAllocatedBytes);
|
||||
|
||||
public static class ReplayRunner
|
||||
{
|
||||
public static ReplayObservation Run(SyntheticWorkload workload, int frameRate)
|
||||
{
|
||||
if (frameRate < 1 || frameRate > 10_000)
|
||||
throw new ArgumentOutOfRangeException(nameof(frameRate), "Use a frame rate from 1 to 10000.");
|
||||
var allocationStart = GC.GetAllocatedBytesForCurrentThread();
|
||||
var setupStart = Stopwatch.GetTimestamp();
|
||||
var engine = new RhythmJudgementEngine(workload.Notes, laneCount: 4);
|
||||
var setupEnd = Stopwatch.GetTimestamp();
|
||||
var replayAllocationStart = GC.GetAllocatedBytesForCurrentThread();
|
||||
|
||||
long frame = 0;
|
||||
foreach (var input in workload.Events)
|
||||
{
|
||||
// Merge two timestamped streams; no sleeps or real-time waiting affect this trace.
|
||||
while ((double)frame / frameRate <= input.Time)
|
||||
engine.Update((double)frame++ / frameRate);
|
||||
if (input.Pressed)
|
||||
engine.Press(input.Lane, input.Time);
|
||||
else
|
||||
engine.Release(input.Lane, input.Time);
|
||||
}
|
||||
engine.Update(workload.Notes[^1].EndTime + 1);
|
||||
var replayEnd = Stopwatch.GetTimestamp();
|
||||
var allocationEnd = GC.GetAllocatedBytesForCurrentThread();
|
||||
return new ReplayObservation(new JudgementSnapshot(engine.Score, engine.Combo, engine.MaxCombo,
|
||||
engine.MissCount, engine.KoolCount, engine.CoolCount, engine.GoodCount,
|
||||
engine.JudgedNoteCount, engine.IsFinished),
|
||||
Milliseconds(setupStart, setupEnd), Milliseconds(setupEnd, replayEnd),
|
||||
replayAllocationStart - allocationStart, allocationEnd - replayAllocationStart);
|
||||
}
|
||||
|
||||
private static double Milliseconds(long start, long end) =>
|
||||
(end - start) * 1000.0 / Stopwatch.Frequency;
|
||||
}
|
||||
Reference in New Issue
Block a user