Overload Resolution Priority in C# 13 — Fine-Tuning API Evolution for Library Authors
C# 13 introduces a highly specialized but impactful feature: OverloadResolutionPriorityAttribute
, which allows library authors to guide the compiler in selecting the preferred method overload — especially during API evolution.
This attribute enables you to:
- Add new, optimized overloads without breaking existing code
- Encourage usage of improved APIs on recompile
- Avoid overload ambiguity at compile time
Let’s walk through how this works, when to use it, and how to avoid introducing confusion.
Why Was This Needed?
When adding a new overload to a public API, especially one that overlaps in parameter shape, you risk:
- Ambiguous method calls at compile time
- Breaking source compatibility
- Preventing older consumers from upgrading
The goal: let old code keep working, but prefer the new overload on recompilation.
What’s New in C# 13?
C# 13 recognizes the OverloadResolutionPriorityAttribute
defined in System.Runtime.CompilerServices
.
using System.Runtime.CompilerServices;
public class MyApi
{
[OverloadResolutionPriority(1)]
public static void Log(string message)
=> Console.WriteLine($"[Legacy] {message}");
[OverloadResolutionPriority(10)]
public static void Log(string message, LogLevel level)
=> Console.WriteLine($"[{level}] {message}");
}
How It Works:
- The compiler prefers higher values of
OverloadResolutionPriority
- This affects compile-time overload resolution
- Runtime behavior remains unchanged
Example: API Evolution Without Breaking Changes
Before C# 13
Log("System started"); // Resolves to Log(string)
Adding Log(string, LogLevel)
might cause:
- Ambiguity
- Preferencing the old overload
With Overload Priority
[OverloadResolutionPriority(10)]
public static void Log(string message, LogLevel level) { ... }
[OverloadResolutionPriority(1)]
public static void Log(string message) { ... }
New code resolves to the newer overload
Old code continues to compile as before
All without breaking the public API
Use Cases
Scenario | Benefit |
---|---|
Evolving APIs in public libraries | Avoid breaking changes or ambiguous calls |
Introducing overloads with new defaults | Prefer new overloads on recompilation |
Adding high-performance variants | Promote optimized versions while preserving compatibility |
Controlling overload ambiguity | Explicitly specify resolution instead of relying on shape |
Best Practices & Cautions
Guideline | Why |
---|---|
Use sparingly | Can make overloads hard to reason about |
Document overload priority clearly | Future maintainers should know why a method is preferred |
Avoid massive priority jumps | Keep values simple (e.g., 1, 2, 3...) |
Combine with [EditorBrowsable] if needed |
Hide overloads from IntelliSense if legacy |
Learn More
Final Thoughts
The OverloadResolutionPriorityAttribute
is a precision tool for API maintainers. It brings you one step closer to stable, evolvable public libraries in C#, helping guide consumers toward better overloads — without introducing breakage or ambiguity.
Use it to modernize safely, upgrade painlessly, and fine-tune the behavior of your overload sets.
Written by: [Cristian Sifuentes] – .NET API Steward | Library Evolution Specialist | Clean Upgrade Advocate
Have you ever broken users by adding an overload? Let this be your future-proofing toolkit.
Top comments (0)