I want to see more languages that incorporate dataflow, the way spreadsheets do. That kind of execution model is perfect for user interfaces. I once spent some time thinking about a dataflow extension for Java, which I called Ripple. As I recall, Internet Explorer at one point was exploring spreadsheet-style continuously-updated functions for dynamic HTML. This was back around when Netscape came up with their ill-fated (and deservedly so) "layers" hack. I thought IE's data flow feature seemed like a great idea, but I think it died when the market showed no interest (probably because it was too "weird"). Unfortunately I have no idea what keywords to search for to find a reference to this.
Most UI-oriented languages these days seem to be based on events. But it's difficult to maintain invariants using events, unless you program in a stylized way where almost all events call a single "recalculate the entire UI" function. Dataflow would make invariants much easier to maintain, and would make the UI itself more efficient because only the parts that have changed would need to be recalculated.
The only language I know of offhand that has a dataflow feature is Visual Basic, but VB's incarnation of the idea is strongly coupled to relational databases. That design is unfortunate because it causes the relational structure of your database to strongly influence your user interface. It would be better if they had made it possible to insert a data model (or computation) in between the database and the UI.
In case you missed what I just said, let me say it again: Visual Basic has a feature that, although crippled, is still a step in the right direction, and I know of no other language that rivals VB in this area. If you're a language designer, consider the gauntlet to have been thrown down.
While I'm at it, I'd also like to see more languages with undo features (or, more generally, transactions), built into the execution model. That would make it almost trivial to write programs that involve dialog boxes with OK and Cancel buttons. Todd Proebstring mentioned this at LL2, and as far as I know, nobody has taken him up on it yet.
Back when I was thinking about Ripple, I thought of adding an undo-style feature, where you could temporarily restrict the effects of a data change so that you could make several changes all at once before updating the rest of the world. Syntactically, this was based on an "atomic" block, similar to Java's synchronized block, where nothing would be updated until the block was completely finished. The block could be aborted from inside the block, via a "rollback" statement.
I got paid once to write a language interpreter that had built-in undo. It also had a built-in editor, and changes to source code were stored on the same undo stack as changes to program state, so that when you hit the undo button, it actually undid edits to the code as well as running the program backwards (this was a controversial decision, and I designed it so that this behavior was optional). The language was designed to control a robot, so the undo feature also made the robot move backwards, in addition to merely restoring the internal program state to what it used to be. It could also undo file output. It was a good thing the language didn't have any networking features, since that would have been the only thing we couldn't have undone.
This brings up a point I want to make about any language that might aspire to including an undo feature. The undo feature must be extensible with application-specific logic for side effects. That way an application programmer can create reversible robot motions, or reversible file I/O, without requiring that robot motion and file I/O be built into the compiler. Let the libraries create an arbitrary number of reversible operations.
These two features go very well together, and I suspect that as soon as you implement dataflow, you'll find yourself wanting transactions almost immediately. Since dataflow is based on implicit execution, you very quickly find yourself wanting some way to explicitly control that execution, and transactions are a good technique for doing that.
I'm not sure why people don't try to solve these things at the language level more often. Is it because most people who design languages don't work on user interfaces? Or is it because people who design languages don't often think of changing their execution model, preferring instead to focus on syntax and typing issues?
Followups to Dataflow Languages:Posted on October 31, 2003 05:20 PM
More languages articles
What is the dataflow feature in VB? (Just a mention; I can look it up if I know what to look for.)
Posted by: Alistair Bayley at November 3, 2003 07:04 AMThe VB feature is called "data binding".
Posted by: kim at November 4, 2003 11:38 AMIE's dataflow feature is called Dynamic Properties.
http://msdn.microsoft.com/workshop/author/dhtml/overview/recalc.asp
Here's some research into dataflow languages. They call it "self-adjusting computation". Presented at POPL-02.
http://www-2.cs.cmu.edu/~umut/research/
Posted by: kim at February 12, 2004 02:45 PM