Custom didSet methods

When declaring a collection, it would be nice to have a way of knowing when
an item is set/added and removed.

For example you could trigger a layer to be added to the layer hiearchy.

var shapeLayers: [CAShapeLayer] {

didAdd(item) {
addSubLayer(item)
}

willRemove(item){
item.removeFromSuperlayer()
}
}

···

--
 Wizard
james@supmenow.com
+44 7523 279 698

I don't know if this is a good idea. If you insert an item to an array,
what should happen? The items after the inserted item should be considered
as removed or not? They indexes are changed but the values not.

zhaoxin

···

On Tue, Jan 12, 2016 at 7:24 PM, James Campbell via swift-evolution < swift-evolution@swift.org> wrote:

When declaring a collection, it would be nice to have a way of knowing
when an item is set/added and removed.

For example you could trigger a layer to be added to the layer hiearchy.

var shapeLayers: [CAShapeLayer] {

didAdd(item) {
addSubLayer(item)
}

willRemove(item){
item.removeFromSuperlayer()
}
}

--
 Wizard
james@supmenow.com
+44 7523 279 698

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

--

Owen Zhao

Currently, didSet already gets called when a set property is mutated. The only difference I see in this proposal is that it lets you know more precisely what changed, so that you can more efficiently update the UI to reflect the change; i.e. if each item is represented by a view object, and you insert an object, the redraw only needs to occur for the view corresponding to the newly inserted item instead of having to recreate all the views.

Seems reasonable to me. KVO currently provides this facility in Objective-C.

Charles

···

On 2016-01-12 07:33, 肇鑫 via swift-evolution wrote:

I don't know if this is a good idea. If you insert an item to an
array, what should happen? The items after the inserted item should be
considered as removed or not? They indexes are changed but the values
not.

zhaoxin

On Tue, Jan 12, 2016 at 7:24 PM, James Campbell via swift-evolution > <swift-evolution@swift.org> wrote:

When declaring a collection, it would be nice to have a way of
knowing when an item is set/added and removed.

For example you could trigger a layer to be added to the layer
hiearchy.

