Skip to main content

Deep Dive into SearchValues<T> in .NET 8: When to Use and When to Avoid

Developer shares real benchmark results after using SearchValues<T>, revealing stark performance differences between Static setup and recreation on every call.

AI-written
Inewgen
26 Jul 2026Source: Dev.to3 min read (0 views)Last updated 20 Sep 2026
Share
Deep Dive into SearchValues<T> in .NET 8: When to Use and When to Avoid

Stock photo for illustration only, not from the actual event

Font size
  • SearchValues introduced in .NET 8 stores a set of constants for searching and the runtime selects the fastest strategy.
  • Benchmark results for dense delimiters show almost no difference from the traditional IndexOfAny, but sparse matches are about 1.7 times faster.
  • Creating SearchValues inside a method per call is nearly 3 times slower than storing it in a static readonly.

Many often view the new tool SearchValues<T> added in .NET 8 as a cheat code that makes string scanning up to five times faster, tempting an immediate refactoring of existing code. But for developers maintaining log management systems that primarily rely on IndexOfAny, performance testing before diving in is the first priority.

From comparative testing in cases where the log buffer has a frequency delimiter densely packed every 60 characters, the results are quite surprising as there is very little difference between the traditional method and the new tool:

9.7 msSearchValues<char>
10.2 msIndexOfAny(char[])
19.4 msmanual char loop

The reason for this is that the IndexOfAny method on modern .NET with small character sets is already well-vectorized. On the other hand, writing a manual check loop the traditional way turns out to be twice as slow as other methods, reflecting that the real performance bottleneck usually comes from the custom loops we write ourselves rather than the standard API.

However, the situation changes when modifying the data pattern to have rarer delimiters, averaging once every 40 kilobytes, which is a simulation case for anomaly scanning. The test results clearly show a difference:

  • IndexOfAny(char[]): Takes 5.6 milliseconds (found 723 matches)
  • SearchValues<char>: Takes 3.3 milliseconds (found 723 matches)

In cases where the target hit rate is relatively low, SearchValues can perform at its full potential in sweeping across long spans of data with nothing in them using wider vectorized steps.

Never miss the latest news?

Subscribe to get news summaries by email - not often enough to be annoying.

โฆษณา

The concept behind SearchValues<T> is to shift the precomputation burden upfront so the runtime doesn't have to recalculate every time a search is performed. Understanding underlying architectural workings like vectorization allows developers to choose APIs that fit the data characteristics, whether dense or sparse patterns, significantly impacting overall application performance.

Another crucial point developers must be extremely careful about is the cost of object creation. If SearchValues is newly created inside a method every time it is called instead of being stored in a static readonly variable, test results with a million short lines of data paint a clear picture:

  • Static SearchValues: Takes 25.1 milliseconds
  • SearchValues per call: Takes 70.2 milliseconds

Creating a new object per single call drops performance by nearly three times, making it even slower than not using it at all. If not declared as a static variable, we are essentially writing code that slows down the system unnecessarily.

software developer debugging

Illustration from stock photo library, not an actual photo from the event

Source: Dev.to

Comments

Leave a Comment
0/2000

Found something wrong in this article? Report an issue with this article