Performance Improvements in .NET 10
51–60 of 98 posts
Re: Performance Improvements in .NET 10
#52Earlier quoted context omitted.
This hasn't been an issue for a long time because nobody uses the non-generic collections anymore. That doesn't help you with your reliance on type erasure though. If you're up for it you should give it another try. Your example of subclassing GenericType and GenericType may be supported with covariance and contravariance in generics [1]. It's probably not very well known among C# developers (vs. basic generics) but…
Yeah, I had a chance a few months back when I was the backup programmer in a game development hackathon and my team was developing with Unity which uses C#. It was fun. People talk about tradeoffs with GC, the worst one is that I've seen an occasional game that has a terrible GC pause, for instance Dome Keeper based on Godot which also runs in .NET. I used play a lot of PhyreEngine (also .NET) games on the Playstatio…
Re: Performance Improvements in .NET 10
#53If only they could fix the ecosystem's stability; I feel like anything written with C#'s staple packages becomes outdated considerably faster than any other options.
Yep. A breaking change that makes my code a gajillion times faster is still always just a dirty breaking change that I'll hate.
Re: Performance Improvements in .NET 10
#54This kinda stuff brings languages like C# and Java closer to Rust in performance, thinking like the "borrow checker" it understands the scope of some objects and puts them on the stack and avoids garbage collection and allocation overhead. It keeps the unsung benefit of garbage collection for "programming in the large" in which memory allocation is treated as a global concern independent of everything else instead of…
This is wishful thinking. It’s the same as other layers we have like auto-vectorization where you don’t know if it’s working without performance analysis. The complexity compounds and reasoning about performance gets harder because the interactions get more complex with abstractions like these. Also, the more I work with this stuff the more I think trying to avoid memory management is foolish. You end up having to th…
Reasoning about performance is hard as it is, given nondeterministic optimisations by the CPU. Furthermore, a program that's optimal for one implementation of an Aarch64 architecture can be far from optimal for a different implementation of the same architecture. Because of that, reasoning deeply about micro-optimisations can be counterproductive, as your analysis today could be outdated tomorrow (or on a different vendor's chip). Full low-level control is helpful when you have full knowledge of the exact environment, including hardware details, and may be harmful otherwise.
What is meant by "performance" is also subjective. Improving average performance and improving worst-case performance are not the same thing. Also, improving the performance of the most efficient program possible and improving the performance of the program you are likely to write given your budget aren't the same thing.
For example, it may be the case that using a low-level language would yield a faster program given virtually unlimited resources, yet a higher-level language with less deterministic optimisation would yield a faster program if you have a more limited budget. Put another way, it may be cheaper to get to 100% of the maximal possible performance in language A, but cheaper to get to 97% with language B. If you don't need more than 97%, language B is the "faster language" from your perspective, as the programs you can actually afford to write will be faster.
> Also, the more I work with this stuff the more I think trying to avoid memory management is foolish.
It's not about avoiding thinking about memory management but about finding good memory management algorithms for your target definition of "good". Tracing garbage collectors offer a set of very attractive algorithms that aren't always easy to match (when it comes to throughput, at least, and in some situations even latency) and offer a knowb that allows you to trade footprint for speed. More manual memory management, as well as refcounting collectors often tend to miss the sweet spot, as they have a tendency for optimising for footprint over throughput. See this great talk about the RAM/CPU tradeoff - https://youtu.be/mLNFVNXbw7I from this year's ISMM (International Symposium on Memory Management); it focuses on tracing collectors, but the point applies to all memory management solutions.
> Should have noted that Zig solves this by making the convention be to pass an allocator in to any function that allocates. So the boundaries/responsibilities become very clear.
Yes, and arenas may give such usage patterns a similar CPU/RAM knob to tracing collectors, but this level of control isn't free. In the end you have to ask yourself if what you're gaining is worth the added effort.
Re: Performance Improvements in .NET 10
#55Earlier quoted context omitted.
lol, whut? Microsoft created the ".NET Standard" for this. Literally anything that targets .NET Standard 1.0 should work from circa 2001 through modern day 2025. You still get the (perf) benefits up the runtime upgrade which is what the blog post is about.
.NET Standard is more for maintaining interoperability between .NET Framework and .NET (Core). At this point only (very) legacy applications should be on Framework. Everything else isn't, so they shouldn't use. NET Standard as a target because it limits the new features they can use.
Re: Performance Improvements in .NET 10
#56If only they could fix the ecosystem's stability; I feel like anything written with C#'s staple packages becomes outdated considerably faster than any other options.
Re: Performance Improvements in .NET 10
#57Earlier quoted context omitted.
In my company running maybe 20K servers on .NET, we get a 10-20% CPU decrease every time we upgrade to the next major.
That's impressive, considering a major release is sniped every year. I've never thought it would be that much of an improvement outside of synthetic benchmarks.
Re: Performance Improvements in .NET 10
#58Earlier quoted context omitted.
Yep. A breaking change that makes my code a gajillion times faster is still always just a dirty breaking change that I'll hate.
The breaking changes are very well documented and are esoteric in nature. https://learn.microsoft.com/en-us/dotnet/core/compatibility/... Scott Hanselman has a very short blog on how 20 year old code is upgraded to the latest .NET in just a few short minutes: https://www.hanselman.com/blog/upgrading-a-20-year-old-unive...
Re: Performance Improvements in .NET 10
#59Earlier quoted context omitted.
> thinking like the "borrow checker" it understands the scope of some objects and puts them on the stack and avoids garbage collection and allocation overhead. On the other side however if you don't write code that the borrow checker would accept you likely won't get these optimizations. And even if it was accepted there's a chance the analysis needs to be too deep or complex for the escape analysis to work. Ultimate…
The counter to that is that is that performance really matters in inner loops and in those cases the hot area is not that big, it doesn’t matter if your setup and tear down give up a lot of possible performance. Early this year my son was playing chess which motivated me to write a chess program. I wrote one in Python really quickly that could challenge him. I was thinking of writing one I could bring to the chess cl…
Re: Performance Improvements in .NET 10
#60This reads like one of those recipe blogs where you first need to hear about great grandpappy's migration during the potato famine before you can get to the details on how to make cupcakes. First 5 paragraphs are just noise.
These posts are among the very best, digging into details explaining why things work and why changes were made.
Every time they get released I'm happy because no one killed it...