Quality-of-life: Treat Count and Length as true synonyms? #63078
Replies: 2 comments 4 replies
-
The reason should be not duplicating api with only name difference.
Probably not. In .NET, source compatibility between different types is not useful, as you can't share source code.
It "solves" the source-level view, but makes the behinds horrible. The historical debt of collection interfaces is quite heavy. Adding a partial solution can make things more messed up. There are type system changes proposed with next versions of C#. The unification should be discussed with the updated type system. |
Beta Was this translation helpful? Give feedback.
-
I hate |
Beta Was this translation helpful? Give feedback.
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
-
Here's a minor pain that happened to me today:
ruleorder against ever mutating an Array in-place. So far, so good.ReadOnlyCollection<T>
, with the caveat thatReadOnlyCollection<T>
is not actually immutable, but there's a new team-wide rule against ever usingReadOnlyCollection<T>
as a wrapper over a live mutating collection. That works.IReadOnlyCollection<T>
andIReadOnlyList<T>
interfaces, which allow almost any collection to be exposed to other components in a software system without fear of those components mutating the data contained within, as well as avoiding the computational cost of copying collections everywhere (assuming you're careful not to pass a live and mutating collection via a read-only interface. Oh, and they support variance too (wow!)IList<T>
does not extendIReadOnlyList<T>
, andIDictionary<K,V>
does not extendIReadOnlyDictionary<K.V>
- but that can be worked-around.System.Collections.Immutable
is the new hotness; the great thing with these collection-types is you don't need to be content with hoping that consumers ofIReadOnlyList<T>
won't try to mutate it themselves by casting to a known mutable collection type - but you also get hard guarantees that the collection won't be live and mutated unexpectedly. This means: another refactoring opportunity to replace all of thoseIReadOnlyList<T>
andIReadOnlyCollection<T>
interface types used for public parameters, properties, and return-types can now be typed with asImmutableArray<T>
!\bIReadOnlyList\b<
with\bImmutableArray\b<
) don't go quite as smoothly as expected because, annoyingly,ImmutableArray<T>
uses.Length
instead of.Count
for its size property. Even though until this point all other collection-types have settled on.Count
, not.Length
. Aieeeeee..Count
references with.Length
property accessors.Why was this necessary?
The
ImmutableArray<T>
type already implementsICollection<T>
so it already has a.Count
property, but as it's an explicit interface implementation it's only exposed when you use an interface reference.I understand wanting
ImmutableArray<T>
to be largely a drop-in replacement forT[]
, so having a public.Length
property does make sense. I'm fine with that. This is the reason given in the introductory blog post:Of course, I take umbrage with the "This makes it easier to port existing code." part: because it actually made my task to porting existing code harder, not easier).
But what justification was there for not making
.Count
public too? I appreciate that identically-behaving members do cause confusion, but .NET has had attributes to hide potentially-confusing types and members:EditorBrowsableAttribute
and (if you're feeling particularly nasty:DebuggerBrowsableAttribute
).The main reason it's so frustrating is because it's a wart that breaks conceptual isomorphisms about collections for absolutely no good reason (at least as far as category-theory is concerned). The semantics of
.Count
and.Length
for immutable collections are identical, and given the C# compiler isn't yet smart enough to identify isomorphisms, at least the library designers could paper-over it by exposing.Count
.The point:
.Count
withEditorBrowsable
?.Count
be exposed to allow for source-level compatibility between all the different Collection types?ImmutableArray<T>.Count
be rewritten to.Length
transparently?Beta Was this translation helpful? Give feedback.
All reactions