-
Notifications
You must be signed in to change notification settings - Fork 4.8k
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
Add System.Math.DivRem for ulong and other integers #42156
Comments
I wish we could rename |
Tagging subscribers to this area: @tannergooding, @pgovind, @jeffhandley |
It'd be neater to use a ValueTuple return and have |
I believe |
Using value tuple + public static (byte Quotient, byte Remainder) DivRem(byte left, byte right);
+ public static (sbyte Quotient, sbyte Remainder) DivRem(sbyte left, sbyte right);
+ public static (short Quotient, short Remainder) DivRem(short left, short right);
+ public static (ushort Quotient, ushort Remainder) DivRem(ushort left, ushort right);
+ public static (int Quotient, int Remainder) DivRem(int left, int right);
+ public static (uint Quotient, uint Remainder) DivRem(uint left, uint right);
+ public static (long Quotient, long Remainder) DivRem(long left, long right);
+ public static (ulong Quotient, ulong Remainder) DivRem(ulong left, ulong right);
+ public static (nint Quotient, nint Remainder) DivRem(nint left, nint right);
+ public static (nuint Quotient, nuint Remainder) DivRem(nuint left, nuint right); |
namespace System
{
public static partial class Math
{
public static (byte Quotient, byte Remainder) DivRem(byte left, byte right);
public static (sbyte Quotient, sbyte Remainder) DivRem(sbyte left, sbyte right);
public static (short Quotient, short Remainder) DivRem(short left, short right);
public static (ushort Quotient, ushort Remainder) DivRem(ushort left, ushort right);
public static (int Quotient, int Remainder) DivRem(int left, int right);
public static (uint Quotient, uint Remainder) DivRem(uint left, uint right);
public static (long Quotient, long Remainder) DivRem(long left, long right);
public static (ulong Quotient, ulong Remainder) DivRem(ulong left, ulong right);
public static (nint Quotient, nint Remainder) DivRem(nint left, nint right);
public static (nuint Quotient, nuint Remainder) DivRem(nuint left, nuint right);
}
} |
It may also be worth considering an analyzer that recommends moving from the out version to valuetuple version since it seems the new version will perform better. |
@tannergooding - I've updated my PR #37928, but we'll need to determine the appropriate naming (I simplistically appended a '2' to distinguish from the variant that returns a scalar). @echesakovMSFT suggested we add a flag in the HW intrinsics table so that we don't have to special-case the methods that return
For the |
The legacy APIs have the benefit that it can be used in if-cases and saves one line:
With tuple based it would not only be longer code but also more ugly:
|
@Symbai, actually you can do this using C# pattern matching: if (Math.DivRem(12, 2) is { Quotient: 6, Remainder: var remainder })
{
Console.WriteLine(remainder);
} |
Didn't know that 👀 |
Closing, this was resolved in #45074 |
Background and Motivation
Math.DivRem currently accepts only int32 and int64. When you are working with uint64, as of now it's easier to calculate division and remainder "by hand".
Which is not only surprising and slightly inconvenient, but it also may lead to suboptimal code if you are not aware of #5213
So for convenience I suggest adding DivRem for uint64 and since, these integers are not special, add for all other integer types while we are at it: uint32, [u]int16, [s]byte
Proposed API
Usage Examples
Personally I ran into it when tried to use the function while formatting bit address inside of really large address space:
However looking for duplicates, I noticed that ulongs are implemented already(just not exposed), so here is the usage example from the very this exact repo.
Risks
There might be confusion what is called due to implicit conversions(when a=b=short, result=int)
The text was updated successfully, but these errors were encountered: