As part of a YouTube video, I went through a bunch of serializers to see their current levels of performance. As it’s been a while, I thought it would be a good idea to get the latest numbers and have a general update. The code is hosted on a Github Repository, which I’m happy to accept community contributions on including fixing any minor issues or adding serialization frameworks.

Changes In This Benchmark

  • Bebop allocations have been improved thanks to AndrewMD5 (PR)
  • Added SourceGenerator version of System.Text.Json
  • Added MemoryPack to the Binary Benchmarks

Package Updates

The repository now has Renovate dependency bot installed, meaning that the repository will automatically update to the latest version of all of the packages.

PackageTypeUpdateChange
AvroConvert (source)nugetminor3.2.9 -> 3.3.2
BenchmarkDotNetnugetpatch0.13.2 -> 0.13.5
MessagePacknugetpatch2.4.35 -> 2.4.59
MongoDB.Bson (source)nugetminor2.17.1 -> 2.19.0
Newtonsoft.Json (source)nugetpatch13.0.1 -> 13.0.2
ServiceStack.Textnugetminor6.2.0 -> 6.6.0
SpanJsonnugetmajor3.3.1 -> 4.0.0
bebopnugetpatch2.4.6 -> 2.4.9
bebop-toolsnugetpatch2.4.6 -> 2.4.9
protobuf-netnugetminor3.1.17 -> 3.2.0

Test Rig Details

BenchmarkDotNet=v0.13.5, OS=Windows 11 (10.0.22621.1265/22H2/2022Update/SunValley2)
Intel Core i9-9900K CPU 3.60GHz (Coffee Lake), 1 CPU, 8 logical and 4 physical cores
.NET SDK=7.0.200
[Host]     : .NET 7.0.3 (7.0.323.6910), X64 RyuJIT AVX2
DefaultJob : .NET 7.0.3 (7.0.323.6910), X64 RyuJIT AVX2

JSON Serialization Results