var shapeLayers: [CAShapeLayer] {

didAdd(item) {
addSubLayer(item)
}

willRemove(item){
item.removeFromSuperlayer()
}

--

 Wizard

james@supmenow.com
+44 7523 279 698 [1]
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution [2]

--

Owen Zhao

Links:
------
[1] tel:%2B44%207523%20279%20698
[2] https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

What about did/willAdd for all collection types, did/willSetAtIndex for collection types with indexes, and
did/willSetAtIndexRange for collection types that support subscripting with ranges?

- Dave

···

On Jan 12, 2016, at 13:26, Charles Srstka via swift-evolution <swift-evolution@swift.org> wrote:

Currently, didSet already gets called when a set property is mutated. The only difference I see in this proposal is that it lets you know more precisely what changed, so that you can more efficiently update the UI to reflect the change; i.e. if each item is represented by a view object, and you insert an object, the redraw only needs to occur for the view corresponding to the newly inserted item instead of having to recreate all the views.

Seems reasonable to me. KVO currently provides this facility in Objective-C.

Charles

On 2016-01-12 07:33, 肇鑫 via swift-evolution wrote:
I don't know if this is a good idea. If you insert an item to an
array, what should happen? The items after the inserted item should be
considered as removed or not? They indexes are changed but the values
not.
zhaoxin
On Tue, Jan 12, 2016 at 7:24 PM, James Campbell via swift-evolution >> <swift-evolution@swift.org> wrote:

When declaring a collection, it would be nice to have a way of
knowing when an item is set/added and removed.
For example you could trigger a layer to be added to the layer
hiearchy.
var shapeLayers: [CAShapeLayer] {
didAdd(item) {
addSubLayer(item)
}
willRemove(item){
item.removeFromSuperlayer()
}
}
--
 Wizard
james@supmenow.com
+44 7523 279 698 [1]
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution [2]

--
Owen Zhao
Links:
------
[1] tel:%2B44%207523%20279%20698
[2] https://lists.swift.org/mailman/listinfo/swift-evolution
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

did/willSetAtIndex could be redundant, since that information could be equally well expressed with a range having a length of 1.

The other thing it's missing is a way to tell what kind of change it was. If something were inserted or removed such that the number of items in the collection were changed, you'd need to know about it to avoid having to redraw whatever view correspond to every single element in the collection coming after the index you've changed.

What KVO did was to offer an NSKeyValueSetMutationKind enum containing constants for insertion and removal as well as OR and AND operations with other sets. If you don't want to do that, another possible interface could be to provide two ranges, one representing the range of the affected region before the change, and another representing it afterward. If you had an empty range for "before" and a non-empty range for "after", that would represent an insertion. The reverse would be removal, and anything else would be a replacement of some kind.

Charles

···

On 2016-01-12 22:04, David Sweeris wrote:

What about did/willAdd for all collection types, did/willSetAtIndex
for collection types with indexes, and
did/willSetAtIndexRange for collection types that support subscripting
with ranges?

- Dave

On Jan 12, 2016, at 13:26, Charles Srstka via swift-evolution >> <swift-evolution@swift.org> wrote:

Currently, didSet already gets called when a set property is mutated. The only difference I see in this proposal is that it lets you know more precisely what changed, so that you can more efficiently update the UI to reflect the change; i.e. if each item is represented by a view object, and you insert an object, the redraw only needs to occur for the view corresponding to the newly inserted item instead of having to recreate all the views.

Seems reasonable to me. KVO currently provides this facility in Objective-C.

Charles

On 2016-01-12 07:33, 肇鑫 via swift-evolution wrote:
I don't know if this is a good idea. If you insert an item to an
array, what should happen? The items after the inserted item should be
considered as removed or not? They indexes are changed but the values
not.
zhaoxin
On Tue, Jan 12, 2016 at 7:24 PM, James Campbell via swift-evolution >>> <swift-evolution@swift.org> wrote:

When declaring a collection, it would be nice to have a way of
knowing when an item is set/added and removed.
For example you could trigger a layer to be added to the layer
hiearchy.
var shapeLayers: [CAShapeLayer] {
didAdd(item) {
addSubLayer(item)
}
willRemove(item){
item.removeFromSuperlayer()
}
--
 Wizard
james@supmenow.com
+44 7523 279 698 [1]
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution [2]

--
Owen Zhao
Links:
------
[1] tel:%2B44%207523%20279%20698
[2] https://lists.swift.org/mailman/listinfo/swift-evolution
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

did/willSetAtIndex could be redundant, since that information could be equally well expressed with a range having a length of 1.

Good point… Conceptually, I actually really like it. On the other hand, you could make the same argument about subscript, and the fact that the collection types implement separate functions for Index and Range<Index> makes me think there are good reasons to keep them separate (specifically I wonder about the performance implications for wrapping the common case of one Index in a Range<Index>).

The other thing it's missing is a way to tell what kind of change it was. If something were inserted or removed such that the number of items in the collection were changed, you’d need to know about it to avoid having to redraw whatever view correspond to every single element in the collection coming after the index you've changed.

What KVO did was to offer an NSKeyValueSetMutationKind enum containing constants for insertion and removal as well as OR and AND operations with other sets. If you don't want to do that, another possible interface could be to provide two ranges, one representing the range of the affected region before the change, and another representing it afterward. If you had an empty range for "before" and a non-empty range for "after", that would represent an insertion. The reverse would be removal, and anything else would be a replacement of some kind.

Charles

Also, good points. I guess my idea then is:
“did/willUpdate”, “did/willInsert”, and “did/willRemove” for when you don’t care about which element was changed (and for types that aren’t indexable anyway)
“did/willUpdateAtIndex”, “did/WillInsertAtIndex”, and “did/WillRemoveAtIndex” for single elements
“did/willUpdateInRange”, “did/WillInsertInRange”, and “did/WillRemoveInRange” for multiple elements

That’s a lot of new keywords, though… Oh! What if it was *only* did/willUpdate, did/willAdd, and did/willRemove, and they were overloaded with (), (atIndex: Index), and (inRange: Range<Index>) forms? Like this:
var foo: [Int] {
  didUpdate(atIndex: Int) {
    …
  }
  didInsert(inRange: Range<Int>) {
    …
  }
}

Actually, could the “inRange” cases be handled simply by having the runtime call the did/will function multiple times? How much of efficiency hit would it be to have multiple function calls, compared to one function call that iterates through a range?

I like the idea of supporting this kind of “extended” did/willSet functionality, but I don’t think there should be *language features* — stuff that gets its own keyword — that necessarily have lots of runtime overhead.

- Dave

···

On Jan 12, 2016, at 19:17, cocoadev@charlessoft.com wrote:

On 2016-01-12 22:04, David Sweeris wrote:

What about did/willAdd for all collection types, did/willSetAtIndex
for collection types with indexes, and
did/willSetAtIndexRange for collection types that support subscripting
with ranges?
- Dave

On Jan 12, 2016, at 13:26, Charles Srstka via swift-evolution <swift-evolution@swift.org> wrote:
Currently, didSet already gets called when a set property is mutated. The only difference I see in this proposal is that it lets you know more precisely what changed, so that you can more efficiently update the UI to reflect the change; i.e. if each item is represented by a view object, and you insert an object, the redraw only needs to occur for the view corresponding to the newly inserted item instead of having to recreate all the views.
Seems reasonable to me. KVO currently provides this facility in Objective-C.
Charles

On 2016-01-12 07:33, 肇鑫 via swift-evolution wrote:
I don't know if this is a good idea. If you insert an item to an
array, what should happen? The items after the inserted item should be
considered as removed or not? They indexes are changed but the values
not.
zhaoxin
On Tue, Jan 12, 2016 at 7:24 PM, James Campbell via swift-evolution >>>> <swift-evolution@swift.org> wrote:

When declaring a collection, it would be nice to have a way of
knowing when an item is set/added and removed.
For example you could trigger a layer to be added to the layer
hiearchy.
var shapeLayers: [CAShapeLayer] {
didAdd(item) {
addSubLayer(item)
}
willRemove(item){
item.removeFromSuperlayer()
}
}
--
 Wizard
james@supmenow.com
+44 7523 279 698 [1]
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution [2]

--
Owen Zhao
Links:
------
[1] tel:%2B44%207523%20279%20698
[2] https://lists.swift.org/mailman/listinfo/swift-evolution
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

Just a random comment on this thread: our desire is to introduce property behaviors, and “demote” things like property observers into library features. This is great because it makes it much easier to extend these capabilities without hacking on the compiler, and will allow you to define custom behaviors in your own code.

I don’t know if the first round of behaviors will actually allow us to eliminate willset/didset though, simply given that they need to poke at the super implementation. That said, we’d rather work towards fixing those problems: proposals to make the existing property observers richer aren’t likely to be accepted.

-Chris

···

On Jan 12, 2016, at 8:07 PM, Dave via swift-evolution <swift-evolution@swift.org> wrote:

What KVO did was to offer an NSKeyValueSetMutationKind enum containing constants for insertion and removal as well as OR and AND operations with other sets. If you don't want to do that, another possible interface could be to provide two ranges, one representing the range of the affected region before the change, and another representing it afterward. If you had an empty range for "before" and a non-empty range for "after", that would represent an insertion. The reverse would be removal, and anything else would be a replacement of some kind.

Charles

Also, good points. I guess my idea then is:
“did/willUpdate”, “did/willInsert”, and “did/willRemove” for when you don’t care about which element was changed (and for types that aren’t indexable anyway)
“did/willUpdateAtIndex”, “did/WillInsertAtIndex”, and “did/WillRemoveAtIndex” for single elements
“did/willUpdateInRange”, “did/WillInsertInRange”, and “did/WillRemoveInRange” for multiple elements

That’s a lot of new keywords, though… Oh! What if it was *only* did/willUpdate, did/willAdd, and did/willRemove, and they were overloaded with (), (atIndex: Index), and (inRange: Range<Index>) forms? Like this:

Is the proposal document for the property behaviors concept available online anywhere? I'm intrigued by it, and would like to read about the specifics.

Thanks,
Charles

···

On 2016-01-12 23:45, Chris Lattner wrote:

On Jan 12, 2016, at 8:07 PM, Dave via swift-evolution > <swift-evolution@swift.org> wrote:

What KVO did was to offer an NSKeyValueSetMutationKind enum containing constants for insertion and removal as well as OR and AND operations with other sets. If you don't want to do that, another possible interface could be to provide two ranges, one representing the range of the affected region before the change, and another representing it afterward. If you had an empty range for "before" and a non-empty range for "after", that would represent an insertion. The reverse would be removal, and anything else would be a replacement of some kind.

Charles

Also, good points. I guess my idea then is:
“did/willUpdate”, “did/willInsert”, and “did/willRemove” for when you don’t care about which element was changed (and for types that aren’t indexable anyway)
“did/willUpdateAtIndex”, “did/WillInsertAtIndex”, and “did/WillRemoveAtIndex” for single elements
“did/willUpdateInRange”, “did/WillInsertInRange”, and “did/WillRemoveInRange” for multiple elements

That’s a lot of new keywords, though… Oh! What if it was *only* did/willUpdate, did/willAdd, and did/willRemove, and they were overloaded with (), (atIndex: Index), and (inRange: Range<Index>) forms? Like this:

Just a random comment on this thread: our desire is to introduce
property behaviors, and “demote” things like property observers into
library features. This is great because it makes it much easier to
extend these capabilities without hacking on the compiler, and will
allow you to define custom behaviors in your own code.

I don’t know if the first round of behaviors will actually allow us to
eliminate willset/didset though, simply given that they need to poke
at the super implementation. That said, we’d rather work towards
fixing those problems: proposals to make the existing property
observers richer aren’t likely to be accepted.

-Chris

I understand and I am aware of this proposal. I only raised this since
collections are a primitive object type that are used quite frequently in
swift. I think it would be acceptable to introduce a generic way of knowing
when an item was added, updated or removed which could be demoted with set
and get.

I think the pros outweigh the cons. Previous proposals such as default
initialisers are either too complex / niche or can already be done via the
swift language. So are better implemented with property behaviours.

···

*___________________________________*

*James⎥Lead Engineer*

*james@supmenow.com <james@supmenow.com>⎥supmenow.com <http://supmenow.com>*

*Sup*

*Runway East *

*10 Finsbury Square*

*London*

* EC2A 1AF *

On Wed, Jan 13, 2016 at 4:45 AM, Chris Lattner via swift-evolution < swift-evolution@swift.org> wrote:

On Jan 12, 2016, at 8:07 PM, Dave via swift-evolution < > swift-evolution@swift.org> wrote:
>> What KVO did was to offer an NSKeyValueSetMutationKind enum containing
constants for insertion and removal as well as OR and AND operations with
other sets. If you don't want to do that, another possible interface could
be to provide two ranges, one representing the range of the affected region
before the change, and another representing it afterward. If you had an
empty range for "before" and a non-empty range for "after", that would
represent an insertion. The reverse would be removal, and anything else
would be a replacement of some kind.
>>
>> Charles
> Also, good points. I guess my idea then is:
> “did/willUpdate”, “did/willInsert”, and “did/willRemove” for when you
don’t care about which element was changed (and for types that aren’t
indexable anyway)
> “did/willUpdateAtIndex”, “did/WillInsertAtIndex”, and
“did/WillRemoveAtIndex” for single elements
> “did/willUpdateInRange”, “did/WillInsertInRange”, and
“did/WillRemoveInRange” for multiple elements
>
> That’s a lot of new keywords, though… Oh! What if it was *only*
did/willUpdate, did/willAdd, and did/willRemove, and they were overloaded
with (), (atIndex: Index), and (inRange: Range<Index>) forms? Like this:

Just a random comment on this thread: our desire is to introduce property
behaviors, and “demote” things like property observers into library
features. This is great because it makes it much easier to extend these
capabilities without hacking on the compiler, and will allow you to define
custom behaviors in your own code.

I don’t know if the first round of behaviors will actually allow us to
eliminate willset/didset though, simply given that they need to poke at the
super implementation. That said, we’d rather work towards fixing those
problems: proposals to make the existing property observers richer aren’t
likely to be accepted.

-Chris

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

Agreed. I hadn’t read that thread yet (or at least hadn’t thought about it enough) when I posted my comments. I know I’m not the OP, but for FWIW I’m more than willing to for this to get merged into the “Behaviors” suggestion. I don’t even think Behaviors would have to be changed… Seems like a proper superset of this idea.

- Dave Sweeris

···

On Jan 12, 2016, at 20:45, Chris Lattner <clattner@apple.com> wrote:

On Jan 12, 2016, at 8:07 PM, Dave via swift-evolution <swift-evolution@swift.org> wrote:

What KVO did was to offer an NSKeyValueSetMutationKind enum containing constants for insertion and removal as well as OR and AND operations with other sets. If you don't want to do that, another possible interface could be to provide two ranges, one representing the range of the affected region before the change, and another representing it afterward. If you had an empty range for "before" and a non-empty range for "after", that would represent an insertion. The reverse would be removal, and anything else would be a replacement of some kind.

Charles

Also, good points. I guess my idea then is:
“did/willUpdate”, “did/willInsert”, and “did/willRemove” for when you don’t care about which element was changed (and for types that aren’t indexable anyway)
“did/willUpdateAtIndex”, “did/WillInsertAtIndex”, and “did/WillRemoveAtIndex” for single elements
“did/willUpdateInRange”, “did/WillInsertInRange”, and “did/WillRemoveInRange” for multiple elements

That’s a lot of new keywords, though… Oh! What if it was *only* did/willUpdate, did/willAdd, and did/willRemove, and they were overloaded with (), (atIndex: Index), and (inRange: Range<Index>) forms? Like this:

Just a random comment on this thread: our desire is to introduce property behaviors, and “demote” things like property observers into library features. This is great because it makes it much easier to extend these capabilities without hacking on the compiler, and will allow you to define custom behaviors in your own code.

I don’t know if the first round of behaviors will actually allow us to eliminate willset/didset though, simply given that they need to poke at the super implementation. That said, we’d rather work towards fixing those problems: proposals to make the existing property observers richer aren’t likely to be accepted.

-Chris

···

On Jan 13, 2016, at 12:49 AM, Charles Srstka via swift-evolution <swift-evolution@swift.org> wrote:

On 2016-01-12 23:45, Chris Lattner wrote:

On Jan 12, 2016, at 8:07 PM, Dave via swift-evolution >> <swift-evolution@swift.org> wrote:

What KVO did was to offer an NSKeyValueSetMutationKind enum containing constants for insertion and removal as well as OR and AND operations with other sets. If you don't want to do that, another possible interface could be to provide two ranges, one representing the range of the affected region before the change, and another representing it afterward. If you had an empty range for "before" and a non-empty range for "after", that would represent an insertion. The reverse would be removal, and anything else would be a replacement of some kind.
Charles

Also, good points. I guess my idea then is:
“did/willUpdate”, “did/willInsert”, and “did/willRemove” for when you don’t care about which element was changed (and for types that aren’t indexable anyway)
“did/willUpdateAtIndex”, “did/WillInsertAtIndex”, and “did/WillRemoveAtIndex” for single elements
“did/willUpdateInRange”, “did/WillInsertInRange”, and “did/WillRemoveInRange” for multiple elements
That’s a lot of new keywords, though… Oh! What if it was *only* did/willUpdate, did/willAdd, and did/willRemove, and they were overloaded with (), (atIndex: Index), and (inRange: Range<Index>) forms? Like this:

Just a random comment on this thread: our desire is to introduce
property behaviors, and “demote” things like property observers into
library features. This is great because it makes it much easier to
extend these capabilities without hacking on the compiler, and will
allow you to define custom behaviors in your own code.
I don’t know if the first round of behaviors will actually allow us to
eliminate willset/didset though, simply given that they need to poke
at the super implementation. That said, we’d rather work towards
fixing those problems: proposals to make the existing property
observers richer aren’t likely to be accepted.
-Chris

Is the proposal document for the property behaviors concept available online anywhere? I'm intrigued by it, and would like to read about the specifics.

Thanks,
Charles

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

This proposal of Property Behaviors is amazing! Thanks a lot Joe Groff
<https://github.com/jckarter&gt; (and others).

···

Em qua, 13 de jan de 2016 às 06:50, Austin Zheng via swift-evolution < swift-evolution@swift.org> escreveu:

Swift property behaviors · GitHub

On Jan 13, 2016, at 12:49 AM, Charles Srstka via swift-evolution < > swift-evolution@swift.org> wrote:

On 2016-01-12 23:45, Chris Lattner wrote:

On Jan 12, 2016, at 8:07 PM, Dave via swift-evolution > <swift-evolution@swift.org> wrote:

What KVO did was to offer an NSKeyValueSetMutationKind enum containing
constants for insertion and removal as well as OR and AND operations with
other sets. If you don't want to do that, another possible interface could
be to provide two ranges, one representing the range of the affected region
before the change, and another representing it afterward. If you had an
empty range for "before" and a non-empty range for "after", that would
represent an insertion. The reverse would be removal, and anything else
would be a replacement of some kind.
Charles

Also, good points. I guess my idea then is:
“did/willUpdate”, “did/willInsert”, and “did/willRemove” for when you
don’t care about which element was changed (and for types that aren’t
indexable anyway)
“did/willUpdateAtIndex”, “did/WillInsertAtIndex”, and
“did/WillRemoveAtIndex” for single elements
“did/willUpdateInRange”, “did/WillInsertInRange”, and
“did/WillRemoveInRange” for multiple elements
That’s a lot of new keywords, though… Oh! What if it was *only*
did/willUpdate, did/willAdd, and did/willRemove, and they were overloaded
with (), (atIndex: Index), and (inRange: Range<Index>) forms? Like this:

Just a random comment on this thread: our desire is to introduce
property behaviors, and “demote” things like property observers into
library features. This is great because it makes it much easier to
extend these capabilities without hacking on the compiler, and will
allow you to define custom behaviors in your own code.
I don’t know if the first round of behaviors will actually allow us to
eliminate willset/didset though, simply given that they need to poke
at the super implementation. That said, we’d rather work towards
fixing those problems: proposals to make the existing property
observers richer aren’t likely to be accepted.
-Chris

Is the proposal document for the property behaviors concept available
online anywhere? I'm intrigued by it, and would like to read about the
specifics.

Thanks,
Charles

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

Hi Charles,

I believe you can find the latest version (as of yesterday) here:

See also this email from Joe Groff summarizing the changes:

···

On Jan 13, 2016, at 5:07 PM, Joe Groff via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Thanks everyone for the first round of feedback on my behaviors proposal. I've revised it with the following changes:

- Instead of relying on mapping behaviors to function or type member lookup, I've introduced a new purpose-built 'var behavior' declaration, which declares the accessor and initializer requirements and provides the storage and behavior methods of the property. I think this gives a clearer design for authoring behaviors, and allows for a more efficient and flexible implementation model.
- I've backed off from trying to include 'let' behaviors. As many of you noted, it's better to tackle immutable computed properties more holistically than to try to backdoor them in.
- I suggest changing the declaration syntax to use a behavior to square brackets—'var [behavior] foo'—which avoids ambiguity with destructuring 'var' bindings, and also works with future candidates for behavior decoration, particularly `subscript`.

Here's the revised proposal:

Property behavior declarations · GitHub

For reference, here's the previous iteration:

Swift property behaviors · GitHub

Thanks for taking a look!

-Joe

On Jan 13, 2016, at 3:49 AM, Charles Srstka via swift-evolution <swift-evolution@swift.org> wrote:

On 2016-01-12 23:45, Chris Lattner wrote:

On Jan 12, 2016, at 8:07 PM, Dave via swift-evolution >> <swift-evolution@swift.org> wrote:

What KVO did was to offer an NSKeyValueSetMutationKind enum containing constants for insertion and removal as well as OR and AND operations with other sets. If you don't want to do that, another possible interface could be to provide two ranges, one representing the range of the affected region before the change, and another representing it afterward. If you had an empty range for "before" and a non-empty range for "after", that would represent an insertion. The reverse would be removal, and anything else would be a replacement of some kind.
Charles

Also, good points. I guess my idea then is:
“did/willUpdate”, “did/willInsert”, and “did/willRemove” for when you don’t care about which element was changed (and for types that aren’t indexable anyway)
“did/willUpdateAtIndex”, “did/WillInsertAtIndex”, and “did/WillRemoveAtIndex” for single elements
“did/willUpdateInRange”, “did/WillInsertInRange”, and “did/WillRemoveInRange” for multiple elements
That’s a lot of new keywords, though… Oh! What if it was *only* did/willUpdate, did/willAdd, and did/willRemove, and they were overloaded with (), (atIndex: Index), and (inRange: Range<Index>) forms? Like this:

Just a random comment on this thread: our desire is to introduce
property behaviors, and “demote” things like property observers into
library features. This is great because it makes it much easier to
extend these capabilities without hacking on the compiler, and will
allow you to define custom behaviors in your own code.
I don’t know if the first round of behaviors will actually allow us to
eliminate willset/didset though, simply given that they need to poke
at the super implementation. That said, we’d rather work towards
fixing those problems: proposals to make the existing property
observers richer aren’t likely to be accepted.
-Chris

Is the proposal document for the property behaviors concept available online anywhere? I'm intrigued by it, and would like to read about the specifics.

Thanks,
Charles

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution