Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

perf: Add a zero-allocation version of the API #11

Merged
merged 1 commit into from
Sep 3, 2024

Conversation

atifaziz
Copy link
Contributor

@atifaziz atifaziz commented Sep 1, 2024

This is a follow-up to PR #8

Incidentally, do you care to also add this? This way, the allocation of string becomes the entire responsibility of the caller, but it will require a modest expansion to the public API. Let me know if you're interested and I can propose something for prosperity, when I am bored next.

I'm interested.

This PR renames Utf8String to Chars, makes it (mostly) public, and adds the following new zero-allocation APIs:

public static void Generate(MonikerStyle monikerStyle, out Chars adjective, out Chars noun) { /* … */ }
public static void GenerateMoniker(out Chars adjective, out Chars noun) { /* … */ }
public static void GenerateMoby(out Chars adjective, out Chars noun) { /* … */ }

Unfortunately, since generic value tuples cannot carry Chars, one cannot simply return (Chars, Chars) or (Chars Adjective, Chars Noun) so out parameters are used instead. The other way to solve this would be to introduce a CharsPair type, but that would just add more code to maintain and test, and bring marginal benefits (though it can always be done later too).

Utf8String is renamed to Chars to encapsulate how data is stored internally. It has methods that permit writing into char and UTF-8 byte buffers for those who care to avoid an allocation; for those who don't care can simply call ToString().

The benchmarks are updated and show roughly a 5x performance increase and zero allocations with the new members:

Method Mean Error StdDev Median Gen0 Allocated
GenerateMoby 58.53 ns 0.783 ns 0.694 ns 58.51 ns 0.0043 55 B
GenerateMoniker 59.96 ns 1.762 ns 5.166 ns 57.31 ns 0.0042 53 B
GenerateMobyPair 11.84 ns 0.221 ns 0.246 ns 11.85 ns - -
GenerateMonikerPair 12.44 ns 0.271 ns 0.535 ns 12.22 ns - -

  • BenchmarkDotNet v0.14.0, Windows 11 (10.0.22631.4037/23H2/2023Update/SunValley3)
  • 13th Gen Intel Core i7-1370P, 1 CPU, 20 logical and 14 physical cores
  • .NET SDK 8.0.400
    • [Host] : .NET 8.0.8 (8.0.824.36612), X64 RyuJIT AVX2
    • DefaultJob : .NET 8.0.8 (8.0.824.36612), X64 RyuJIT AVX2

@alexmg alexmg changed the title Add a zero-allocation version of the API perf: Add a zero-allocation version of the API Sep 3, 2024
@codecov-commenter
Copy link

Welcome to Codecov 🎉

Once you merge this PR into your default branch, you're all set! Codecov will compare coverage reports and display results in all future pull requests.

Thanks for integrating Codecov - We've got you covered ☂️

@alexmg alexmg merged commit d3d5dc6 into alexmg:develop Sep 3, 2024
2 checks passed
@alexmg
Copy link
Owner

alexmg commented Sep 3, 2024

Thanks for the additional contribution @atifaziz! 👍

@atifaziz atifaziz deleted the zero-alloc-api branch September 3, 2024 13:01
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants