Type cannot be converted to itself

Here's an innocuous-looking extension on Sequence:

extension Sequence {
  func removeNils<T>() -> [T]
  where Element == T? {
    self.compactMap(\T?.self)
  }
}

However, it doesn't even compile:

error: key path value type 'T?' cannot be converted to contextual type 'T?'

Why can I not convert this type to itself? This has to be the most baffling error message I've seen.

Yeah this is a known bug, it should ‘just work’ from the existing function conversion rules for keypath literals.

At the end of the thread I had a comment with a breadcrumb from when I looked into it—when we’re able to eagerly resolve the full path (since self is a special member and we know exactly what type it produces) we produce the actual keypath value directly rather than waiting until after we have a chance to do the function conversion.

2 Likes

Is this related to the code size issue I noticed last year (where \.self and { $0 } behave significantly differently)?

I wouldn’t expect those issues to be related beyond the fact that they both happen to involve the identity keypath. The issue in this thread has to do with the logic of how we type check keypath literals, the issue you’ve linked is gonna come down to the codegen that happens for keypath values.