Bump on AnySequence / AnyCollection conversion

Continuing the discussion from [SR-119] AnySequence --> Any*Collection promotion:

I'm working on something involving AnySequence. I saw AnyCollection and its bi-directional and random-access counterparts while reading Apple's docs. I noticed that the collection versions can all cross convert (unconditionally when going towards a base, fail-able when going away from a base), but the conversion set doesn't include AnySequence. Any reason why? In the past few years since the older post, has any new Swift features changed the landscape? Does ABI stability mess anything up?

I already added a vote to the existing bug (SR-119).

Just that nobody's implemented it. I don't think there are ABI blockers to it.

That said, my personal opinion is it isn't worth it, because the AnySequence family aren't something we should be investing more time in. They are irretrievably inefficient and as a general goal best avoided in favor of various other solutions.

What solutions are you thinking about? My prototype code returns an Array of sequences. And an Element can be one of two types. Iā€™d prefer to hide the differences with AnySequence instead of a custom two-state enum Sequence.

instead of a custom two-state enum Sequence.

You mean a custom Sequence like this one?

Why do you want to hide this critical information from the compiler? Why is hiding this information, even from the user, a goal?

This is exactly a case where using AnySequence would be catastrophic for performance. You are taking a key bit of information ā€“ that there are only two possibilities, that can be dispatched to with a simple branch ā€“ and hiding it behind an abstraction that has to account for infinite possible element types of any shape and size at any point in the collection hierarchy, and which allocates memory for every element in all but the most trivial of circumstances (including allocating metadata, which is immortal and therefore essentially a dirty memory leak).

If we expect people to use enums instead, I think we need to do a lot of language work to make that option as ergonomic as AnySequence. It would take a fair bit of boilerplate to manually write even a simple two-case wrapper enum.

In theory at least, the optimizer ought to be able to do a better job of cleaning up the abstraction in these types as well, since it would not generally be semantics-breaking for it to replace an AnyCollection return value with a single underlying type with a return value of that underlying type, or with a compiler-generated sum type of the finite set of underlying types.

1 Like

Yeah, that's why I think Either: Sequence where Left: Sequence, Right: Sequence might be an OK alternative in the short term.