<div dir="ltr">The problem here seems to be with using the default implementation provided. If you override `append` in ObservedArray, the compiler allows it. That seems 'safe' but odd at first. I wouldn't *want* to implement every mutating method, but that is the current solution. I haven't puzzled out the reasoning behind this myself.<div><br></div><div><br><div>``` swift<br><div>class ObservedArray<T> : ArrayLiteralConvertible {</div><div> var value: [T]</div><div> init(value: [T]) {</div><div> self.value = value</div><div> }</div><div> required init() {</div><div> self.value = []</div><div> }</div><div><br></div><div> required convenience init(arrayLiteral elements: T...) {</div><div> self.init(elements)</div><div> }</div><div><br></div><div>}</div><div><br></div><div>extension ObservedArray {</div><div> typealias Index = Int</div><div><br></div><div> var startIndex: Index {</div><div> return value.startIndex</div><div> }</div><div><br></div><div> var endIndex: Index {</div><div> return value.endIndex</div><div> }</div><div><br></div><div> subscript(position: Index) -> T {</div><div> return value[position]</div><div> }</div><div><br></div><div>}</div><div><br></div><div>extension ObservedArray : RangeReplaceableCollectionType {</div><div> typealias Generator = IndexingGenerator<[T]></div><div><br></div><div> func generate() -> Generator {</div><div> return value.generate()</div><div> }</div><div>}</div><div><br></div><div>extension ObservedArray {</div><div> func replaceRange<C : CollectionType where C.Generator.Element == Generator.Element>(subRange: Range<Index>, with newElements: C) {</div><div> value.replaceRange(subRange, with: newElements)</div><div> }</div><div><br></div><div> func append(newElement: T) { // <- adding this makes it work</div><div> value.append(newElement)</div><div> }</div><div>}</div><div><br></div><div>let array: ObservedArray<String> = []</div><div>array.append("1")</div><div><br></div><br>```</div><div><div><br></div><div><br></div><div><br></div></div></div></div><div class="gmail_extra"><br><div class="gmail_quote">On Sat, Apr 30, 2016 at 7:52 AM, James Froggatt via swift-evolution <span dir="ltr"><<a href="mailto:swift-evolution@swift.org" target="_blank">swift-evolution@swift.org</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">I don't believe this has been addressed, please correct me if I'm wrong.<br>
<br>
--My Situation--<br>
I've recently been working on an observable collection type. Because each stores ‘subscriptions’ to changes that occur, it made sense to me that this should be a reference type, so subscriptions can't be copied with the values themselves.<br>
<br>
I have made this class conform to RangeReplaceableCollectionType, providing it with all the standard collection functions. I do the following:<br>
<br>
let array: ObservedArray<String> = []<br>
array.append("1") //Error: Cannot use mutating member on immutable value: ‘array’ is a ‘let’ constant<br>
<br>
I have to make the reference immutable just to use my new collection type? This is a bit of a deal-breaker.<br>
<br>
--The Problem--<br>
Mutating methods allow ‘self’ to be reassigned, which is just another way to mutate a value type. However, reassigning ‘self’ has a special meaning to reference types, which is presumably the reason they are disallowed in classes.<br>
<br>
However, classes can conform to protocols with mutating methods, leading to the compiler disallowing calls to mutating methods for ‘let’ values of type ‘protocol<MutatingProtocol, AnyObject>’, which can be an annoyance in generic code. In addition, classes can inherit mutating methods from protocol extensions, leading to the behaviour I describe above.<br>
<br>
Is this intentional behaviour? Am I going about this in the wrong way? Or is this really an omission in the language?<br>
_______________________________________________<br>
swift-evolution mailing list<br>
<a href="mailto:swift-evolution@swift.org">swift-evolution@swift.org</a><br>
<a href="https://lists.swift.org/mailman/listinfo/swift-evolution" rel="noreferrer" target="_blank">https://lists.swift.org/mailman/listinfo/swift-evolution</a><br>
</blockquote></div><br></div>