Intersection types and Delegation

Hello everyone!

I have a class structure like this

interface A {
    fun foo1(callback: (a: Int)-> Unit)
}

class AImpl : A {
    override fun foo1(callback: (a: Int)-> Unit) { return }
    fun foo2(callback: (a: Int)-> Unit) { return }
}

class ADelegate(a : A) : A by a

class B {
    val a = ADelegate(AImpl())

    fun b1() {
        a.foo1 {
            a.runCatching { }.onFailure { return@foo1 }
        }
    }

    fun b2() {
        (a as AImpl).foo2 {
            a.runCatching { }.onFailure { return@foo2 }
        }
    }
}

And I want to be able to call foo2, however even though IDEA can infer that this inside the foo2 :: runCatching is ADelegate & AImpl when compiling it says that return is not allowed inside onFailure.

For foo1 there is no problem though.

Can anyone give me an insight about the problem?

This might be due to the new enhanced type inference, which is enabled in IDEA but not yet in the compiler. Or was it the other way around? If it is the other way around, you should file a bug report.

I have no clue, was there any release notice or something like that?

Yes there was. It is easily googleable.

The new type inference was introduced in this release:

I can confirm that enabling the new type inference in the compiler options will cause the compiler error to disappear.

As an aside, a as AImpl will fail, as ADelegate does not extend AImpl.

Shouldn’t the delegation allow for it though?

No, ADelegate is a subclass of A, but not AImpl.

1 Like