A few years back I had to write a base view model which is not aware of the model that will be used with it as generic. Only thing that the base view model knows is that every model will definitely have a Name property. And I had to write all the logic to set the properties of this Model in the base only as it was common and we used to receive the property name(string) and value(object) from SignalR. I used reflection as I am not aware of the properties of Model’s used in child view models. Slowly as the number of child viewmodels increased and the list of object’s(Model’s) inside each child view model, I started seeing the problem. Then I clearly understood that reflection is the major reason for the performance issue.
Then after some thorough research, I did some benchmarks to see how much does reflection cost me vs using an interface and implementing those methods in every model and making it strongly typed and avoiding reflection.
Version 1:
I wrote a new simple interface.
public interface IObject
{
bool SetValue(string propertyName, object value);
object GetValue(string propertyName);
T GetValue<T>(string propertyName); // I skipped the implementation of this in this post. Please find that in source code.
}
and it’s implementation is like.
public class FooV1 : IObject
{
public int Integer { get; set; } = int.MaxValue;
public string String { get; set; } = "some random string";
public object GetValue(string propertyName)
{
return propertyName switch
{
nameof(Integer) => Integer,
nameof(String) => String,
_ => null,
};
}
public bool SetValue(string propertyName, object value)
{
switch (propertyName)
{
case nameof(Integer):
{
Integer = (int)value;
return true;
}
case nameof(String):
{
String = (string)value;
return true;
}
default:
return false;
}
}
}
When I did the benchmarks for setting a value using reflection, I saw using an interface brought down the time taken to set a property to a min of 70% and max of 91%.
As this worked out very well, and I had too many model’s so I built our own source generator using a console app as I was using .NET6 where the source generators are still experimental. And this whole implementation brought down our app launch time from 60+ seconds to less than 20 seconds. Btw, the properties inside the Model used to change very rarely. So when they did, we used to run the generator again and copy the files. And we ensure these generated files should never be changed manually and named them something like Foo.g.cs which helps me review the PR’s easily from the team. And ofcourse, I wrote an API to return the properties and their metadata in the way that I need so that my generator can generate the classes for me.
Version 2: (Update on 16th March 2025)
Uses ReadOnlySpan<char> but same like V3.
Version 3: (Update on 22th March 2025)
I read in multiple blogs that .NET invested a lot in performance improvement using ReadOnlySpan over the years. I was wondering if we can still make this better. So I tried again with ChatGPT help. Now compared to V1, V2 had at least 40% improvement over V1.
Nothing changed in my interface. But the implementation changed a bit.
public class Foo : IObject
{
public int Integer { get; set; } = int.MaxValue;
public string String { get; set; } = "some random string";
}
And my implementation is like
[MethodImpl(MethodImplOptions.AggressiveInlining)]
public bool SetValue(string propertyName, object value)
{
switch (propertyName.Length)
{
case 6 when string.CompareOrdinal(propertyName, "String") == 0:
String = (string)value;
return true;
case 7 when string.CompareOrdinal(propertyName, "Integer") == 0:
Integer = (int)value;
return true;
}
return false;
}
[MethodImpl(MethodImplOptions.AggressiveInlining)]
public object GetValue(string propertyName)
{
return propertyName.Length switch
{
6 when string.CompareOrdinal(propertyName, "String") == 0 => String,
7 when string.CompareOrdinal(propertyName, "Integer") == 0 => Integer,
_ => Unsafe.NullRef<object>(),
};
}
As I said, I took ChatGPT help, I am not 100% sure how MethodImpl helps.
Major benefits I saw are switch case speed was improved by 20% at least when I was checking the lenhth of the property name first.
Here are the benchmarks (Source Models)
- Reflection_Without_Cache
- Reflection_With_Cache
- V1 - use
nameof(Integer)inside switch - V2 - use
case 8 when span.SequenceEqual("DateTime")inside switch - V3 - use ` case 4 when string.CompareOrdinal(propertyName, “Guid”) == 0` inside switch
For some scenarios, V1 and V2 are better than V3. But ultimately V1, V2, V3 are found to be much faster than reflection.
.NET 8 only.
BenchmarkDotNet v0.14.0, Windows 11 (10.0.26100.3476)
Unknown processor
.NET SDK 9.0.201
[Host] : .NET 8.0.13 (8.0.1325.6609), X64 RyuJIT AVX2
Job-WPGPLG : .NET 8.0.13 (8.0.1325.6609), X64 RyuJIT AVX2
OutlierMode=DontRemove Runtime=.NET 8.0
| Method | Categories | Mean | Error | StdDev | StdErr | Median | Min | Q1 | Q3 | Max | Op/s | Ratio | MannWhitney(10%) | RatioSD | Rank | Baseline | Gen0 | Gen1 | Allocated | Alloc Ratio |
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| NoReflection_V2_Set_DateTime | Get_DateTime | 4.5517 ns | 0.2983 ns | 0.8796 ns | 0.0880 ns | 4.2290 ns | 3.4317 ns | 3.8785 ns | 4.9696 ns | 7.8496 ns | 219,700,020.8 | 0.000 | Faster | 0.00 | 1 | No | 0.0019 | - | 24 B | 0.002 |
| NoReflection_V3_Set_DateTime | Get_DateTime | 4.7152 ns | 0.2273 ns | 0.6703 ns | 0.0670 ns | 4.6290 ns | 3.4477 ns | 4.2965 ns | 5.0264 ns | 7.2109 ns | 212,080,656.2 | 0.000 | Faster | 0.00 | 1 | No | 0.0019 | - | 24 B | 0.002 |
| NoReflection_V1_Set_DateTime | Get_DateTime | 4.7909 ns | 0.2835 ns | 0.8359 ns | 0.0836 ns | 4.5264 ns | 3.3833 ns | 4.2094 ns | 5.3136 ns | 7.4346 ns | 208,727,204.8 | 0.000 | Faster | 0.00 | 1 | No | 0.0019 | - | 24 B | 0.002 |
| Reflection_With_Cache_Set_DateTime | Get_DateTime | 21.8594 ns | 0.6201 ns | 1.8284 ns | 0.1828 ns | 21.3681 ns | 19.6099 ns | 20.7650 ns | 22.1471 ns | 30.0197 ns | 45,746,892.2 | 0.000 | Faster | 0.00 | 2 | No | 0.0019 | - | 24 B | 0.002 |
| Reflection_Without_Cache_Set_DateTime | Get_DateTime | 134,661.9640 ns | 2,691.1319 ns | 7,412.1594 ns | 790.1388 ns | 133,193.8232 ns | 123,581.5552 ns | 130,676.0071 ns | 136,705.8472 ns | 177,430.4810 ns | 7,426.0 | 1.003 | Baseline | 0.07 | 3 | Yes | 0.7324 | 0.4883 | 9869 B | 1.000 |
| NoReflection_V3_Set_DateTimeOffset | Get_DateTimeOffset | 3.7162 ns | 0.1290 ns | 0.2083 ns | 0.0357 ns | 3.7949 ns | 3.2027 ns | 3.5734 ns | 3.8436 ns | 4.0136 ns | 269,089,492.3 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| NoReflection_V2_Set_DateTimeOffset | Get_DateTimeOffset | 4.0179 ns | 0.1463 ns | 0.4313 ns | 0.0431 ns | 3.8755 ns | 3.5427 ns | 3.7683 ns | 4.1254 ns | 6.0838 ns | 248,887,791.9 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| NoReflection_V1_Set_DateTimeOffset | Get_DateTimeOffset | 4.1067 ns | 0.1277 ns | 0.1470 ns | 0.0329 ns | 4.0821 ns | 3.8588 ns | 4.0282 ns | 4.2195 ns | 4.3973 ns | 243,504,377.2 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| Reflection_With_Cache_Set_DateTimeOffset | Get_DateTimeOffset | 22.9583 ns | 0.4975 ns | 0.6642 ns | 0.1328 ns | 22.8489 ns | 21.5919 ns | 22.5537 ns | 23.3382 ns | 24.5150 ns | 43,557,325.1 | 0.000 | Faster | 0.00 | 2 | No | 0.0025 | - | 32 B | 0.003 |
| Reflection_Without_Cache_Set_DateTimeOffset | Get_DateTimeOffset | 137,139.4918 ns | 2,729.6094 ns | 6,487.2061 ns | 792.5384 ns | 136,235.6445 ns | 125,979.3457 ns | 133,105.0781 ns | 139,492.0898 ns | 156,980.2246 ns | 7,291.8 | 1.002 | Baseline | 0.07 | 3 | Yes | 0.7324 | 0.4883 | 9877 B | 1.000 |
| NoReflection_V1_Set_Decimal | Get_Decimal | 3.7811 ns | 0.1228 ns | 0.3035 ns | 0.0358 ns | 3.7175 ns | 3.3545 ns | 3.5838 ns | 3.8663 ns | 4.8348 ns | 264,470,348.3 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| NoReflection_V2_Set_Decimal | Get_Decimal | 4.0014 ns | 0.1239 ns | 0.1695 ns | 0.0333 ns | 3.9680 ns | 3.7608 ns | 3.8577 ns | 4.1279 ns | 4.3559 ns | 249,914,466.0 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| NoReflection_V3_Set_Decimal | Get_Decimal | 4.0153 ns | 0.1281 ns | 0.1258 ns | 0.0315 ns | 4.0288 ns | 3.7534 ns | 3.9167 ns | 4.1218 ns | 4.2130 ns | 249,045,715.4 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| Reflection_With_Cache_Set_Decimal | Get_Decimal | 20.5950 ns | 0.4473 ns | 0.5657 ns | 0.1180 ns | 20.4532 ns | 19.7400 ns | 20.1383 ns | 21.0274 ns | 21.6487 ns | 48,555,358.9 | 0.000 | Faster | 0.00 | 2 | No | 0.0025 | - | 32 B | 0.003 |
| Reflection_Without_Cache_Set_Decimal | Get_Decimal | 134,489.7712 ns | 2,631.0768 ns | 4,538.4785 ns | 736.2384 ns | 133,503.2104 ns | 127,546.0693 ns | 131,537.1033 ns | 136,604.9133 ns | 146,288.9893 ns | 7,435.5 | 1.001 | Baseline | 0.05 | 3 | Yes | 0.7324 | 0.4883 | 9877 B | 1.000 |
| NoReflection_V3_Set_Double | Get_Double | 3.5649 ns | 0.1177 ns | 0.1308 ns | 0.0300 ns | 3.5514 ns | 3.3009 ns | 3.4836 ns | 3.6701 ns | 3.8001 ns | 280,513,385.0 | 0.000 | Faster | 0.00 | 1 | No | 0.0019 | - | 24 B | 0.002 |
| NoReflection_V1_Set_Double | Get_Double | 3.6716 ns | 0.1213 ns | 0.3044 ns | 0.0354 ns | 3.6054 ns | 3.2118 ns | 3.4908 ns | 3.7530 ns | 5.0924 ns | 272,358,381.0 | 0.000 | Faster | 0.00 | 1 | No | 0.0019 | - | 24 B | 0.002 |
| NoReflection_V2_Set_Double | Get_Double | 3.7531 ns | 0.1216 ns | 0.1447 ns | 0.0316 ns | 3.7683 ns | 3.5128 ns | 3.6303 ns | 3.8475 ns | 4.0238 ns | 266,449,272.1 | 0.000 | Faster | 0.00 | 1 | No | 0.0019 | - | 24 B | 0.002 |
| Reflection_With_Cache_Set_Double | Get_Double | 19.2798 ns | 0.4345 ns | 0.5650 ns | 0.1153 ns | 19.1776 ns | 18.0503 ns | 18.9049 ns | 19.7031 ns | 20.4502 ns | 51,867,729.6 | 0.000 | Faster | 0.00 | 2 | No | 0.0019 | - | 24 B | 0.002 |
| Reflection_Without_Cache_Set_Double | Get_Double | 129,740.5649 ns | 2,579.6557 ns | 3,616.3173 ns | 695.9606 ns | 129,637.7808 ns | 119,660.0220 ns | 128,151.2939 ns | 131,464.3677 ns | 138,131.7017 ns | 7,707.7 | 1.001 | Baseline | 0.04 | 3 | Yes | 0.7324 | 0.4883 | 9869 B | 1.000 |
| NoReflection_V1_Set_Guid | Get_Guid | 3.7056 ns | 0.1230 ns | 0.2341 ns | 0.0349 ns | 3.6541 ns | 3.3387 ns | 3.5241 ns | 3.8523 ns | 4.2413 ns | 269,862,033.1 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| NoReflection_V3_Set_Guid | Get_Guid | 3.7767 ns | 0.1229 ns | 0.1262 ns | 0.0306 ns | 3.7678 ns | 3.5814 ns | 3.6889 ns | 3.8115 ns | 4.0256 ns | 264,779,728.0 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| NoReflection_V2_Set_Guid | Get_Guid | 3.8309 ns | 0.1226 ns | 0.3231 ns | 0.0359 ns | 3.7543 ns | 3.3759 ns | 3.6551 ns | 3.9058 ns | 4.9528 ns | 261,034,235.7 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| Reflection_With_Cache_Set_Guid | Get_Guid | 19.8743 ns | 0.4411 ns | 0.4126 ns | 0.1065 ns | 19.8063 ns | 19.3926 ns | 19.6436 ns | 20.0446 ns | 21.0902 ns | 50,316,263.3 | 0.000 | Faster | 0.00 | 2 | No | 0.0025 | - | 32 B | 0.003 |
| Reflection_Without_Cache_Set_Guid | Get_Guid | 135,491.5876 ns | 2,743.1428 ns | 8,088.2191 ns | 808.8219 ns | 133,703.3081 ns | 124,534.2773 ns | 130,160.0647 ns | 137,751.4526 ns | 171,266.7236 ns | 7,380.5 | 1.003 | Baseline | 0.08 | 3 | Yes | 0.7324 | 0.4883 | 9877 B | 1.000 |
| NoReflection_V2_Set_Integer | Get_Integer | 3.5274 ns | 0.1202 ns | 0.1235 ns | 0.0299 ns | 3.5408 ns | 3.2584 ns | 3.4917 ns | 3.6042 ns | 3.8026 ns | 283,492,711.1 | 0.000 | Faster | 0.00 | 1 | No | 0.0019 | - | 24 B | 0.002 |
| NoReflection_V3_Set_Integer | Get_Integer | 3.7825 ns | 0.1513 ns | 0.4460 ns | 0.0446 ns | 3.6393 ns | 3.3081 ns | 3.5307 ns | 3.8380 ns | 5.3877 ns | 264,372,830.3 | 0.000 | Faster | 0.00 | 1 | No | 0.0019 | - | 24 B | 0.002 |
| NoReflection_V1_Set_Integer | Get_Integer | 3.8396 ns | 0.1351 ns | 0.3982 ns | 0.0398 ns | 3.7218 ns | 3.3032 ns | 3.6317 ns | 3.8514 ns | 5.4046 ns | 260,442,978.2 | 0.000 | Faster | 0.00 | 1 | No | 0.0019 | - | 24 B | 0.002 |
| Reflection_With_Cache_Set_Integer | Get_Integer | 19.0440 ns | 0.4303 ns | 0.6571 ns | 0.1180 ns | 18.8650 ns | 18.1617 ns | 18.5483 ns | 19.4110 ns | 20.6893 ns | 52,509,882.9 | 0.000 | Faster | 0.00 | 2 | No | 0.0019 | - | 24 B | 0.002 |
| Reflection_Without_Cache_Set_Integer | Get_Integer | 126,710.4232 ns | 2,499.3397 ns | 2,337.8839 ns | 603.6390 ns | 126,187.4023 ns | 123,532.2754 ns | 125,077.6245 ns | 128,073.9624 ns | 131,795.9961 ns | 7,892.0 | 1.000 | Baseline | 0.03 | 3 | Yes | 0.7324 | 0.4883 | 9869 B | 1.000 |
| NoReflection_V3_Set_String | Get_String | 0.0782 ns | 0.0466 ns | 0.0654 ns | 0.0126 ns | 0.0658 ns | 0.0000 ns | 0.0329 ns | 0.0962 ns | 0.2702 ns | 12,781,470,817.8 | 0.000 | Faster | 0.00 | 1 | No | - | - | - | 0.00 |
| NoReflection_V1_Set_String | Get_String | 0.2158 ns | 0.0503 ns | 0.0470 ns | 0.0121 ns | 0.2134 ns | 0.1162 ns | 0.1817 ns | 0.2613 ns | 0.2772 ns | 4,633,337,326.3 | 0.000 | Faster | 0.00 | 2 | No | - | - | - | 0.00 |
| NoReflection_V2_Set_String | Get_String | 0.2952 ns | 0.0601 ns | 0.1772 ns | 0.0177 ns | 0.2639 ns | 0.0904 ns | 0.1982 ns | 0.3172 ns | 1.1964 ns | 3,387,405,487.9 | 0.000 | Faster | 0.00 | 2 | No | - | - | - | 0.00 |
| Reflection_With_Cache_Set_String | Get_String | 15.6339 ns | 0.3505 ns | 0.4173 ns | 0.0911 ns | 15.6530 ns | 14.7821 ns | 15.3859 ns | 15.8924 ns | 16.4015 ns | 63,963,611.2 | 0.000 | Faster | 0.00 | 3 | No | - | - | - | 0.00 |
| Reflection_Without_Cache_Set_String | Get_String | 118,884.1680 ns | 2,586.5382 ns | 7,626.4669 ns | 762.6467 ns | 117,331.6162 ns | 111,331.3843 ns | 115,293.2861 ns | 120,267.0593 ns | 164,474.0601 ns | 8,411.5 | 1.003 | Baseline | 0.08 | 4 | Yes | 0.7324 | 0.4883 | 9845 B | 1.00 |
| NoReflection_V2_Get_DateTime | Set_DateTime | 2.8906 ns | 0.1041 ns | 0.3070 ns | 0.0307 ns | 2.8211 ns | 2.4469 ns | 2.6998 ns | 2.9995 ns | 4.0856 ns | 345,950,412.4 | 0.000 | Faster | 0.00 | 1 | No | 0.0019 | - | 24 B | 0.002 |
| NoReflection_V3_Get_DateTime | Set_DateTime | 3.1750 ns | 0.1230 ns | 0.3625 ns | 0.0363 ns | 3.0762 ns | 2.8220 ns | 2.9759 ns | 3.2142 ns | 5.2140 ns | 314,963,146.1 | 0.000 | Faster | 0.00 | 2 | No | 0.0019 | - | 24 B | 0.002 |
| NoReflection_V1_Get_DateTime | Set_DateTime | 5.2101 ns | 0.1803 ns | 0.5315 ns | 0.0531 ns | 5.0712 ns | 4.7095 ns | 4.9405 ns | 5.2395 ns | 8.2705 ns | 191,934,799.5 | 0.000 | Faster | 0.00 | 3 | No | 0.0019 | - | 24 B | 0.002 |
| Reflection_With_Cache_Get_DateTime | Set_DateTime | 20.1890 ns | 0.4316 ns | 0.4037 ns | 0.1042 ns | 20.1776 ns | 19.6258 ns | 19.9135 ns | 20.4161 ns | 21.2007 ns | 49,532,045.7 | 0.000 | Faster | 0.00 | 4 | No | 0.0019 | - | 24 B | 0.002 |
| Reflection_Without_Cache_Get_DateTime | Set_DateTime | 130,268.6307 ns | 2,597.7659 ns | 3,555.8516 ns | 697.3599 ns | 129,806.9580 ns | 124,744.2383 ns | 127,990.5579 ns | 132,300.6104 ns | 139,301.9287 ns | 7,676.4 | 1.001 | Baseline | 0.04 | 5 | Yes | 0.7324 | 0.4883 | 9869 B | 1.000 |
| NoReflection_V3_Get_DateTimeOffset | Set_DateTimeOffset | 3.0432 ns | 0.0960 ns | 0.1495 ns | 0.0264 ns | 3.1056 ns | 2.6898 ns | 2.9241 ns | 3.1514 ns | 3.2748 ns | 328,598,384.2 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| NoReflection_V2_Get_DateTimeOffset | Set_DateTimeOffset | 3.4683 ns | 0.0951 ns | 0.1096 ns | 0.0245 ns | 3.4397 ns | 3.3095 ns | 3.4105 ns | 3.5001 ns | 3.7342 ns | 288,328,118.2 | 0.000 | Faster | 0.00 | 2 | No | 0.0025 | - | 32 B | 0.003 |
| Reflection_With_Cache_Get_DateTimeOffset | Set_DateTimeOffset | 23.8058 ns | 0.5025 ns | 1.2972 ns | 0.1469 ns | 23.4511 ns | 22.2782 ns | 23.0489 ns | 24.1136 ns | 29.5990 ns | 42,006,550.4 | 0.000 | Faster | 0.00 | 3 | No | 0.0025 | - | 32 B | 0.003 |
| NoReflection_V1_Get_DateTimeOffset | Set_DateTimeOffset | 317.5865 ns | 6.3141 ns | 6.4841 ns | 1.5726 ns | 316.9801 ns | 306.2600 ns | 313.6859 ns | 323.1713 ns | 331.3868 ns | 3,148,748.2 | 0.002 | Faster | 0.00 | 4 | No | 0.0086 | - | 112 B | 0.011 |
| Reflection_Without_Cache_Get_DateTimeOffset | Set_DateTimeOffset | 137,027.1792 ns | 2,730.2798 ns | 7,877.4822 ns | 803.9922 ns | 134,812.8906 ns | 124,553.1372 ns | 131,685.6934 ns | 139,315.8020 ns | 162,161.8774 ns | 7,297.8 | 1.003 | Baseline | 0.08 | 5 | Yes | 0.7324 | 0.4883 | 9877 B | 1.000 |
| NoReflection_V1_Get_Decimal | Set_Decimal | 6.2628 ns | 0.1259 ns | 0.1178 ns | 0.0304 ns | 6.2240 ns | 6.1194 ns | 6.1524 ns | 6.3526 ns | 6.4604 ns | 159,673,612.8 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| NoReflection_V3_Get_Decimal | Set_Decimal | 6.3059 ns | 0.1663 ns | 0.4904 ns | 0.0490 ns | 6.1845 ns | 5.7768 ns | 6.0436 ns | 6.4363 ns | 8.9667 ns | 158,580,496.6 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| NoReflection_V2_Get_Decimal | Set_Decimal | 6.4429 ns | 0.3363 ns | 0.9915 ns | 0.0992 ns | 6.2171 ns | 5.6030 ns | 6.0364 ns | 6.3887 ns | 11.3938 ns | 155,210,034.8 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| Reflection_With_Cache_Get_Decimal | Set_Decimal | 20.3052 ns | 0.4326 ns | 1.2201 ns | 0.1272 ns | 19.9694 ns | 18.3997 ns | 19.6820 ns | 20.5008 ns | 26.4400 ns | 49,248,471.1 | 0.000 | Faster | 0.00 | 2 | No | 0.0025 | - | 32 B | 0.003 |
| Reflection_Without_Cache_Get_Decimal | Set_Decimal | 137,143.1565 ns | 2,936.4919 ns | 8,658.3132 ns | 865.8313 ns | 135,118.4082 ns | 127,400.3540 ns | 132,145.0684 ns | 138,664.0930 ns | 173,335.6812 ns | 7,291.7 | 1.004 | Baseline | 0.08 | 3 | Yes | 0.7324 | 0.4883 | 9877 B | 1.000 |
| NoReflection_V1_Get_Double | Set_Double | 2.6467 ns | 0.0812 ns | 0.2223 ns | 0.0238 ns | 2.5704 ns | 2.3163 ns | 2.5037 ns | 2.7248 ns | 3.3613 ns | 377,831,827.0 | 0.000 | Faster | 0.00 | 1 | No | 0.0019 | - | 24 B | 0.002 |
| NoReflection_V2_Get_Double | Set_Double | 2.9580 ns | 0.0971 ns | 0.2862 ns | 0.0286 ns | 2.8888 ns | 2.6219 ns | 2.7903 ns | 3.0067 ns | 4.1613 ns | 338,070,224.4 | 0.000 | Faster | 0.00 | 2 | No | 0.0019 | - | 24 B | 0.002 |
| NoReflection_V3_Get_Double | Set_Double | 3.1474 ns | 0.1019 ns | 0.3005 ns | 0.0300 ns | 3.0606 ns | 2.7716 ns | 2.9684 ns | 3.1827 ns | 4.2605 ns | 317,723,917.8 | 0.000 | Faster | 0.00 | 3 | No | 0.0019 | - | 24 B | 0.002 |
| Reflection_With_Cache_Get_Double | Set_Double | 20.4806 ns | 0.7390 ns | 2.1791 ns | 0.2179 ns | 19.6909 ns | 18.3152 ns | 19.3207 ns | 20.9957 ns | 29.3660 ns | 48,826,672.0 | 0.000 | Faster | 0.00 | 4 | No | 0.0019 | - | 24 B | 0.002 |
| Reflection_Without_Cache_Get_Double | Set_Double | 129,202.4500 ns | 2,531.6658 ns | 4,298.9609 ns | 706.7448 ns | 129,334.4727 ns | 121,357.5684 ns | 125,726.1230 ns | 131,337.5000 ns | 141,482.3975 ns | 7,739.8 | 1.001 | Baseline | 0.05 | 5 | Yes | 0.7324 | 0.4883 | 9869 B | 1.000 |
| NoReflection_V3_Get_Guid | Set_Guid | 2.8940 ns | 0.0859 ns | 0.2534 ns | 0.0253 ns | 2.8206 ns | 2.6164 ns | 2.7380 ns | 2.9600 ns | 3.8257 ns | 345,543,118.1 | 0.000 | Faster | 0.00 | 1 | No | 0.0025 | - | 32 B | 0.003 |
| NoReflection_V2_Get_Guid | Set_Guid | 3.3165 ns | 0.0944 ns | 0.2279 ns | 0.0274 ns | 3.2616 ns | 3.0444 ns | 3.1606 ns | 3.4025 ns | 4.1803 ns | 301,523,790.6 | 0.000 | Faster | 0.00 | 2 | No | 0.0025 | - | 32 B | 0.003 |
| Reflection_With_Cache_Get_Guid | Set_Guid | 20.7118 ns | 1.2184 ns | 3.5926 ns | 0.3593 ns | 19.4997 ns | 16.0189 ns | 18.9454 ns | 21.6103 ns | 39.6250 ns | 48,281,562.7 | 0.000 | Faster | 0.00 | 3 | No | 0.0025 | - | 32 B | 0.003 |
| NoReflection_V1_Get_Guid | Set_Guid | 30.0480 ns | 0.6153 ns | 0.6839 ns | 0.1569 ns | 29.9435 ns | 28.9659 ns | 29.6475 ns | 30.5377 ns | 31.2570 ns | 33,280,091.6 | 0.000 | Faster | 0.00 | 4 | No | 0.0102 | - | 128 B | 0.013 |
| Reflection_Without_Cache_Get_Guid | Set_Guid | 132,874.0360 ns | 2,604.8178 ns | 3,977.8322 ns | 714.4398 ns | 132,995.6787 ns | 124,531.3721 ns | 130,434.8755 ns | 134,868.2983 ns | 141,678.2715 ns | 7,525.9 | 1.001 | Baseline | 0.04 | 5 | Yes | 0.7324 | 0.4883 | 9877 B | 1.000 |
| NoReflection_V1_Get_Integer | Set_Integer | 2.7217 ns | 0.0670 ns | 0.0627 ns | 0.0162 ns | 2.7441 ns | 2.6047 ns | 2.6768 ns | 2.7695 ns | 2.8092 ns | 367,420,135.5 | 0.000 | Faster | 0.00 | 1 | No | 0.0019 | - | 24 B | 0.002 |
| NoReflection_V2_Get_Integer | Set_Integer | 3.0827 ns | 0.0984 ns | 0.2902 ns | 0.0290 ns | 3.0070 ns | 2.7975 ns | 2.9216 ns | 3.1258 ns | 4.2512 ns | 324,387,748.7 | 0.000 | Faster | 0.00 | 2 | No | 0.0019 | - | 24 B | 0.002 |
| NoReflection_V3_Get_Integer | Set_Integer | 3.9375 ns | 0.3712 ns | 1.0945 ns | 0.1095 ns | 3.5521 ns | 2.8889 ns | 3.2500 ns | 4.1203 ns | 8.0053 ns | 253,965,374.5 | 0.000 | Faster | 0.00 | 3 | No | 0.0019 | - | 24 B | 0.002 |
| Reflection_With_Cache_Get_Integer | Set_Integer | 30.9542 ns | 2.6882 ns | 7.9263 ns | 0.7926 ns | 28.5827 ns | 18.2969 ns | 23.8744 ns | 38.9046 ns | 47.9196 ns | 32,305,785.4 | 0.000 | Faster | 0.00 | 4 | No | 0.0019 | - | 24 B | 0.002 |
| Reflection_Without_Cache_Get_Integer | Set_Integer | 142,474.0798 ns | 6,921.4765 ns | 20,408.1310 ns | 2,040.8131 ns | 133,723.9502 ns | 123,583.1543 ns | 128,822.6746 ns | 150,420.3979 ns | 228,735.4248 ns | 7,018.8 | 1.017 | Baseline | 0.19 | 5 | Yes | 0.7324 | 0.4883 | 9869 B | 1.000 |
| NoReflection_V1_Get_String | Set_String | 0.2627 ns | 0.0649 ns | 0.1914 ns | 0.0191 ns | 0.2061 ns | 0.0540 ns | 0.1455 ns | 0.3112 ns | 1.1851 ns | 3,805,982,355.8 | 0.000 | Faster | 0.00 | 1 | No | - | - | - | 0.00 |
| NoReflection_V3_Get_String | Set_String | 0.4023 ns | 0.0363 ns | 0.1041 ns | 0.0107 ns | 0.4101 ns | 0.2508 ns | 0.3003 ns | 0.4764 ns | 0.8205 ns | 2,485,524,201.2 | 0.000 | Faster | 0.00 | 2 | No | - | - | - | 0.00 |
| NoReflection_V2_Get_String | Set_String | 0.4799 ns | 0.0348 ns | 0.0965 ns | 0.0102 ns | 0.4739 ns | 0.3357 ns | 0.3822 ns | 0.5736 ns | 0.6416 ns | 2,083,978,900.8 | 0.000 | Faster | 0.00 | 3 | No | - | - | - | 0.00 |
| Reflection_With_Cache_Get_String | Set_String | 18.1842 ns | 0.5745 ns | 1.6938 ns | 0.1694 ns | 17.8831 ns | 15.4772 ns | 17.0659 ns | 18.6517 ns | 24.9986 ns | 54,992,887.4 | 0.000 | Faster | 0.00 | 4 | No | - | - | - | 0.00 |
| Reflection_Without_Cache_Get_String | Set_String | 142,514.6326 ns | 14,749.9085 ns | 43,490.4413 ns | 4,349.0441 ns | 126,482.3364 ns | 108,507.4951 ns | 121,651.1719 ns | 137,077.9968 ns | 343,677.6611 ns | 7,016.8 | 1.057 | Baseline | 0.38 | 5 | Yes | 0.7324 | 0.4883 | 9845 B | 1.00 |
This is one of my best performance improvements I have ever done. This might not be significant in many places but for situations like mine, this saves a lot of time during run time.
Note: I tried to use this logic in System.Text.Json but couldn’t beat it though it was using reflection. It was highly optimized and I gave up.