Re-purposing UPDATE to be the "anti-DEFAULT"

@gchiu asked for an operation that is similar to default, though kind of the reverse. Rather than rejecting an assignment based on whether the current value of a variable is blank/void, it would reject the assignment if the new value was blank or void...keeping the old value in these cases.

I liked his idea of calling this UPDATE:

>> x: 10

>> x: update ()
>> print x
10

>> x: update [1 + 1]
>> print x
2

>> x: update 20
>> print x
20

>> x: update [if 1 > 2 [1000]]
>> print x
20

I like it--I'd certainly use it. But one problem is that there's an existing UPDATE port action, which was defined in Rebol2:

http://www.rebol.com/docs/words/wupdate.html

I'm not totally getting this, as it seems sort of like a WAIT statement, a SYNC, a FLUSH, a FETCH... I dunno. UPDATE seems a strange word to grab when there's this nice other function for it.

For what it's worth, UPDATE is not called anywhere in the R3-Alpha sources. If anyone feels it's somehow critical or crucial or can't be named-out-of-the-way / done-another-way speak up, as I want this operator too.

Okay, actually it is used... but the only mentions are internal. It's what native port actors use to "respond to WAKE-UP".

So the action never triggers in usermode ports.

Because this is apparently some internal message only, I'm going to bump it to ON-WAKE-UP.

Can't you just check to see if it's a port! and if so, keep the existing behaviour? Otherwise, use the new behaviour?

No. What if you wanted to update a variable from one port to another? Also, the interface is different. A left-quoting operation with a right-hand-side is actually arity 2, it just looks arity 1.

(Though interestingly, there is some smart ability to look at things and make decisions at runtime based on how an operator is to act... like how I said you could have 1 + 2 be 3, but (+ 1 2 3) be 6. The dynamic behavior can actually look around and act fairly differently, even when looking backwards...but sometimes quoting backwards and sometimes not is actually one of the things we don't have, because "the deed is done" by the time execution happens.)

If it turns out to be relevant to userspace we can name it "sync" or something, once we figure out what it actually is. But the whole PORT! thing is going to get rethought. So it's good if we have all our relevant protocols nice and up to date to look at as a group and solve together.

UPDATE (and UPDATE*) are now provided in master, so use them and see how it goes.

UPDATE 2018 (no pun intended): Today this construct is known as MAYBE, e.g. x: maybe switch [...] will only overwrite x if the switch succeeds and produces a non-NULL result.

Note that UPDATE* considers the right hand side being BLANK! to be an update, while plain UPDATE thinks that's not a value worth updating to. A similar separation exists for DEFAULT and DEFAULT*

Additionally, the * versions do not worry about whether you have an evaluative right hand side that's not a block.

1 Like