Why conditional conformance to AnyObject in protocol extenstion is not equal to conformance to AnyObject in protocol?

Hello!
I have a protocol in which there is a mutable variable. When I conform the protocol to AnyObject, then I can write a function that changes this variable without "mutating" keyword.

protocol Foo: AnyObject {
    var value: Int { get set }
}
extension Foo {
    func change() {
        value = 1
    }
}

However, when I make an extension with conditional conformance to AnyObject, code is not compile anymore.

protocol Foo {
    var value: Int { get set }
}
extension Foo where Self: AnyObject {
    func change() {
        value = 1 // Error: Cannot assign to property: 'self' is immutable
    }
}

If "mutating" is added to the function declaration, then it compiles. But this is a class, and inside the function "change" internal state is changing, not self.
What am I doing wrong?

1 Like

Hmm, it looks like a variant of SR-11298. I can’t think of a scenario where this would be problematic, because we know Self is a class type.

In the meantime, instead of adding mutating, you can do this:

func change() {
  var _self = self
  _self.value = 1
}

It would also mean you can keep the instance immutable.

1 Like

I think you can declare your property as

var value: Int { get nonmutating set }

But then all conformance of Foo must have nonmutating setters. (You can also declare a mutating getter)