4 ms·
> Adding a new method is a breaking change, for example, because I could have written a method with that name previously. Then you should have used a way to na
by euyyn 11y ago
> Adding a new method is a breaking change, for example, because I could have written a method with that name previously.
Then you should have used a way to namespace your method, as is done in Objective-C with category methods.
- steveklabnik 11y agoWe have a module system, but that doesn't help. You can still define methods on arbitrary types, subject to the coherence rules. You can still write out a disambiguated form to distinguish the two, but it's not the default way. That's one of the reasons why adding a defaulted method to a trait is a minor change. See https://github.com/rust-lang/rfcs/blob/master/text/1105-api-evolution.md#minor-change-adding-a-defaulted-item https://github.com/rust-lang/rfcs/blob/master/text/1105-api-... for more.
- pcwalton 11y ago> Then you should have used a way to namespace your method, as is done in Objective-C with category methods. Categories do nothing to protect against breakage due to adding methods.
- tatterdemalion 11y agoAll methods are namespaced but there is sugar which can cause a conflict because it searches the namespaces in scope for methods. Imagine the trait (namespace) `Baz` defines a method `bar()`, and `Foo` is a type which implements `Baz`. `foo.bar()` is sugar for `<Foo as Baz>::bar(foo)`. Imagine `Foo` also implements `Quux`, another trait in scope, and `Quux` is extended to also define `bar()`. Now `foo.bar()` is ambiguous, because it could also mean `<Foo as Quux>::bar(foo)`. As you can imagine, though, this happens very rarely. You can't avoid a conflict unless you require specifying the namespace at every call-site, which is in my estimation a much greater burden than editing your code to use the explicit namespace form if a conflict arises because of a new method in a dependency.