Skip to content

v4.0.0-rc.7

Pre-release
Pre-release

Choose a tag to compare

@github-actions github-actions released this 23 Oct 08:18
· 941 commits to main since this release

Install: dotnet add package Nino --version 4.0.0-rc.7 (Unity package: 4.0.0-preview.207)

New

  • The Unity package includes Nino's code fixes: Rider and Visual Studio offer the same quick fixes for Nino's analyzer warnings as in a NuGet project.

Performance

  • Serializing a list or array of fixed-size values to a byte[] writes straight into an array of its size, without a copy out of the scratch buffer.
  • Without AVX-512, lists and arrays of value tuples and other padded raw values are moved with in-lane shuffles (AVX2, SSSE3) instead of cross-lane permutes or one value at a time: a list of 1,000 (int, long) serializes in 194 ns instead of 380 ns (GitHub's x64 runners, EPYC 7763, AVX2).
  • On Intel x64 CPUs, deserializing into a new list or array of padded value tuples or DateTimeOffsets is faster: the array is allocated zeroed, as stores into an uninitialized array read each cache line from memory first.
  • Copies of 33 to 128 bytes are inline vector moves instead of a memmove call, and reads of raw values into an existing array use Nino's vector copy: small raw arrays, lists and non-Latin-1 strings read faster.
  • Multi-dimensional arrays of fixed-size elements (tuples, DateTimeOffsets, raw structs) are read and written as blocks instead of one value at a time.
  • ConcurrentStack<T> and ConcurrentBag<T> of fixed-size elements serialize as one block, and PriorityQueue reads and writes and HashSet writes of non-raw elements loop on a local reader or writer.
  • Nullable members of raw types (int?, long?, double?, DateTime? ...) are read under one bounds check for the flag and the value.
  • Version and the Unity types of Nino.UnityTypes (AnimationCurve, Gradient, RectOffset) reserve their bytes at once and read each run of keys under one bounds check.
  • Serializing an ImmutableStack<T> (Nino.Immutable) allocates nothing, as it no longer builds and reverses a list: 1,000 ints in 2.7 µs instead of 4.5 µs on GitHub's Arm64 runners (Neoverse-N2) and 2.9 µs instead of 3.1 µs on x64 (EPYC 7763).
  • Serializing collections without a specialized path (Collection<T>, ObservableCollection<T>, custom ICollection<T> types) no longer stores and reloads the writer around every element.
  • Version-tolerant types read adjacent raw members as one block whenever the data holds all of them: the benchmark's array of version-tolerant classes deserializes in 49.8 µs instead of 57.3 µs (GitHub's x64 runners, EPYC 7763).
  • Serializing keyed types is a little faster: a keyed member's key and region length, and the raw members just before it, are reserved at once.
  • Lists of [NinoPooled] types deserialize a little faster: renting from the pool is inlined into their element loops.
  • Serializing arrays and lists of tuples, KeyValuePairs and other padded structs takes the same time wherever the output buffer starts, instead of slowing down at some alignments.
  • New arrays of 2 to 6 KB that a read fills are allocated zeroed, which is cheaper there than uninitialized: 1,000 ints deserialize into a ReadOnlyCollection<T> or ReadOnlySequence<T> in 257 and 264 ns instead of 348 ns (GitHub's x64 runners, EPYC 7763) and in 364 and 363 ns instead of 416 and 423 ns (Arm64 runners, Neoverse-N2), and into a Memory<T> in 262 ns instead of 312 ns (x64).
  • On Arm64, arrays and lists of padded structs (tuples, KeyValuePairs) are copied with load and store pairs, 32 bytes a step.
  • Block copies of 8 to 32 KB (4 to 16 KB without 64-byte vectors) use Nino's vector loop instead of memmove, which is several times slower on some AMD EPYC CPUs.
  • Arrays and lists of 5-byte values such as (byte, int) move several values at a time with AVX2 and SSSE3 (x64 without AVX-512), instead of one at a time.
  • HashSet<T> and Dictionary<TKey, TValue> of raw values are written from their entries in one loop when no entry has been removed, on .NET, .NET Framework, Mono and Unity.
  • On Arm64, arrays and lists of small padded tuples read and write faster: 1,000 (byte, int) deserialize in 805 ns instead of 1,123 ns and serialize in 122 ns instead of 422 ns, 1,000 (short, int) in 801 ns instead of 1,103 ns and 124 ns instead of 200 ns, and 1,000 (int, long) in 1,415 ns instead of 1,815 ns and 219 ns instead of 375 ns (GitHub's Arm64 runners).
  • Subtypes read or written through a generic base (abstract class Box<T>, IRepository<T>) take the same generated dispatch as through a non-generic base, for the subtypes of each closed base declared in its assembly, instead of a registry lookup and a virtual call for each value.
  • Subtypes of a generic base whose type argument is a reference type or a tuple holding one (Box<string>, Box<(int, string)>) read and write the base's members without a formatter lookup and a virtual call for each value.
  • On x64 CPUs without AVX-512, block copies of up to 1 MB use Nino's 32-byte vector loop instead of memmove.
  • Nino.Immutable reads ImmutableDictionary and ImmutableHashSet by building their tree directly in one pass: 1,000 ints deserialize in 20.6 and 19.7 µs instead of 109.4 and 92.1 µs (GitHub's x64 runners, EPYC 7763) and in 21.3 and 20.4 µs instead of 81.7 and 78.8 µs (Arm64 runners, Neoverse-N2).
  • Nino.Immutable reads ImmutableSortedDictionary and ImmutableSortedSet by building their tree directly in one pass: 1,000 ints deserialize in 13.3 and 13.2 µs instead of 55.6 and 18.5 µs (GitHub's x64 runners, EPYC 7763) and in 14.6 and 13.8 µs instead of 62.5 and 19.1 µs (Arm64 runners, Neoverse-N2).
  • LinkedList<T> and SortedDictionary<TKey, TValue> are read by linking their nodes or building their tree directly: 1,000 ints deserialize into a LinkedList in 11.5 µs instead of 14.1 µs (GitHub's x64 runners, EPYC 7763) and 12.3 µs instead of 14.5 µs (Arm64 runners, Neoverse-N2), and into a SortedDictionary in 17.4 µs instead of 23.9 µs and 16.7 µs instead of 27.1 µs.
  • Nino.Immutable writes ImmutableDictionary, ImmutableHashSet, ImmutableSortedDictionary and ImmutableSortedSet straight out of their trees: 1,000 ints serialize 4 to 5 times as fast for the first two and 2 to 2.6 times as fast for the sorted ones (GitHub's x64 runners, EPYC 7763, and Arm64 runners, Neoverse-N2).
  • SortedSet<T> and SortedDictionary<TKey, TValue> serialize copied out of their trees: 1,000 ints in 2.8 µs instead of 5.5 µs (SortedSet) and 3.0 to 3.2 µs instead of 5.6 to 5.8 µs (SortedDictionary) (GitHub's x64 runners, EPYC 7763, and Arm64 runners, Neoverse-N2).
  • Empty collections skip their element loops, and a pool that was never filled answers a rent without a call or a thread-local access: a pooled node deserializes in 156 ns instead of 205 ns (GitHub's x64 runners, EPYC 7763) and 145 ns instead of 193 ns (Arm64 runners, Neoverse-N2).
  • New HashSet<T> and Dictionary<TKey, TValue> of raw elements are filled directly: 1,000 ints deserialize into a HashSet in 2.6 µs instead of 6.1 µs (GitHub's x64 runners, EPYC 7763) and 2.8 µs instead of 5.3 µs (Arm64 runners, Neoverse-N2).
  • On Arm64, block copies of up to 64 KB use paired vector loads from an aligned source instead of memmove.
  • On AMD x64 CPUs, reads into a new array copy with vector stores instead of memmove, whose rep movsb is slower there: 1,000 KeyValuePair<int, int> deserialize in 418 ns instead of 465 ns (GitHub's x64 runners, EPYC 7763).
  • Arrays of polymorphic classes are faster both ways: 100 of them serialize in 34 µs instead of 46 µs and deserialize in 172 µs instead of 224 µs (GitHub's x64 runners, Xeon 6973P-C), and serialize in 58 µs instead of 76 µs and deserialize in 193 µs instead of 221 µs (Arm64 runners, Neoverse-N2).

Fixes

  • Serializing a span of unmanaged values past 4 GB, a StringBuilder past 1 G chars or UTF-8 text past 2 GB throws OverflowException instead of writing past the end of the buffer.
  • Generic abstract classes, generic interfaces and abstract classes nested in generic types with subtypes no longer break the build: their subtypes are written and read through the registry, in every format.
  • A class nested in a generic class with [NinoType] subtypes in another assembly no longer overflows the stack the first time it is serialized.
  • Code fixes (implementing [NinoPooled] hooks, adding or removing attributes) keep the line breaks of the file they edit, instead of inserting the machine's (CRLF lines in an LF file on Windows).
  • Data crafted against a reader can no longer crash the process: a struct nested in itself thousands deep (through a list, nullable or interface member) throws instead of overflowing the stack.
  • A failed read into an existing value no longer leaves an array of uninitialized memory in it, and a StringBuilder or multi-dimensional array length is checked against the data before allocating.
  • Invalid Version, Uri, CultureInfo, TimeZoneInfo and DateTimeOffset values and null dictionary keys throw Nino's InvalidOperationException (the original as its inner exception) instead of BCL exceptions, so Nino.AspNetCore answers them with 400.
  • Data that claims more elements than it holds can no longer make a read allocate hundreds of times its size: every collection allocates ahead of its elements at most 16 times the bytes left in the input, and grows as elements are actually read.

Every change between v4 releases: Changelog.

What's Changed since v4.0.0-rc.6

158 commits

✨ Features

⚡ Performance (65)

🐛 Fixes

♻️ Refactoring and cleanup (23)
📖 Documentation (19)
🧪 Tests (19)
🔧 Build, CI and dependencies (22)

Contributors

Thanks to everyone who contributed to this release: @JasonXuDeveloper, doge

Full Changelog: v4.0.0-rc.6...v4.0.0-rc.7

📊 v3 3.3.13 vs v4 (same machine)

Nino v3 3.3.13 (NuGet) against v4.0.0-rc.7, back to back on the same runner

benchmarks/v3 (the Nino and MemoryPack cases of the same SimpleTest, built against Nino 3.3.13 from nuget.org) ran directly before the v4
SimpleTest run below, on the same runner, with the same BenchmarkDotNet settings
(--launchCount 3 --warmupCount 5 --iterationCount 15). MemoryPack runs in both, so its two columns show how much the runner moved.

v4 vs v3

case v3 3.3.13 v4 v4 vs v3 MemoryPack (v4 run) MemoryPack (v3 run)
SerializeSimpleClass 124.71 ns 69.59 ns 0.56x 291.13 ns 300.15 ns
SerializeSimpleClasses 17.98 μs 7.84 μs 0.44x 27.39 μs 29.56 μs
SerializeSimpleStruct 1.28 ns 0.76 ns faster (v4 too fast to measure) 2.44 ns 2.55 ns
SerializeSimpleStructs 13.20 ns 11.71 ns 0.89x 14.25 ns 13.97 ns
SerializeVectors 3.64 μs 3.57 μs 0.98x 3.53 μs 3.57 μs
DeserializeSimpleClass 442.61 ns 366.34 ns 0.83x 514.45 ns 564.16 ns
DeserializeSimpleClasses 47.64 μs 39.24 μs 0.82x 51.12 μs 54.98 μs
DeserializeSimpleStruct 0.36 ns 0.34 ns on par (both too fast to measure) 0.33 ns 0.33 ns
DeserializeSimpleStructs 81.97 ns 76.92 ns 0.94x 88.65 ns 90.76 ns
DeserializeVectors 97.46 μs 96.22 μs 0.99x 95.26 μs 102.20 μs

v4 vs v3 = mean(v4) / mean(v3); below 1.00x means v4 is faster.
MemoryPack drift (v4 run / v3 run): min 0.91x, max 1.02x (same code in both runs; the spread is the noise floor of this comparison).

v3 3.3.13 runner


BenchmarkDotNet v0.15.8, Linux Ubuntu 26.04.1 LTS (Resolute Raccoon)
INTEL XEON PLATINUM 8573C 3.18GHz, 1 CPU, 4 logical and 2 physical cores
.NET SDK 10.0.402
  [Host]             : .NET 10.0.13 (10.0.13, 10.0.1326.50504), X64 RyuJIT x86-64-v4
  ShortRun-.NET 10.0 : .NET 10.0.13 (10.0.13, 10.0.1326.50504), X64 RyuJIT x86-64-v4

Job=ShortRun-.NET 10.0  Runtime=.NET 10.0  Server=True  
IterationCount=15  LaunchCount=3  WarmupCount=5  

The v3 report: benchmark-v3-full.md.

📊 Arm64 benchmark

The same benchmarks of v4.0.0-rc.7 on an Arm64 runner

The benchmark classes of the x64 report below, with the same BenchmarkDotNet settings
(--launchCount 3 --warmupCount 5 --iterationCount 15), on GitHub's ubuntu-24.04-arm runners. Compare Nino with MemoryPack within
this table: the runners differ from the x64 ones, so times across the two tables say little.


BenchmarkDotNet v0.15.8, Linux Ubuntu 24.04.5 LTS (Noble Numbat)
Neoverse-N2, 4 physical cores
.NET SDK 10.0.402
  [Host]             : .NET 10.0.13 (10.0.13, 10.0.1326.50504), Arm64 RyuJIT armv8.0-a
  ShortRun-.NET 10.0 : .NET 10.0.13 (10.0.13, 10.0.1326.50504), Arm64 RyuJIT armv8.0-a

Job=ShortRun-.NET 10.0  Runtime=.NET 10.0  Server=True  
IterationCount=15  LaunchCount=3  WarmupCount=5  

PooledTest

Method Mean Ratio Payload Allocated
NinoDeserializeNew 500.67 ns 1.00 - 2536 B
NinoDeserializePooled 287.58 ns 0.57 - -
MemoryPackDeserializeNew 747.96 ns 1.49 - 2536 B
MemoryPackDeserializeOverwrite 546.36 ns 1.09 - 1080 B

SimpleTest

Method Mean Ratio Payload Allocated
NinoDeserializeSimpleClass 504.39 ns 1.00 - 2528 B
MemoryPackDeserializeSimpleClass 756.66 ns 1.50 - 2528 B
NinoSerializeSimpleClass 105.52 ns 1.00 1,104 B -
MemoryPackSerializeSimpleClass 453.24 ns 4.30 1,148 B -
NinoDeserializeSimpleClasses 49.53 μs 1.00 - 253624 B
MemoryPackDeserializeSimpleClasses 68.98 μs 1.39 - 253624 B
NinoSerializeSimpleClasses 11.13 μs 1.00 110,404 B -
MemoryPackSerializeSimpleClasses 44.89 μs 4.03 114,804 B -
NinoDeserializeSimpleStruct 4.69 ns 1.00 - -
MemoryPackDeserializeSimpleStruct 4.71 ns 1.00 - -
NinoSerializeSimpleStruct 1.88 ns 1.00 12 B -
MemoryPackSerializeSimpleStruct 4.87 ns 2.59 12 B -
NinoDeserializeSimpleStructs 114.55 ns 1.00 - 1224 B
MemoryPackDeserializeSimpleStructs 139.42 ns 1.22 - 1224 B
NinoSerializeSimpleStructs 21.13 ns 1.00 1,204 B -
MemoryPackSerializeSimpleStructs 29.41 ns 1.39 1,204 B -
NinoDeserializeVectors 104.84 μs 1.00 - 160024 B
MemoryPackDeserializeVectors 107.92 μs 1.03 - 160026 B
NinoSerializeVectors 3.27 μs 1.00 160,004 B -
MemoryPackSerializeVectors 3.25 μs 0.99 160,004 B -

FixedSizeTest

Method Mean Ratio Payload Allocated
NinoDeserializeFixedClass 9.85 ns 1.00 - 56 B
MemoryPackDeserializeFixedClass 29.32 ns 2.98 - 56 B
NinoSerializeFixedClass 11.32 ns 1.00 41 B 72 B
MemoryPackSerializeFixedClass 30.57 ns 2.70 41 B 72 B
NinoDeserializeFixedClasses 1.15 μs 1.00 - 6424 B
MemoryPackDeserializeFixedClasses 1.57 μs 1.37 - 6424 B
NinoSerializeFixedClasses 622.83 ns 1.00 4,104 B 4128 B
MemoryPackSerializeFixedClasses 1.86 μs 2.98 4,104 B 4128 B
NinoDeserializeFixedStruct 0.52 ns 1.00 - -
MemoryPackDeserializeFixedStruct 1.17 ns 2.24 - -
NinoSerializeFixedStruct 9.71 ns 1.00 40 B 64 B
MemoryPackSerializeFixedStruct 9.77 ns 1.01 40 B 64 B

CommonTypesTest

Method Mean Ratio Payload Allocated
NinoDeserializeInventory 621.39 ns 1.00 - 8024 B
MemoryPackDeserializeInventory 654.02 ns 1.05 - 8024 B
NinoSerializeInventory 129.09 ns 1.00 8,004 B -
MemoryPackSerializeInventory 140.14 ns 1.09 8,004 B -
NinoDeserializeOrders 25.94 μs 1.00 - 88552 B
MemoryPackDeserializeOrders 36.14 μs 1.39 - 88552 B
NinoSerializeOrders 7.29 μs 1.00 26,126 B -
MemoryPackSerializeOrders 14.56 μs 2.00 27,990 B -
NinoDeserializePlayers 32.85 μs 1.00 - 120056 B
MemoryPackDeserializePlayers 45.47 μs 1.38 - 120056 B
NinoSerializePlayers 9.55 μs 1.00 39,164 B -
MemoryPackSerializePlayers 27.29 μs 2.86 43,364 B -
NinoDeserializeShapes 11.01 μs 1.00 - 36056 B
MemoryPackDeserializeShapes 15.57 μs 1.41 - 36056 B
NinoSerializeShapes 1.93 μs 1.00 14,004 B -
MemoryPackSerializeShapes 25.51 μs 13.22 12,004 B -
NinoDeserializeStringDictionary 40.85 μs 1.00 - 110216 B
MemoryPackDeserializeStringDictionary 60.50 μs 1.48 - 110216 B
NinoSerializeStringDictionary 8.54 μs 1.00 22,734 B -
MemoryPackSerializeStringDictionary 35.68 μs 4.18 30,734 B -
NinoDeserializeTree 52.10 μs 1.00 - 171872 B
MemoryPackDeserializeTree 69.22 μs 1.33 - 171872 B
NinoSerializeTree 15.61 μs 1.00 31,258 B -
MemoryPackSerializeTree 21.53 μs 1.38 32,623 B -

GenericPolymorphicTest

Method Mean Ratio Payload Allocated
NinoDeserializeGenericIntBase 13.03 μs 1.00 - 32024 B
MemoryPackDeserializeGenericIntBase 46.29 μs 3.55 - 32024 B
NinoSerializeGenericIntBase 3.03 μs 1.00 - -
MemoryPackSerializeGenericIntBase 56.10 μs 18.50 - -
NinoDeserializeGenericManagedTupleBase 37.63 μs 1.00 - 72024 B
MemoryPackDeserializeGenericManagedTupleBase 80.42 μs 2.14 - 72024 B
NinoSerializeGenericManagedTupleBase 9.38 μs 1.00 - -
MemoryPackSerializeGenericManagedTupleBase 106.51 μs 11.36 - -
NinoDeserializeGenericOpenClassTupleBase 31.51 μs 1.00 - 72024 B
MemoryPackDeserializeGenericOpenClassTupleBase 70.26 μs 2.23 - 72024 B
NinoSerializeGenericOpenClassTupleBase 7.71 μs 1.00 - -
MemoryPackSerializeGenericOpenClassTupleBase 109.69 μs 14.23 - -
NinoDeserializeGenericSealedClassTupleBase 31.65 μs 1.00 - 72024 B
MemoryPackDeserializeGenericSealedClassTupleBase 70.32 μs 2.22 - 72024 B
NinoSerializeGenericSealedClassTupleBase 8.11 μs 1.00 - -
MemoryPackSerializeGenericSealedClassTupleBase 109.04 μs 13.48 - -
NinoDeserializeGenericUnmanagedTupleBase 18.37 μs 1.00 - 40024 B
MemoryPackDeserializeGenericUnmanagedTupleBase 45.70 μs 2.49 - 40024 B
NinoSerializeGenericUnmanagedTupleBase 5.29 μs 1.00 - -
MemoryPackSerializeGenericUnmanagedTupleBase 62.57 μs 11.82 - -
NinoDeserializeNonGenericBase 12.06 μs 1.00 - 32024 B
MemoryPackDeserializeNonGenericBase 22.39 μs 1.86 - 32024 B
NinoSerializeNonGenericBase 3.11 μs 1.00 - -
MemoryPackSerializeNonGenericBase 38.39 μs 12.35 - -

VersionTolerantTest

Method Mean Ratio Payload Allocated
NinoDeserializeTolerantClass 508.20 ns 1.00 - 2528 B
MemoryPackDeserializeTolerantClass 764.00 ns 1.50 - 2528 B
NinoSerializeTolerantClass 101.10 ns 1.00 1,108 B -
MemoryPackSerializeTolerantClass 614.50 ns 6.08 1,164 B -
NinoDeserializeTolerantClasses 51.77 μs 1.00 - 253624 B
MemoryPackDeserializeTolerantClasses 76.08 μs 1.47 - 253624 B
NinoSerializeTolerantClasses 12.14 μs 1.00 110,804 B -
MemoryPackSerializeTolerantClasses 61.43 μs 5.06 116,404 B -

BclTypesTest

Method Mean Ratio Payload Allocated
NinoDeserializeImmutableDictionary 21.81 μs 1.00 - 68088 B
MemoryPackDeserializeImmutableDictionary 87.83 μs 4.03 - 56096 B
NinoSerializeImmutableDictionary 3.38 μs 1.00 8,004 B -
MemoryPackSerializeImmutableDictionary 17.41 μs 5.14 8,004 B -
NinoDeserializeImmutableHashSet 21.10 μs 1.00 - 64096 B
MemoryPackDeserializeImmutableHashSet 87.47 μs 4.15 - 56104 B
NinoSerializeImmutableHashSet 3.14 μs 1.00 4,004 B -
MemoryPackSerializeImmutableHashSet 27.15 μs 8.64 4,004 B -
NinoDeserializeImmutableQueue 7.78 μs 1.00 - 36064 B
MemoryPackDeserializeImmutableQueue 10.98 μs 1.41 - 32112 B
NinoSerializeImmutableQueue 1.45 μs 1.00 4,004 B -
MemoryPackSerializeImmutableQueue 10.20 μs 7.05 4,004 B -
NinoDeserializeImmutableSortedDictionary 14.59 μs 1.00 - 56072 B
MemoryPackDeserializeImmutableSortedDictionary 81.43 μs 5.58 - 48112 B
NinoSerializeImmutableSortedDictionary 3.12 μs 1.00 8,004 B -
MemoryPackSerializeImmutableSortedDictionary 8.19 μs 2.62 8,004 B -
NinoDeserializeImmutableSortedSet 14.00 μs 1.00 - 52056 B
MemoryPackDeserializeImmutableSortedSet 76.02 μs 5.43 - 48088 B
NinoSerializeImmutableSortedSet 2.59 μs 1.00 4,004 B -
MemoryPackSerializeImmutableSortedSet 20.02 μs 7.72 4,004 B -
NinoDeserializeImmutableStack 7.78 μs 1.00 - 36024 B
MemoryPackDeserializeImmutableStack 11.11 μs 1.43 - 32040 B
NinoSerializeImmutableStack 2.65 μs 1.00 4,004 B -
MemoryPackSerializeImmutableStack 16.68 μs 6.29 4,004 B -
NinoDeserializeBigInteger 40.36 ns 1.00 - 256 B
NinoSerializeBigInteger 12.67 ns 1.00 203 B -
NinoDeserializeBitArray 56.21 ns 1.00 - 336 B
NinoSerializeBitArray 25.40 ns 1.00 129 B -
NinoDeserializeBlockingCollection 11.59 μs 1.00 - 12984 B
MemoryPackDeserializeBlockingCollection 53.98 μs 4.66 - -
NinoSerializeBlockingCollection 5.36 μs 1.00 4,004 B 4096 B
MemoryPackSerializeBlockingCollection 15.66 μs 2.92 4,004 B 72 B
NinoDeserializeCultureInfo 63.29 ns 1.00 - 64 B
MemoryPackDeserializeCultureInfo 84.91 ns 1.34 - 64 B
NinoSerializeCultureInfo 4.25 ns 1.00 9 B -
MemoryPackSerializeCultureInfo 31.25 ns 7.35 13 B -
NinoDeserializeLazy 23.71 ns 1.00 - 112 B
MemoryPackDeserializeLazy 46.53 ns 1.96 - 112 B
NinoSerializeLazy 6.24 ns 1.00 27 B -
MemoryPackSerializeLazy 55.76 ns 8.93 31 B -
NinoDeserializeLookup 720.10 ns 1.00 - 5152 B
MemoryPackDeserializeLookup 1.01 μs 1.40 - 5576 B
NinoSerializeLookup 2.46 μs 1.00 4,084 B 320 B
MemoryPackSerializeLookup 13.64 μs 5.55 4,094 B -
NinoDeserializeMemory 357.85 ns 1.00 - 4056 B
MemoryPackDeserializeMemory 438.43 ns 1.23 - 4056 B
NinoSerializeMemory 58.06 ns 1.00 4,004 B -
MemoryPackSerializeMemory 101.07 ns 1.74 4,004 B -
NinoDeserializeReadOnlyCollection 348.87 ns 1.00 - 4048 B
MemoryPackDeserializeReadOnlyCollection 436.55 ns 1.25 - 4048 B
NinoSerializeReadOnlyCollection 2.64 μs 1.00 4,004 B 40 B
MemoryPackSerializeReadOnlyCollection 13.72 μs 5.20 4,004 B 40 B
NinoDeserializeReadOnlySequence 349.92 ns 1.00 - 4064 B
MemoryPackDeserializeReadOnlySequence 437.62 ns 1.25 - 4064 B
NinoSerializeReadOnlySequence 66.06 ns 1.00 4,004 B -
MemoryPackSerializeReadOnlySequence 102.79 ns 1.56 4,004 B -
NinoDeserializeStringBuilder 202.37 ns 1.00 - 2072 B
MemoryPackDeserializeStringBuilder 220.65 ns 1.09 - 2072 B
NinoSerializeStringBuilder 34.97 ns 1.00 2,004 B -
MemoryPackSerializeStringBuilder 70.68 ns 2.02 2,004 B -
NinoDeserializeTimeZoneInfo 14.56 ns 1.00 - 32 B
MemoryPackDeserializeTimeZoneInfo 335.77 ns 23.07 - 680 B
NinoSerializeTimeZoneInfo 11.78 ns 1.00 11 B -
MemoryPackSerializeTimeZoneInfo 287.45 ns 24.40 102 B 216 B
NinoDeserializeUri 100.14 ns 1.00 - 184 B
MemoryPackDeserializeUri 124.52 ns 1.24 - 184 B
NinoSerializeUri 8.37 ns 1.00 56 B -
MemoryPackSerializeUri 36.85 ns 4.40 60 B -
NinoDeserializeVersion 7.82 ns 1.00 - 32 B
MemoryPackDeserializeVersion 23.32 ns 2.98 - 32 B
NinoSerializeVersion 2.89 ns 1.00 16 B -
MemoryPackSerializeVersion 28.95 ns 10.01 17 B -

PolymorphicTest

Method Mean Ratio Payload Allocated
NinoDeserializePolymorphicClassArray 197.82 μs 1.00 - 745624 B
MemoryPackDeserializePolymorphicClassArray 331.67 μs 1.68 - 745624 B
NinoSerializePolymorphicClassArray 59.06 μs 1.00 397,304 B -
MemoryPackSerializePolymorphicClassArray 375.65 μs 6.37 384,404 B -
NinoDeserializePolymorphicClass 19.73 μs 1.00 - 79688 B
MemoryPackDeserializePolymorphicClass 30.53 μs 1.55 - 79688 B
NinoSerializePolymorphicClass 6.44 μs 1.00 53,789 B -
MemoryPackSerializePolymorphicClass 33.45 μs 5.20 51,760 B -
NinoDeserializePolymorphicFooArray 18.79 μs 1.00 - 76024 B
MemoryPackDeserializePolymorphicFooArray 33.05 μs 1.76 - 76024 B
NinoSerializePolymorphicFooArray 6.61 μs 1.00 52,404 B -
MemoryPackSerializePolymorphicFooArray 31.75 μs 4.80 50,404 B -

PooledGraphTest

Method Mean Ratio Payload Allocated
NinoLeavesNew 3.06 μs 1.00 - 13656 B
NinoLeavesPooledElements 3.06 μs 1.00 - 856 B
NinoLeavesInPlace 437.02 ns 0.14 - -
MemoryPackLeavesNew 3.89 μs 1.27 - 13656 B
MemoryPackLeavesOverwrite 4.23 μs 1.38 - 12800 B
NinoNodeNew 484.02 ns 1.00 - 2192 B
NinoNodePooled 144.74 ns 0.30 - -
MemoryPackNodeNew 663.61 ns 1.37 - 2192 B
MemoryPackNodeOverwrite 557.94 ns 1.15 - 1024 B
NinoPlainNew 2.87 μs 1.00 - 12856 B
MemoryPackPlainNew 3.80 μs 1.33 - 12856 B

CollectionsTest

Method Mean Ratio Payload Allocated
NinoDeserializeConcurrentDictionary 18.85 μs 1.00 - 49184 B
MemoryPackDeserializeConcurrentDictionary 67.56 μs 3.58 - 141032 B
NinoSerializeConcurrentDictionary 2.28 μs 1.00 8,004 B -
MemoryPackSerializeConcurrentDictionary 3.15 μs 1.38 8,004 B -
NinoDeserializeHashSet 2.84 μs 1.00 - 17768 B
MemoryPackDeserializeHashSet 6.45 μs 2.27 - 17768 B
NinoSerializeHashSet 373.33 ns 1.00 4,004 B -
MemoryPackSerializeHashSet 13.11 μs 35.11 4,004 B -
NinoDeserializeKeyValuePairs 659.38 ns 1.00 - 8024 B
MemoryPackDeserializeKeyValuePairs 682.21 ns 1.03 - 8024 B
NinoSerializeKeyValuePairs 110.07 ns 1.00 8,004 B -
MemoryPackSerializeKeyValuePairs 141.26 ns 1.28 8,004 B -
NinoDeserializeLinkedList 12.19 μs 1.00 - 48040 B
MemoryPackDeserializeLinkedList 15.02 μs 1.23 - 48040 B
NinoSerializeLinkedList 1.34 μs 1.00 4,004 B -
MemoryPackSerializeLinkedList 14.05 μs 10.45 4,004 B -
NinoDeserializeQueue 359.63 ns 1.00 - 4064 B
MemoryPackDeserializeQueue 3.90 μs 10.84 - 4064 B
NinoSerializeQueue 64.16 ns 1.00 4,004 B -
MemoryPackSerializeQueue 12.78 μs 199.23 4,004 B -
NinoDeserializeSortedDictionary 16.63 μs 1.00 - 48112 B
MemoryPackDeserializeSortedDictionary 44.98 μs 2.70 - 48112 B
NinoSerializeSortedDictionary 3.00 μs 1.00 8,004 B -
MemoryPackSerializeSortedDictionary 6.04 μs 2.01 8,004 B 200 B
NinoDeserializeSortedList 2.42 μs 1.00 - 8112 B
MemoryPackDeserializeSortedList 15.07 μs 6.22 - -
NinoSerializeSortedList 2.04 μs 1.00 8,004 B -
MemoryPackSerializeSortedList 3.29 μs 1.61 8,004 B -
NinoDeserializeSortedSet 14.71 μs 1.00 - 40048 B
MemoryPackDeserializeSortedSet 40.40 μs 2.75 - 40048 B
NinoSerializeSortedSet 2.85 μs 1.00 4,004 B -
MemoryPackSerializeSortedSet 16.25 μs 5.70 4,004 B 200 B
NinoDeserializeTupleList 1.38 μs 1.00 - 16056 B
MemoryPackDeserializeTupleList 1.41 μs 1.03 - 16056 B
NinoSerializeTupleList 219.51 ns 1.00 12,004 B -
MemoryPackSerializeTupleList 291.79 ns 1.33 16,004 B -

ReferenceTest

Method Mean Ratio Payload Allocated
NinoDeserializeGraph 6.47 μs 1.00 - 14104 B
MemoryPackDeserializeGraph 18.82 μs 2.91 - 14104 B
NinoSerializeGraph 4.37 μs 1.00 5,878 B -
MemoryPackSerializeGraph 32.04 μs 7.34 5,584 B -

The classes ran in parallel, each on its own runner (a class's Nino and MemoryPack cases on one):

  • PooledTest, SimpleTest: Neoverse-N2, 4 physical cores
  • CommonTypesTest, FixedSizeTest: Neoverse-N2, 4 physical cores
  • GenericPolymorphicTest, VersionTolerantTest: Neoverse-N2, 4 physical cores
  • BclTypesTest, PolymorphicTest: Neoverse-N2, 4 physical cores
  • BclTypesTest, PooledGraphTest: Neoverse-N2, 4 physical cores
  • BclTypesTest, CollectionsTest: Neoverse-N2, 4 physical cores
  • CollectionsTest, ReferenceTest: Neoverse-N2, 4 physical cores

Median, Min, Max and the GC counts: benchmark-arm64-full.md.

📊 Performance Report

Click to expand benchmark results

BenchmarkDotNet v0.15.8, Linux Ubuntu 26.04.1 LTS (Resolute Raccoon)
INTEL XEON PLATINUM 8573C 3.50GHz, 1 CPU, 4 logical and 2 physical cores
.NET SDK 10.0.402
  [Host]             : .NET 10.0.13 (10.0.13, 10.0.1326.50504), X64 RyuJIT x86-64-v4
  ShortRun-.NET 10.0 : .NET 10.0.13 (10.0.13, 10.0.1326.50504), X64 RyuJIT x86-64-v4

Job=ShortRun-.NET 10.0  Runtime=.NET 10.0  Server=True  
IterationCount=15  LaunchCount=3  WarmupCount=5  

PooledTest

Method Mean Ratio Payload Allocated
NinoDeserializeNew 390.80 ns 1.00 - 2536 B
NinoDeserializePooled 181.10 ns 0.46 - -
MemoryPackDeserializeNew 523.45 ns 1.34 - 2536 B
MemoryPackDeserializeOverwrite 443.44 ns 1.14 - 1080 B

SimpleTest

Method Mean Ratio Payload Allocated
NinoDeserializeSimpleClass 366.34 ns 1.00 - 2528 B
MemoryPackDeserializeSimpleClass 514.45 ns 1.40 - 2528 B
NinoSerializeSimpleClass 69.59 ns 1.00 1,104 B -
MemoryPackSerializeSimpleClass 291.13 ns 4.19 1,148 B -
NinoDeserializeSimpleClasses 39.24 μs 1.00 - 253624 B
MemoryPackDeserializeSimpleClasses 51.12 μs 1.30 - 253624 B
NinoSerializeSimpleClasses 7.84 μs 1.00 110,404 B -
MemoryPackSerializeSimpleClasses 27.39 μs 3.49 114,804 B -
NinoDeserializeSimpleStruct 0.34 ns 1.00 - -
MemoryPackDeserializeSimpleStruct 0.33 ns 0.99 - -
NinoSerializeSimpleStruct 0.76 ns 1.01 12 B -
MemoryPackSerializeSimpleStruct 2.44 ns 3.24 12 B -
NinoDeserializeSimpleStructs 76.92 ns 1.00 - 1224 B
MemoryPackDeserializeSimpleStructs 88.65 ns 1.15 - 1224 B
NinoSerializeSimpleStructs 11.71 ns 1.00 1,204 B -
MemoryPackSerializeSimpleStructs 14.25 ns 1.22 1,204 B -
NinoDeserializeVectors 96.22 μs 1.00 - 160028 B
MemoryPackDeserializeVectors 95.26 μs 0.99 - 160031 B
NinoSerializeVectors 3.57 μs 1.00 160,004 B -
MemoryPackSerializeVectors 3.53 μs 0.99 160,004 B -

FixedSizeTest

Method Mean Ratio Payload Allocated
NinoDeserializeFixedClass 8.06 ns 1.00 - 56 B
MemoryPackDeserializeFixedClass 22.80 ns 2.83 - 56 B
NinoSerializeFixedClass 8.76 ns 1.00 41 B 72 B
MemoryPackSerializeFixedClass 24.77 ns 2.83 41 B 72 B
NinoDeserializeFixedClasses 1.02 μs 1.00 - 6424 B
MemoryPackDeserializeFixedClasses 1.38 μs 1.35 - 6424 B
NinoSerializeFixedClasses 562.76 ns 1.00 4,104 B 4128 B
MemoryPackSerializeFixedClasses 1.75 μs 3.11 4,104 B 4128 B
NinoDeserializeFixedStruct 0.29 ns 1.01 - -
MemoryPackDeserializeFixedStruct 1.08 ns 3.73 - -
NinoSerializeFixedStruct 7.88 ns 1.00 40 B 64 B
MemoryPackSerializeFixedStruct 8.02 ns 1.02 40 B 64 B

CommonTypesTest

Method Mean Ratio Payload Allocated
NinoDeserializeInventory 390.00 ns 1.00 - 8024 B
MemoryPackDeserializeInventory 415.95 ns 1.07 - 8024 B
NinoSerializeInventory 136.52 ns 1.03 8,004 B -
MemoryPackSerializeInventory 105.45 ns 0.80 8,004 B -
NinoDeserializeOrders 24.29 μs 1.00 - 88552 B
MemoryPackDeserializeOrders 32.87 μs 1.36 - 88552 B
NinoSerializeOrders 7.78 μs 1.00 26,126 B -
MemoryPackSerializeOrders 14.84 μs 1.91 27,990 B -
NinoDeserializePlayers 32.71 μs 1.00 - 120056 B
MemoryPackDeserializePlayers 41.94 μs 1.29 - 120056 B
NinoSerializePlayers 8.82 μs 1.00 39,164 B -
MemoryPackSerializePlayers 25.12 μs 2.85 43,364 B -
NinoDeserializeShapes 10.77 μs 1.00 - 36056 B
MemoryPackDeserializeShapes 16.56 μs 1.54 - 36056 B
NinoSerializeShapes 2.04 μs 1.00 14,004 B -
MemoryPackSerializeShapes 22.85 μs 11.23 12,004 B -
NinoDeserializeStringDictionary 31.81 μs 1.00 - 110216 B
MemoryPackDeserializeStringDictionary 54.07 μs 1.70 - 110216 B
NinoSerializeStringDictionary 8.69 μs 1.00 22,734 B -
MemoryPackSerializeStringDictionary 32.73 μs 3.77 30,734 B -
NinoDeserializeTree 53.04 μs 1.00 - 171872 B
MemoryPackDeserializeTree 66.70 μs 1.26 - 171872 B
NinoSerializeTree 16.38 μs 1.00 31,258 B -
MemoryPackSerializeTree 20.04 μs 1.22 32,623 B -

GenericPolymorphicTest

Method Mean Ratio Payload Allocated
NinoDeserializeGenericIntBase 11.04 μs 1.00 - 32024 B
MemoryPackDeserializeGenericIntBase 37.03 μs 3.36 - -
NinoSerializeGenericIntBase 2.75 μs 1.00 - -
MemoryPackSerializeGenericIntBase 41.32 μs 15.01 - -
NinoDeserializeGenericManagedTupleBase 24.06 μs 1.00 - 72024 B
MemoryPackDeserializeGenericManagedTupleBase 59.01 μs 2.46 - -
NinoSerializeGenericManagedTupleBase 16.99 μs 1.00 - -
MemoryPackSerializeGenericManagedTupleBase 74.47 μs 4.38 - -
NinoDeserializeGenericOpenClassTupleBase 21.56 μs 1.01 - 72024 B
MemoryPackDeserializeGenericOpenClassTupleBase 54.39 μs 2.54 - 72024 B
NinoSerializeGenericOpenClassTupleBase 14.56 μs 1.02 - -
MemoryPackSerializeGenericOpenClassTupleBase 75.94 μs 5.29 - -
NinoDeserializeGenericSealedClassTupleBase 20.72 μs 1.00 - 72024 B
MemoryPackDeserializeGenericSealedClassTupleBase 52.81 μs 2.56 - 72024 B
NinoSerializeGenericSealedClassTupleBase 16.03 μs 1.07 - -
MemoryPackSerializeGenericSealedClassTupleBase 73.28 μs 4.89 - -
NinoDeserializeGenericUnmanagedTupleBase 12.80 μs 1.00 - 40024 B
MemoryPackDeserializeGenericUnmanagedTupleBase 38.99 μs 3.05 - -
NinoSerializeGenericUnmanagedTupleBase 4.69 μs 1.00 - -
MemoryPackSerializeGenericUnmanagedTupleBase 45.30 μs 9.66 - -
NinoDeserializeNonGenericBase 9.84 μs 1.00 - 32024 B
MemoryPackDeserializeNonGenericBase 21.78 μs 2.21 - 32024 B
NinoSerializeNonGenericBase 2.82 μs 1.00 - -
MemoryPackSerializeNonGenericBase 27.33 μs 9.71 - -

VersionTolerantTest

Method Mean Ratio Payload Allocated
NinoDeserializeTolerantClass 327.50 ns 1.01 - 2528 B
MemoryPackDeserializeTolerantClass 536.17 ns 1.65 - 2528 B
NinoSerializeTolerantClass 76.06 ns 1.00 1,108 B -
MemoryPackSerializeTolerantClass 416.28 ns 5.47 1,164 B -
NinoDeserializeTolerantClasses 32.16 μs 1.00 - 253624 B
MemoryPackDeserializeTolerantClasses 54.74 μs 1.70 - 253624 B
NinoSerializeTolerantClasses 8.66 μs 1.00 110,804 B -
MemoryPackSerializeTolerantClasses 39.95 μs 4.61 116,404 B -

BclTypesTest

Method Mean Ratio Payload Allocated
NinoDeserializeImmutableDictionary 21.07 μs 1.00 - 68088 B
MemoryPackDeserializeImmutableDictionary 116.47 μs 5.53 - 56096 B
NinoSerializeImmutableDictionary 3.34 μs 1.00 8,004 B -
MemoryPackSerializeImmutableDictionary 26.99 μs 8.08 8,004 B -
NinoDeserializeImmutableHashSet 20.72 μs 1.00 - 64096 B
MemoryPackDeserializeImmutableHashSet 106.28 μs 5.13 - 56104 B
NinoSerializeImmutableHashSet 3.10 μs 1.00 4,004 B -
MemoryPackSerializeImmutableHashSet 23.94 μs 7.73 4,004 B -
NinoDeserializeImmutableQueue 7.57 μs 1.00 - 36064 B
MemoryPackDeserializeImmutableQueue 9.44 μs 1.25 - 32112 B
NinoSerializeImmutableQueue 1.98 μs 1.00 4,004 B -
MemoryPackSerializeImmutableQueue 9.44 μs 4.76 4,004 B -
NinoDeserializeImmutableSortedDictionary 13.58 μs 1.00 - 56072 B
MemoryPackDeserializeImmutableSortedDictionary 108.26 μs 7.98 - -
NinoSerializeImmutableSortedDictionary 3.11 μs 1.00 8,004 B -
MemoryPackSerializeImmutableSortedDictionary 9.53 μs 3.06 8,004 B -
NinoDeserializeImmutableSortedSet 13.00 μs 1.00 - 52056 B
MemoryPackDeserializeImmutableSortedSet 87.60 μs 6.74 - 48088 B
NinoSerializeImmutableSortedSet 2.80 μs 1.00 4,004 B -
MemoryPackSerializeImmutableSortedSet 18.33 μs 6.55 4,004 B -
NinoDeserializeImmutableStack 7.61 μs 1.00 - 36024 B
MemoryPackDeserializeImmutableStack 10.12 μs 1.33 - 32040 B
NinoSerializeImmutableStack 2.89 μs 1.00 4,004 B -
MemoryPackSerializeImmutableStack 17.14 μs 5.93 4,004 B 4112 B
NinoDeserializeBigInteger 17.31 ns 1.00 - 256 B
NinoSerializeBigInteger 8.79 ns 1.01 203 B -
NinoDeserializeBitArray 21.44 ns 1.00 - 336 B
NinoSerializeBitArray 12.69 ns 1.00 129 B -
NinoDeserializeBlockingCollection 5.69 μs 1.00 - 12792 B
MemoryPackDeserializeBlockingCollection 33.62 μs 5.90 - -
NinoSerializeBlockingCollection 2.89 μs 1.00 4,004 B 4096 B
MemoryPackSerializeBlockingCollection 6.04 μs 2.09 4,004 B 72 B
NinoDeserializeCultureInfo 29.60 ns 1.00 - 64 B
MemoryPackDeserializeCultureInfo 36.04 ns 1.22 - 64 B
NinoSerializeCultureInfo 3.10 ns 1.01 9 B -
MemoryPackSerializeCultureInfo 14.34 ns 4.64 13 B -
NinoDeserializeLazy 11.12 ns 1.01 - 112 B
MemoryPackDeserializeLazy 17.65 ns 1.60 - 112 B
NinoSerializeLazy 4.41 ns 1.01 27 B -
MemoryPackSerializeLazy 24.05 ns 5.51 31 B -
NinoDeserializeLookup 320.29 ns 1.00 - 5152 B
MemoryPackDeserializeLookup 392.88 ns 1.23 - 5576 B
NinoSerializeLookup 1.35 μs 1.00 4,084 B 1127 B
MemoryPackSerializeLookup 4.98 μs 3.70 4,094 B 320 B
NinoDeserializeMemory 124.25 ns 1.00 - 4056 B
MemoryPackDeserializeMemory 149.88 ns 1.21 - 4056 B
NinoSerializeMemory 21.98 ns 1.00 4,004 B -
MemoryPackSerializeMemory 39.04 ns 1.78 4,004 B -
NinoDeserializeReadOnlyCollection 250.64 ns 1.00 - 4048 B
MemoryPackDeserializeReadOnlyCollection 310.88 ns 1.24 - 4048 B
NinoSerializeReadOnlyCollection 2.35 μs 1.00 4,004 B 40 B
MemoryPackSerializeReadOnlyCollection 17.07 μs 7.27 4,004 B 40 B
NinoDeserializeReadOnlySequence 256.59 ns 1.00 - 4064 B
MemoryPackDeserializeReadOnlySequence 319.35 ns 1.25 - 4064 B
NinoSerializeReadOnlySequence 56.07 ns 1.00 4,004 B -
MemoryPackSerializeReadOnlySequence 74.27 ns 1.33 4,004 B -
NinoDeserializeStringBuilder 142.99 ns 1.00 - 2072 B
MemoryPackDeserializeStringBuilder 158.26 ns 1.11 - 2072 B
NinoSerializeStringBuilder 31.24 ns 1.00 2,004 B -
MemoryPackSerializeStringBuilder 52.58 ns 1.68 2,004 B -
NinoDeserializeTimeZoneInfo 13.74 ns 1.00 - 32 B
MemoryPackDeserializeTimeZoneInfo 362.35 ns 26.37 - 680 B
NinoSerializeTimeZoneInfo 12.00 ns 1.00 11 B -
MemoryPackSerializeTimeZoneInfo 279.10 ns 23.25 102 B 216 B
NinoDeserializeUri 108.22 ns 1.00 - 184 B
MemoryPackDeserializeUri 123.05 ns 1.14 - 184 B
NinoSerializeUri 10.46 ns 1.00 56 B -
MemoryPackSerializeUri 29.00 ns 2.77 60 B -
NinoDeserializeVersion 7.07 ns 1.00 - 32 B
MemoryPackDeserializeVersion 18.44 ns 2.61 - 32 B
NinoSerializeVersion 5.11 ns 1.00 16 B -
MemoryPackSerializeVersion 22.81 ns 4.46 17 B -

PolymorphicTest

Method Mean Ratio Payload Allocated
NinoDeserializePolymorphicClassArray 201.60 μs 1.00 - 745624 B
MemoryPackDeserializePolymorphicClassArray 392.17 μs 1.95 - 745624 B
NinoSerializePolymorphicClassArray 58.77 μs 1.00 397,304 B -
MemoryPackSerializePolymorphicClassArray 365.45 μs 6.22 384,404 B -
NinoDeserializePolymorphicClass 17.85 μs 1.00 - 79688 B
MemoryPackDeserializePolymorphicClass 30.57 μs 1.71 - 79688 B
NinoSerializePolymorphicClass 6.30 μs 1.00 53,789 B -
MemoryPackSerializePolymorphicClass 43.02 μs 6.83 51,760 B -
NinoDeserializePolymorphicFooArray 15.47 μs 1.00 - 76024 B
MemoryPackDeserializePolymorphicFooArray 28.26 μs 1.83 - 76024 B
NinoSerializePolymorphicFooArray 6.86 μs 1.00 52,404 B -
MemoryPackSerializePolymorphicFooArray 39.53 μs 5.76 50,404 B -

PooledGraphTest

Method Mean Ratio Payload Allocated
NinoLeavesNew 1.61 μs 1.00 - 13656 B
NinoLeavesPooledElements 1.36 μs 0.85 - 773 B
NinoLeavesInPlace 257.19 ns 0.16 - -
MemoryPackLeavesNew 1.89 μs 1.18 - 13656 B
MemoryPackLeavesOverwrite 2.24 μs 1.39 - 12800 B
NinoNodeNew 240.41 ns 1.00 - 2192 B
NinoNodePooled 70.31 ns 0.29 - -
MemoryPackNodeNew 319.21 ns 1.33 - 2192 B
MemoryPackNodeOverwrite 259.42 ns 1.08 - 1024 B
NinoPlainNew 1.49 μs 1.00 - 12856 B
MemoryPackPlainNew 1.81 μs 1.21 - 12856 B

CollectionsTest

Method Mean Ratio Payload Allocated
NinoDeserializeConcurrentDictionary 15.01 μs 1.00 - 49184 B
MemoryPackDeserializeConcurrentDictionary 56.44 μs 3.76 - 141032 B
NinoSerializeConcurrentDictionary 2.39 μs 1.00 8,004 B -
MemoryPackSerializeConcurrentDictionary 3.85 μs 1.62 8,004 B -
NinoDeserializeHashSet 2.58 μs 1.00 - 17768 B
MemoryPackDeserializeHashSet 6.56 μs 2.54 - 17768 B
NinoSerializeHashSet 325.03 ns 1.00 4,004 B -
MemoryPackSerializeHashSet 8.46 μs 26.01 4,004 B -
NinoDeserializeKeyValuePairs 423.64 ns 1.00 - 8024 B
MemoryPackDeserializeKeyValuePairs 458.82 ns 1.08 - 8024 B
NinoSerializeKeyValuePairs 88.87 ns 1.00 8,004 B -
MemoryPackSerializeKeyValuePairs 95.84 ns 1.08 8,004 B -
NinoDeserializeLinkedList 7.70 μs 1.00 - 48040 B
MemoryPackDeserializeLinkedList 10.02 μs 1.30 - 48040 B
NinoSerializeLinkedList 1.01 μs 1.00 4,004 B -
MemoryPackSerializeLinkedList 4.69 μs 4.62 4,004 B -
NinoDeserializeQueue 135.96 ns 1.00 - 4064 B
MemoryPackDeserializeQueue 2.11 μs 15.51 - 4064 B
NinoSerializeQueue 26.29 ns 1.00 4,004 B -
MemoryPackSerializeQueue 4.56 μs 173.44 4,004 B -
NinoDeserializeSortedDictionary 9.03 μs 1.00 - 48112 B
MemoryPackDeserializeSortedDictionary 27.54 μs 3.05 - -
NinoSerializeSortedDictionary 2.22 μs 1.00 8,004 B -
MemoryPackSerializeSortedDictionary 3.78 μs 1.71 8,004 B 200 B
NinoDeserializeSortedList 1.08 μs 1.00 - 8112 B
MemoryPackDeserializeSortedList 8.97 μs 8.30 - 8112 B
NinoSerializeSortedList 966.50 ns 1.00 8,004 B -
MemoryPackSerializeSortedList 1.98 μs 2.05 8,004 B -
NinoDeserializeSortedSet 8.21 μs 1.00 - 40048 B
MemoryPackDeserializeSortedSet 26.11 μs 3.18 - 40048 B
NinoSerializeSortedSet 1.50 μs 1.00 4,004 B -
MemoryPackSerializeSortedSet 6.62 μs 4.42 4,004 B 200 B
NinoDeserializeTupleList 501.60 ns 1.00 - 16056 B
MemoryPackDeserializeTupleList 526.35 ns 1.05 - 16056 B
NinoSerializeTupleList 78.61 ns 1.02 12,004 B -
MemoryPackSerializeTupleList 82.18 ns 1.07 16,004 B -

ReferenceTest

Method Mean Ratio Payload Allocated
NinoDeserializeGraph 3.46 μs 1.00 - 14104 B
MemoryPackDeserializeGraph 11.73 μs 3.39 - 14104 B
NinoSerializeGraph 3.00 μs 1.00 5,878 B -
MemoryPackSerializeGraph 17.61 μs 5.87 5,584 B -

The classes ran in parallel, each on its own runner (a class's Nino and MemoryPack cases on one):

  • PooledTest, SimpleTest: INTEL XEON PLATINUM 8573C 3.50GHz, 1 CPU, 4 logical and 2 physical cores
  • CommonTypesTest, FixedSizeTest: AMD EPYC 9V74 2.87GHz, 1 CPU, 4 logical and 2 physical cores
  • GenericPolymorphicTest, VersionTolerantTest: AMD EPYC 9V74 3.69GHz, 1 CPU, 4 logical and 2 physical cores
  • BclTypesTest, PolymorphicTest: AMD EPYC 7763 2.69GHz, 1 CPU, 4 logical and 2 physical cores
  • BclTypesTest, PooledGraphTest: AMD EPYC 9V45 4.53GHz, 1 CPU, 4 logical and 2 physical cores
  • BclTypesTest, CollectionsTest: AMD EPYC 7763 2.66GHz, 1 CPU, 4 logical and 2 physical cores
  • CollectionsTest, ReferenceTest: AMD EPYC 9V45 4.20GHz, 1 CPU, 4 logical and 2 physical cores

Median, Min, Max and the GC counts: benchmark-x64-full.md.


Benchmark generated automatically on 2026-10-23 10:43:06 UTC