Interaction of 'first class spans' with inline array types/Extension methods over inline array types
Given several inline array types of
byte
of various lengths used to model certain fixed size buffers:
would it be possible, with the upcoming 'first class spans' (https://github.com/dotnet/csharplang/issues/8714), to write an extension method over Span<byte>
like such:
and then have that extension appear over all inline array types of byte
as such:
or is that not covered by that proposal? If not, can this (defining a single extension method for any inline array of a given primitive) be achieved in some other way?15 Replies
Unknown User•4w ago
Message Not Public
Sign In & Join Server To View
There is no way that I can think of that this would work
First class spans does not promote the inline array->span conversion to be part of the language
i thought the conversion already was a part of it?
Not in the same way
Not "first class"
I see. Does expressing this 'explicitly' like this work or would this be invalid/UB/unsafe?
I think that's fine? Not 100%, but if you're not getting ref safety warnings then it's probably ok
As long as
[UnscopedRef]
is present I'm not getting any errors/warnings. I got the idea from a TerraFX snippet:
https://discord.com/channels/143867839282020352/312132327348240384/1167843268231430154
But I have to admit I'm nowhere near familiar enough with how this all really works to tell at a glance.One general bit of feedback is that you're really not following any C# naming guidelines here
Right. Apologies for the poor legibility. I happen to share this project with some Rust expats and we had one too many discussion about naming...
And thanks for the pointers.
Unscoped ref here basically means, from a rust perspective, that you're returning something with the same lifetime as the thing you called it on
IE,
fn as_span<'a>(byteArray: &'a mut ByteArray20) -> &'a mut [byte] {}
(assuming I remember my rust syntax right)And the opposite (scoped?) would only have a lifetime of the actual
as_span
method call, meaning I can't return that ref because it would escape the method?Right. The only valid things to return from there are
&'static
stuff
The default (not UnscopedRef
) isn't really the "opposite"
It's more fn as_span<'a>(byteArray: &'a mut ByteArray20) -> &'static mut [byte] {}
I see. In the above example the unscoped ref is valid during
test()
and stops being valid thereafter?Yep, just like in rust
It's best to think of C# lifetime tracking as just rust lifetimes, with defaults implied for you
Right. I see. I'm personally not familiar with Rust, but I do like that I can now explain it to my collaborators as well in their terms- thank you very much for clarifying