1
StartsWith with StringComparison.OrdinalIgnoreCase versus ToUpper on .NET 8
Date Added (UTC):
08 Apr 2024 @ 01:08
Date Updated (UTC):08 Apr 2024 @ 01:08
.NET Version(s): Tag(s):
Added By:
.NET Developer and tech lead from Ireland!
Benchmark Results:
Benchmark Code:
using BenchmarkDotNet.Attributes;
using BenchmarkDotNet.Columns;
using BenchmarkDotNet.Configs;
using BenchmarkDotNet.Environments;
using BenchmarkDotNet.Jobs;
using BenchmarkDotNet.Reports;
using System;
[MemoryDiagnoser]
[Config(typeof(Config))]
[HideColumns("Error", "StdDev", "Median", "RatioSD")]
public class StartsWithOrdinalIgnoreCase
{
private readonly string _input = "https://dot.net";
[Benchmark(Baseline = true)]
public bool IsHttps_ToUpper() => _input.ToUpperInvariant().StartsWith("HTTPS://");
[Benchmark]
public bool IsHttps_StringComparison() => _input.StartsWith("HTTPS://", StringComparison.OrdinalIgnoreCase);
private class Config : ManualConfig
{
public Config()
{
AddJob(Job.Default.WithId(".NET 8").WithRuntime(CoreRuntime.Core80));
SummaryStyle =
SummaryStyle.Default.WithRatioStyle(RatioStyle.Percentage);
}
}
}
Powered by SharpLab
// .NET 8
public bool IsHttps_ToUpper()
{
return _input.ToUpperInvariant().StartsWith("HTTPS://");
}
// .NET 8
public bool IsHttps_StringComparison()
{
return _input.StartsWith("HTTPS://", StringComparison.OrdinalIgnoreCase);
}
Powered by SharpLab
// .NET 8
.method public hidebysig
instance bool IsHttps_ToUpper () cil managed
{
.custom instance void [BenchmarkDotNet.Annotations]BenchmarkDotNet.Attributes.BenchmarkAttribute::.ctor(int32, string) = (
01 00 1b 00 00 00 01 5f 01 00 54 02 08 42 61 73
65 6c 69 6e 65 01
)
// Method begins at RVA 0x2050
// Code size 22 (0x16)
.maxstack 8
// sequence point: (line 28, col 38) to (line 28, col 86) in _
IL_0000: ldarg.0
IL_0001: ldfld string StartsWithOrdinalIgnoreCase::_input
IL_0006: callvirt instance string [System.Runtime]System.String::ToUpperInvariant()
IL_000b: ldstr "HTTPS://"
IL_0010: callvirt instance bool [System.Runtime]System.String::StartsWith(string)
IL_0015: ret
}
// .NET 8
.method public hidebysig
instance bool IsHttps_StringComparison () cil managed
{
.custom instance void [BenchmarkDotNet.Annotations]BenchmarkDotNet.Attributes.BenchmarkAttribute::.ctor(int32, string) = (
01 00 1e 00 00 00 01 5f 00 00
)
// Method begins at RVA 0x2067
// Code size 18 (0x12)
.maxstack 8
// sequence point: (line 31, col 47) to (line 31, col 112) in _
IL_0000: ldarg.0
IL_0001: ldfld string StartsWithOrdinalIgnoreCase::_input
IL_0006: ldstr "HTTPS://"
IL_000b: ldc.i4.5
IL_000c: callvirt instance bool [System.Runtime]System.String::StartsWith(string, valuetype [System.Runtime]System.StringComparison)
IL_0011: ret
}
Powered by SharpLab
|
|
Benchmark Description:
The provided benchmark code is designed to measure and compare the performance of two different methods for checking if a given string starts with a specific prefix in a case-insensitive manner. This benchmark is set up using BenchmarkDotNet, a powerful .NET library for benchmarking code performance. The benchmark is configured to run on .NET 8, as indicated by the configuration setup within the `Config` class. This specific version of .NET is chosen to ensure the benchmarks are run on a consistent and modern runtime environment, which helps in obtaining relevant and up-to-date performance insights.
### General Setup
- **.NET Version**: The benchmark specifies the use of .NET 8 (`CoreRuntime.Core80`), ensuring that the tests are run on a specific and modern version of the .NET runtime.
- **BenchmarkDotNet Configuration**: The configuration class `Config` extends `ManualConfig` from BenchmarkDotNet, allowing customization of the benchmarking environment. It specifies the use of `.NET 8` runtime and customizes the summary style to display ratio percentages.
- **Memory Diagnoser**: The `[MemoryDiagnoser]` attribute is used to diagnose memory usage, providing insights into the allocations made by each benchmark method.
- **Column Hiding**: The `[HideColumns]` attribute is used to simplify the output by hiding specific columns like Error, StdDev (Standard Deviation), Median, and RatioSD (Ratio Standard Deviation).
### Benchmark Methods
#### 1. `IsHttps_ToUpper()`
- **Purpose**: This method checks if the `_input` string starts with "HTTPS://" by first converting the entire `_input` string to uppercase using `ToUpperInvariant()` and then using `StartsWith("HTTPS://")` to perform the comparison.
- **Performance Aspect**: This benchmark is designed to measure the performance implications of converting an entire string to uppercase as a means to perform a case-insensitive comparison. It tests both the computational overhead of the `ToUpperInvariant()` method and the subsequent `StartsWith` operation.
- **Expected Insights**: Running this benchmark will help understand the cost (in terms of execution time and memory allocations) associated with string manipulation through case conversion before performing a comparison. It is generally expected to be less efficient due to the additional string allocation and processing involved in the `ToUpperInvariant()` call.
#### 2. `IsHttps_StringComparison()`
- **Purpose**: This method directly checks if the `_input` string starts with "HTTPS://" in a case-insensitive manner by using the `StartsWith` method with `StringComparison.OrdinalIgnoreCase` as a parameter.
- **Performance Aspect**: The benchmark aims to measure the efficiency of performing a case-insensitive comparison without modifying the original string. It specifically tests the performance of the `StartsWith` method when using the `StringComparison.OrdinalIgnoreCase` comparison option.
- **Expected Insights**: This method is expected to be more efficient than the `IsHttps_ToUpper()` method because it avoids the overhead of converting the `_input` string to uppercase. The direct use of `StringComparison.OrdinalIgnoreCase` allows for a more optimized comparison that doesn't require additional string allocations or transformations. The results should typically show lower execution times and fewer memory allocations compared to the `IsHttps_ToUpper()` method.
### Summary
By comparing these two methods, the benchmark aims to highlight the performance benefits of using more direct and optimized string comparison techniques (`IsHttps_StringComparison()`) over more manual and potentially less efficient approaches (`IsHttps_ToUpper()`). The insights gained can guide developers in choosing more performant string comparison strategies in their .NET applications, especially in scenarios where such comparisons are frequent or critical for performance.