MethoddataMeanErrorStdDevMedianMinMaxRatioRatioSDGen0Gen1Gen2AllocatedAlloc Ratio
SpanJson_DeserializeLarge91,190.8 us1,811.48 us4,374.94 us89,969.2 us83,768.1 us104,369.6 us0.660.054000.00003833.3333666.666744667.44 KB1.00
Jil_DeserializeLarge100,230.1 us1,943.11 us2,237.69 us100,638.2 us96,002.4 us103,568.0 us0.720.024000.00003833.3333666.666727753.73 KB0.62
UTF8Json_DeserializeLarge109,200.0 us2,085.04 us2,047.79 us109,092.9 us105,728.9 us113,311.5 us0.790.023800.00003600.0000600.000044666.62 KB1.00
SystemTextJson_DeserializeLarge138,832.0 us1,958.74 us1,832.20 us138,740.8 us136,207.2 us141,876.0 us1.000.003750.00003500.0000500.000044668.96 KB1.00
SystemTextJson_SrcGen_DeserializeLarge140,451.0 us2,175.38 us2,034.85 us140,515.7 us137,389.1 us144,502.9 us1.010.023750.00003500.0000500.000044668.96 KB1.00
ServiceStack_DeserializeLarge220,351.1 us4,329.13 us7,112.88 us218,680.2 us210,853.8 us238,109.4 us1.580.064666.66672333.3333333.333337471.89 KB0.84
NewtonsoftJson_DeserializeLarge249,970.0 us4,223.49 us4,519.08 us248,670.5 us244,194.6 us260,768.2 us1.800.045000.00002500.0000500.000039137.85 KB0.88
Jil_DeserializeMedium16,157.2 us266.15 us316.83 us16,072.6 us15,767.3 us16,985.5 us0.590.02843.7500750.0000-6935.28 KB0.62
SpanJson_DeserializeMedium16,572.0 us267.62 us237.24 us16,686.7 us16,136.5 us16,803.6 us0.610.011093.7500968.7500250.000011124.97 KB1.00
UTF8Json_DeserializeMedium21,231.9 us414.06 us552.76 us21,134.0 us20,066.9 us22,387.3 us0.780.031093.7500968.7500250.000011125.04 KB1.00
SystemTextJson_DeserializeMedium27,273.0 us329.03 us307.77 us27,179.3 us26,864.5 us28,011.8 us1.000.001093.7500968.7500250.000011125.72 KB1.00
SystemTextJson_SrcGen_DeserializeMedium27,648.3 us241.70 us214.26 us27,591.1 us27,366.2 us28,085.3 us1.010.021093.7500968.7500250.000011126.42 KB1.00
ServiceStack_DeserializeMedium48,323.4 us734.66 us687.20 us48,138.1 us47,236.9 us49,689.3 us1.770.031181.81821000.000090.90919357.83 KB0.84
NewtonsoftJson_DeserializeMedium55,349.4 us1,089.57 us2,298.27 us55,172.9 us51,556.2 us60,647.0 us2.050.071100.0000900.0000-9776.74 KB0.88
SpanJson_DeserializeSmall511.2 us9.20 us8.15 us509.2 us501.2 us528.3 us0.540.0151.757851.757851.7578446.93 KB1.60
Jil_DeserializeSmall564.0 us2.39 us2.00 us563.5 us561.7 us567.8 us0.600.0034.179710.7422-279.63 KB1.00
UTF8Json_DeserializeSmall665.7 us5.09 us4.76 us665.6 us658.7 us673.7 us0.710.0083.007861.523448.8281447.05 KB1.60
SystemTextJson_DeserializeSmall939.9 us1.45 us1.21 us939.7 us937.5 us941.7 us1.000.0034.179711.7188-279.71 KB1.00
SystemTextJson_SrcGen_DeserializeSmall983.0 us2.19 us1.94 us983.0 us979.7 us985.9 us1.050.0033.203111.7188-279.71 KB1.00
ServiceStack_DeserializeSmall1,551.9 us13.64 us12.76 us1,546.8 us1,535.9 us1,578.3 us1.650.0144.921913.6719-379.04 KB1.36
NewtonsoftJson_DeserializeSmall1,880.9 us28.69 us26.84 us1,886.8 us1,831.2 us1,914.5 us2.000.0346.875019.5313-398.46 KB1.42
SpanJson_SerializeLarge24,379.2 us67.39 us56.27 us24,383.5 us24,263.1 us24,476.9 us0.480.00125.0000125.0000125.000016384.13 KB0.48
UTF8Json_SerializeLarge39,032.1 us765.63 us1,419.15 us38,884.8 us36,683.0 us42,188.1 us0.800.03615.3846615.3846615.384682319.57 KB2.40
SystemTextJson_SrcGen_SerializeLarge49,655.5 us217.47 us181.60 us49,619.5 us49,443.4 us50,147.9 us0.980.00---34296.93 KB1.00
SystemTextJson_SerializeLarge50,513.3 us170.93 us151.53 us50,520.8 us50,184.7 us50,817.3 us1.000.00---34296.93 KB1.00
Jil_SerializeLarge53,530.0 us1,067.88 us1,425.59 us53,763.7 us50,595.6 us55,955.4 us1.070.035000.00004888.8889888.888967819 KB1.98
NewtonsoftJson_SerializeLarge125,169.9 us2,045.01 us1,812.85 us125,387.6 us122,390.9 us128,757.7 us2.480.046600.00003600.0000800.000081290.58 KB2.37
ServiceStack_SerializeLarge146,043.9 us293.87 us274.89 us145,935.9 us145,687.9 us146,551.0 us2.890.016000.0000--78487.63 KB2.29
SpanJson_SerializeMedium6,141.6 us56.25 us52.61 us6,155.3 us5,993.7 us6,201.1 us0.480.01117.1875117.1875117.18754096.11 KB0.48
UTF8Json_SerializeMedium10,055.7 us199.79 us177.11 us10,020.6 us9,819.5 us10,372.9 us0.780.02500.0000500.0000500.000020445.27 KB2.41
SystemTextJson_SerializeMedium12,890.4 us203.52 us190.38 us12,866.9 us12,676.6 us13,272.9 us1.000.00187.5000187.5000187.50008496.96 KB1.00
SystemTextJson_SrcGen_SerializeMedium13,029.8 us164.63 us153.99 us13,040.7 us12,804.6 us13,314.2 us1.010.02187.5000187.5000187.50008496.96 KB1.00
Jil_SerializeMedium16,192.0 us315.34 us410.04 us16,162.8 us15,534.3 us17,039.5 us1.260.051906.25001812.5000875.000016806.86 KB1.98
NewtonsoftJson_SerializeMedium31,214.2 us558.44 us948.28 us30,899.0 us30,212.6 us33,347.0 us2.410.072312.50001875.0000875.000020170.37 KB2.37
ServiceStack_SerializeMedium38,538.6 us314.84 us294.50 us38,582.1 us38,049.6 us39,009.7 us2.990.041571.4286142.8571142.857119358.84 KB2.28
SpanJson_SerializeSmall234.9 us0.43 us0.38 us234.9 us234.1 us235.3 us0.470.0075.683675.683675.6836256.07 KB0.75
UTF8Json_SerializeSmall303.2 us0.89 us0.84 us303.3 us301.8 us304.4 us0.610.00148.9258148.9258148.9258551.72 KB1.62
Jil_SerializeSmall436.1 us19.80 us58.37 us473.4 us322.6 us486.5 us0.700.0399.609499.609499.6094673.91 KB1.98
SystemTextJson_SerializeSmall499.2 us3.20 us2.84 us499.9 us492.4 us502.9 us1.000.0089.843889.843889.8438340.86 KB1.00
SystemTextJson_SrcGen_SerializeSmall503.1 us2.69 us2.38 us503.0 us498.8 us507.4 us1.010.0189.843889.843889.8438340.85 KB1.00
NewtonsoftJson_SerializeSmall1,102.0 us11.72 us9.15 us1,104.2 us1,081.5 us1,110.3 us2.210.03148.4375113.281389.8438821.44 KB2.41
ServiceStack_SerializeSmall1,581.4 us17.93 us16.77 us1,577.9 us1,562.8 us1,617.2 us3.170.04142.578182.031382.0313784.99 KB2.30

