Hacker News new | ask | show | jobs
by Animats 4219 days ago
Yes, way too imperative. "map" and "reduce" are imperative; they order something done.

With true declarative forms, you can treat them as data and do something other than execute them. It's hard to do much with an imperative form other than execute it. A scene graph or a game level file is a declarative form; you can view it from different angles and positions. The programs that plan actions for NPCs look at a game level and decide what to do. CAD files are declarative. Spreadsheets are mostly declarative.

The usual problem with declarative forms is lack of expressive power. If you need to express something the declarative form can't handle, it's tempting to bolt on some kind of imperative gimmick. This is how we ended up with Javascript.

4 comments

> "map" and "reduce" are imperative; they order something done.

So maybe it's my age showing, but I was taught that imperative was using explicit variables to control the "looping" (e.g. for with an index a la C style programming) whereas using "higher order functions" was not imperative. And I tend to agree with that. So I disagree that map and reduce are imperative because they don't explicitly control how the looping is done.

Can anyone cite where map and reduce are imperative? Must be some new-fangled text book that I'm not aware of ;)

And I get that someone could impose on me to cite references that map and reduce are not imperative. Point taken and I'm thinking that I got this from SICP in the first place so I'm looking it up now. Will report back if I find anything.

EDIT: First quote from SICP:

"In contrast to functional programming, programming that makes extensive use of assignment is known as imperative programming. In addition to raising complications about computational models, programs written in imperative style are susceptible to bugs that cannot occur in functionalprograms."

If I may try to answer for Animats, I think the point is that you're still using the map in an imperative way. You set a variable to some list, then you apply a map to that list and assign that to another variable. If you then change the first variable, the latter doesn't change - that means the order of execution matters for the application of the map.

That said, that's mostly a specificity of Javascript than a property of the map operation. There's no reason you can't have a map on an FRP that truly declares a relationship between entities.

I think (perhaps unknowingly) you're just playing a semantic game. By your definition everything is imperative, even if it is also totally declarative. All programs are imperative in your sense. Even if you could tell the computer "Do what I want" and expect it to be psychic, that would still be imperative by your definition.

But the difference between imperative programming and declarative programming is not drawn by "ordering something done" (even if the article didn't define things precisely enough to prevent confusion on this point). It's basically a level-of-abstraction/level-of-detail thing. Saying "double each number in this list" is significantly different than saying "follow this step-by-step algorithm to double each number in the list".

The boundaries can get fuzzy; arguments can be made about where to draw the lines. But your approach lumps everything on one side of the line, and therefore becomes incapable of saying anything very useful.

"map" and "reduce" are imperative; they order something done.

Well, in JS, sure, but what about if you could do:

  a = 13
  b = map(function(x){ return x; }, [1, 2, 8, a])
  print b
  >  [1, 2, 8, 13]
  a = 26
  print b
  > [1, 2, 8, 26]
(While I'm representing it as a sequential program, the idea would be to plug "a" and "b" to some IO channels.)

What I'm trying to say is that the concept of map is not necessarily imperative, just JS's version.

> Yes, way too imperative. "map" and "reduce" are imperative; they order something done.

Well how would you write these snippets the right way then?with the language of your choice, so it fits the declaritive way a 100% ?

I'm not saying those things should be written in a declarative form, just that what the author is calling "declarative" isn't.

If you wanted to do something like that in a declarative way, though, consider a spreadsheet with an intelligent evaluator. The spreadsheet is a declaration of a dependency relationship. When a number is changed, the numbers depending upon it change. It's not always just a recalculation, either. There are spreadsheets that let you work backwards (change a total, watch the inputs change), and cloud-based spreadsheets that sync (one of YCombinator's companies, Fivetran, has one).

Spreadsheets also suffer from imperative creep. People try to use Excel spreadsheets for iterative work, which gets away from the declarative design.

Spreadsheets also suffer from imperative creep. People try to use Excel spreadsheets for iterative work, which gets away from the declarative design.

...which is how we ended up with VBA macros.

> If you wanted to do something like that in a declarative way, though, consider a spreadsheet with an intelligent evaluator. The spreadsheet is a declaration of a dependency relationship. When a number is changed, the numbers depending upon it change.

Seems like you're talking about functional reactive programming (or reactive programming in general).