Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[SR-6980] Swift 4.1 new warning "Cannot override with a stored property" #49528

Closed
swift-ci opened this issue Feb 11, 2018 · 10 comments
Closed
Labels
bug A deviation from expected or documented behavior. Also: expected but undesirable behavior.

Comments

@swift-ci
Copy link
Collaborator

Previous ID SR-6980
Radar rdar://problem/37429467
Original Reporter jeffjohnson (JIRA User)
Type Bug
Status Resolved
Resolution Won't Do

Attachment: Download

Environment

The warning occurs with Xcode 9.3 beta 1 and 2. It did not occur with Xcode 9.2 and earlier.

Additional Detail from JIRA
Votes 0
Component/s
Labels Bug
Assignee None
Priority Medium

md5: d709d11470f2fb2d511d81ea9c0829d8

relates to:

  • SR-6165 Overriding computed property with stored one is not allowed unless it is lazy

Issue Description:

I'm getting a new build warning "Cannot override with a stored property" with Swift 4.1. The warning did not occur with Swift 4.0. See attached screenshots. This is from the open source project Bonjeff.

![](Underpass download 1.png)

![](Underpass download 2.png)

@jckarter
Copy link
Member

@swift-ci create

@belkadan
Copy link
Contributor

This is correct behavior, unfortunately. Previous versions of Swift mistakenly allowed you to override using a stored property as long as that stored property was lazy. The rule is supposed to be that stored properties cannot be used to override at all, because it makes observing accessors ambiguous. (Are they wrapping the new storage, or the superclass's implementation?)

The intended workaround is to make a new property and forward to that one from the override.

We're not inherently against allowing stored properties to be overrides, lazy or otherwise. But it's something that would have to go through the Swift Evolution Process.

@swift-ci
Copy link
Collaborator Author

Comment by Jeff Johnson (JIRA)

For the record, I'm trying to do something like this:

protocol MyProtocol {
    var foo:String { get }
    func doSomething()
}

class BaseClass:MyProtocol {
    var foo:String { fatalError() }
    func doSomething() {
        print("Do Something")
    }
}

class SubClass:BaseClass {
    override lazy var foo:String = "Something lazy"
}

There's a dummy property in the base class for protocol conformance that must be overridden by subclasses.

@jckarter
Copy link
Member

From my recollection of history, our prohibition against overriding with stored properties predated our adding the required override keyword. Now that overriding is explicit it's less likely someone would do this by accident, so it's worth reconsidering the rule.

@belkadan
Copy link
Contributor

That's true, but again, we haven't solved the observing accessor problem:

class Sub: Base {
  override var foo: String {
    didSet { print(oldValue) }
  }
}

Does this allocate new storage, or wrap the parent's storage?

@swift-ci
Copy link
Collaborator Author

Comment by Jeff Johnson (JIRA)

This is interesting because in my project base class I'm actually doing something more like

lazy var foo:String = { fatalError() }()

According to the documentation, "You can add property observers to any stored properties you define, except for lazy stored properties."

I'm confused about overriding though. Are you supposed to be able to add a property observer to a lazy stored property in an override, and if so, why can't the observer be added otherwise? It appears I can add an observer in the subclass for the lazy var with

override var foo:String

@belkadan
Copy link
Contributor

Hm, I don't remember why lazy properties have a restriction on observers. The issue is more that there's a general rule about stored properties as overrides, and lazy properties are still supposed to act like stored properties and not get special privileges.

@jckarter
Copy link
Member

I don't think we ever intentionally prevented or enabled it. Since lazy properties are largely implemented by just expanding to a computed property under the hood, the prohibition on observers is likely to just be an accident of that.

@swift-ci
Copy link
Collaborator Author

Comment by Jeff Johnson (JIRA)

If the reason you can't override a stored property is ambiguous property observers, and lazy stored properties are not allowed to have property observers, then my argument is that you should be allowed to override a lazy stored property.

Currently there is a strange situation where you are not allowed to add property observers to a lazy stored property directly, but you are able to add property observers to a lazy stored property in an override. That may be another bug?

Whichever way you go with property observers, the current situation seems very inconsistent.

@jckarter
Copy link
Member

I filed a couple of follow-up bugs for the issues you raised:

https://bugs.swift.org/browse/SR-7082
https://bugs.swift.org/browse/SR-7083

@swift-ci swift-ci transferred this issue from apple/swift-issues Apr 25, 2022
This issue was closed.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug A deviation from expected or documented behavior. Also: expected but undesirable behavior.
Projects
None yet
Development

No branches or pull requests

3 participants