The JSON benchmarks appear to have remained pretty consistent with the previous set of results from a few months ago. The inclusion of the source generator version for System.Text.Json turned out to be a bit of a non-event in the end as the performance is on-par with the non-generator version. SpanJson is still the king for JSON.

Binary Serialization Results

MethoddataMeanErrorStdDevMinMaxGen0Gen1Gen2Allocated
GroBuf_DeserializeLarge47,243.86 us825.702 us772.362 us45,642.06 us48,513.91 us3636.36363545.4545545.454526179193 B
Bebop_DeserializeLarge48,244.74 us748.848 us700.473 us47,523.21 us49,245.47 us3909.09093818.1818727.272726980756 B
MemoryPack_DeserializeLarge48,738.47 us911.477 us852.597 us47,061.95 us50,501.60 us3636.36363545.4545545.454526179103 B
MessagePack_DeserializeLarge62,726.35 us1,155.674 us1,330.876 us60,548.57 us65,081.39 us3500.00003375.0000500.000026179115 B
ProtoBufNet_DeserializeLarge71,688.15 us1,416.613 us2,031.664 us69,305.33 us76,257.39 us3714.28573571.4286571.428626820875 B
Hyperion_DeserializeLarge87,696.21 us1,700.080 us1,889.634 us85,881.60 us91,572.22 us4166.66674000.0000500.000031180175 B
MsgPack_DeserializeLarge92,672.91 us1,770.147 us1,817.811 us89,019.35 us96,053.55 us4166.66674000.0000500.000032018907 B
AvroConvert_DeserializeLarge196,401.45 us3,830.642 us4,980.917 us187,416.40 us203,311.00 us10000.00003666.6667333.333396425000 B
BSON_DeserializeLarge235,586.13 us3,199.265 us2,836.065 us229,802.00 us240,312.37 us8333.33334333.3333333.333369298835 B
GroBuf_DeserializeMedium4,257.91 us62.966 us52.579 us4,179.05 us4,336.40 us773.4375703.1250-6533041 B
Bebop_DeserializeMedium4,402.57 us60.201 us56.312 us4,308.14 us4,478.53 us804.6875750.0000-6732454 B
MemoryPack_DeserializeMedium4,425.59 us43.134 us40.347 us4,370.96 us4,497.73 us773.4375703.1250-6532969 B
ProtoBufNet_DeserializeMedium8,896.05 us44.146 us39.134 us8,804.73 us8,960.84 us796.8750593.7500-6693108 B
MessagePack_DeserializeMedium8,967.02 us74.913 us66.408 us8,843.58 us9,075.46 us765.6250687.5000-6532978 B
Hyperion_DeserializeMedium13,124.22 us46.479 us41.203 us13,063.96 us13,210.24 us921.8750843.7500-7789506 B
MsgPack_DeserializeMedium13,680.20 us189.208 us202.450 us13,328.87 us14,038.78 us953.1250906.2500-7992954 B
AvroConvert_DeserializeMedium43,866.48 us713.613 us667.514 us42,987.47 us45,111.19 us2692.30771076.9231230.769224169490 B
BSON_DeserializeMedium59,161.54 us1,155.333 us1,080.699 us57,379.79 us60,921.69 us2222.22221222.2222222.222217298596 B
GroBuf_DeserializeSmall113.90 us1.860 us1.649 us111.64 us117.01 us31.494110.4980-263784 B
Bebop_DeserializeSmall116.13 us1.069 us1.000 us114.89 us118.71 us32.470712.0850-272000 B
MemoryPack_DeserializeSmall121.76 us0.376 us0.314 us120.74 us121.99 us31.494110.4980-263712 B
MessagePack_DeserializeSmall299.24 us0.495 us0.439 us298.79 us300.21 us31.250010.2539-263713 B
ProtoBufNet_DeserializeSmall302.80 us4.197 us6.152 us298.31 us321.27 us32.226610.7422-270233 B
Hyperion_DeserializeSmall354.44 us1.090 us1.019 us353.28 us356.81 us37.597712.6953-315425 B
MsgPack_DeserializeSmall463.82 us4.525 us4.232 us458.79 us472.56 us38.085912.6953-322225 B
AvroConvert_DeserializeSmall1,516.93 us8.215 us7.684 us1,504.66 us1,527.68 us134.765648.8281-1135455 B
BSON_DeserializeSmall1,697.43 us19.415 us18.161 us1,666.60 us1,727.83 us82.031327.3438-701884 B
MemoryPack_SerializeLarge9,668.02 us11.755 us9.816 us9,649.58 us9,682.30 us31.250031.250031.25009818513 B
GroBuf_SerializeLarge10,991.49 us13.141 us11.649 us10,968.58 us11,013.30 us62.500062.500062.500018824229 B
Bebop_SerializeLarge12,556.43 us55.511 us46.354 us12,493.10 us12,641.42 us---36 B
MessagePack_SerializeLarge16,490.02 us66.105 us61.834 us16,413.60 us16,612.91 us---7196899 B
ProtoBufNet_SerializeLarge27,214.02 us270.428 us239.727 us26,966.38 us27,802.83 us156.2500156.2500156.250027893153 B
Hyperion_SerializeLarge34,844.59 us425.809 us398.302 us34,004.25 us35,126.87 us600.000066.666766.666728827900 B
MsgPack_SerializeLarge40,435.03 us372.214 us329.958 us39,724.02 us40,921.32 us1230.7692384.6154307.692367710617 B
AvroConvert_SerializeLarge55,918.00 us640.324 us598.960 us54,529.86 us56,514.13 us4111.1111111.1111111.111178042956 B
BSON_SerializeLarge139,522.40 us1,145.433 us1,071.439 us137,698.95 us141,130.38 us4750.0000--90285250 B
MemoryPack_SerializeMedium2,344.52 us27.653 us24.514 us2,318.72 us2,405.98 us85.937585.937585.93752446033 B
GroBuf_SerializeMedium2,594.14 us51.653 us59.484 us2,480.14 us2,687.87 us109.3750109.3750109.37504688436 B
Bebop_SerializeMedium2,874.85 us8.709 us6.800 us2,869.72 us2,887.92 us---27 B
MessagePack_SerializeMedium4,229.39 us82.978 us77.618 us4,104.00 us4,339.72 us31.250031.250031.25001737144 B
ProtoBufNet_SerializeMedium7,162.14 us45.605 us40.428 us7,107.72 us7,238.80 us140.6250125.0000125.00007090069 B
Hyperion_SerializeMedium8,857.20 us29.018 us25.724 us8,821.47 us8,914.76 us296.8750156.2500156.25007197143 B
MsgPack_SerializeMedium9,629.06 us188.542 us376.539 us8,914.96 us10,518.29 us671.8750406.2500390.625015023469 B
AvroConvert_SerializeMedium16,328.77 us310.634 us305.085 us15,725.40 us16,876.81 us1375.0000562.5000343.750019539986 B
BSON_SerializeMedium37,320.81 us603.465 us564.481 us36,480.74 us38,157.81 us1428.5714285.7143285.714322510582 B
MemoryPack_SerializeSmall86.05 us0.790 us0.701 us85.32 us87.32 us16.113316.113316.113398798 B
GroBuf_SerializeSmall90.58 us1.163 us1.088 us89.51 us92.61 us27.221727.221727.2217189554 B
Bebop_SerializeSmall114.32 us0.799 us0.748 us113.45 us116.12 us---24 B
MessagePack_SerializeSmall159.42 us1.411 us1.178 us157.78 us161.28 us8.0566--69336 B
ProtoBufNet_SerializeSmall259.28 us3.939 us3.492 us252.99 us266.47 us26.85554.3945-228617 B
MsgPack_SerializeSmall281.98 us2.989 us2.496 us278.27 us285.97 us70.800812.2070-596033 B
Hyperion_SerializeSmall339.40 us2.626 us2.193 us335.48 us342.36 us52.246125.878922.4609384295 B
AvroConvert_SerializeSmall773.36 us8.749 us8.184 us763.25 us792.67 us129.882861.523444.9219983877 B
BSON_SerializeSmall1,449.58 us28.409 us29.174 us1,417.69 us1,504.62 us158.2031101.562595.70311093695 B

It appears that the PR for Bebop has definitely had the desired effect, basically putting it on par with GroBuf. GroBuf is still king for deserialization but it’s lost it’s crown for serialization by a small margin. The new king for binary serialization is MemoryPack by Neuecc. This is Neuecc’s forth serialization framework and appears to be making leaps in performance with each one.

As with any software, you should take these results as an indication of which framework to use - making sure that your business requirements are met first before optimizing for performance. Performance itself can mean either speed or memory usage, depending on your requirements.