-
Notifications
You must be signed in to change notification settings - Fork 4.9k
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
[API Proposal]: Guid from int128 and Guid to int128 #73781
Comments
I couldn't figure out the best area label to add to this issue. If you have write-permissions please help me learn by adding exactly one area label. |
I don't think this is a good idea. |
@teo-tsirpanis : It has more to do with eliminating allocations than anything else. |
Yeah I imagine. You should reach out to the maintainers of the DBMS and its drivers. Maybe there could be a new API in ADO.NET but I don't know how it would look like. |
@teo-tsirpanis : You imagine badly. I am working on the logical equivalent of being the DBMS driver. |
Something you could do is write the It is more predictable with regards to endianness and avoids reinterpret casts. |
Tagging subscribers to this area: @dotnet/area-system-runtime Issue DetailsBackground and motivationWe have new type Int128 that is the same size as a Guid. I'd pretty much like to use it everywhere I have byte[16]; and just not allocate the arrays for dealing with Guid.
I'd really like the int128 values to exactly match the in-memory values of the bytes in the byte[16] array. Or put another way, the following (bad) way to write the constructor: API Proposalnamespace System.Collections.Generic;
public class MyFancyCollection<T> : IEnumerable<T>
{
public void Fancy(T item);
} API Usage// Fancy the value
var c = new MyFancyCollection<int>();
c.Fancy(42);
// Getting the values out
foreach (var v in c)
Console.WriteLine(v); Alternative DesignsWhile I did come up with an alternative design, it immortalizes the bad way of writing the constructor. An even worse idea is to to the endian bitbashing and reinterpret cast between guid and int128. RisksA lot less risky than reinterpret casts lying around.
|
Most RDBMSs have a GUID type, though. |
The byte order of a GUID is not clearly defined. See also #53354. |
While A valid "Guid" definition could be one of many ranging from a single Given the current layout, a "correct" conversion would likely be one that is equivalent to: Span<byte> tmp = stackalloc byte[16];
bool succeeded = guid.TryWriteBytes(tmp);
Debug.Assert(succeeded);
if (BitConverter.IsLittleEndian)
{
return BinaryPrimitives.ReadInt128LittleEndian(tmp);
}
else
{
return BinaryPrimitives.ReadInt128BigEndian(tmp);
} This is different from a simple "reinterpret-cast" which is much cheaper and just gives the raw bits exactly as is. Which of these two operations you want is likely entirely dependent on your own scenario. For the "reinterpret-cast" scenario, I wouldn't be opposed to a proposal that asks for For the "correctly convert the |
Background and motivation
We have new type Int128 that is the same size as a Guid. I'd pretty much like to use it everywhere I have byte[16]; and just not allocate the arrays for dealing with Guid.
I'd really like the int128 values to exactly match the in-memory values of the bytes in the byte[16] array.
Or put another way, the following (bad) way to write the constructor:
public Guid(int128 b) : this(new ReadOnlySpan<byte>((byte*)&b, 16)) {}
API Proposal
API Usage
Alternative Designs
While I did come up with an alternative design, it immortalizes the bad way of writing the constructor.
An even worse idea is to to the endian bitbashing and reinterpret cast between guid and int128.
Risks
A lot less risky than reinterpret casts lying around.
The text was updated successfully, but these errors were encountered: