@@ -308,23 +308,32 @@ let ``index-friendly queries should perform well``() =
308308let ``query performance should be consistent across multiple runs`` () =
309309 let runs = 3
310310 let times = ResizeArray< int64>()
311-
311+
312+ let runQuery () =
313+ query {
314+ for customer in dc.Main.Customers do
315+ take 10
316+ select customer.CustomerId
317+ } |> Seq.toArray
318+
319+ // Warm-up run: the first query pays JIT and initial-connection cost
320+ // (e.g. 3 ms vs 1 ms on warm runs), which is not representative of steady-state variance.
321+ runQuery() |> ignore
322+
312323 for i in 1 .. runs do
313- let ( _ , time ) = measureQueryPerformance $" Run{i}" ( fun () ->
314- query {
315- for customer in dc.Main.Customers do
316- take 10
317- select customer.CustomerId
318- } |> Seq.toArray)
319-
324+ let ( _ , time ) = measureQueryPerformance $" Run{i}" runQuery
320325 times.Add( time)
321-
326+
322327 let avgTime = times |> Seq.averageBy float
323328 let maxTime = times |> Seq.max
324329 let minTime = times |> Seq.min
325-
326- // Performance should be reasonably consistent
327- Assert.IsTrue( maxTime - minTime < int64( avgTime) * 2 L) // Max variance of 2x average
330+
331+ // Performance should be reasonably consistent. These queries run in ~1-3 ms, so at the
332+ // Stopwatch's millisecond resolution a single ms of scheduling jitter can exceed a purely
333+ // relative bound. Allow an absolute slack floor for quantization, and round the average up
334+ // (int64 truncation of e.g. 1.667 -> 1 would otherwise tighten the threshold).
335+ let threshold = max 5 L ( int64 ( ceil avgTime) * 2 L) // Max variance: 2x average, min 5 ms slack
336+ Assert.IsTrue( maxTime - minTime < threshold)
328337
329338 printfn " Query times: Min=%d ms, Max=%d ms, Avg=%.1f ms" minTime maxTime avgTime
330339
0 commit comments