0

I want to use let expressions, but the following code doesn't work:

true ? (let x=1, let y=2, x+y) : (let x=3, let y=4, x-y); // SyntaxError

How am I supposed to do this?

  • Another case where trying to force use of a ternary just leads to a bigger mess. If you need to go through hoops to use a ternary, you should probably just use an explicit if...else. – Carcigenicate May 06 '17 at 15:23
  • @Carcigenicate Solid advice, but playing around like OP really gives great insight into the language itself. – le_m May 06 '17 at 15:36

2 Answers2

0

Unfortunately, Javascript lacks lisp-style let expressions. However, since there are default parameters and arrow functions we can mimic them:

const let_ = f => f();

console.log(
  true ? let_((x = 1, y = 2) => x + y) : let_((x = 3, y = 4) => x - y) // 3
);

To be honest, this is a bit tedious and the code is pretty verbose. The following recursive use case might be more convincing:

const let_ = f => f();

const fact = n => let_(
  (aux = (n, acc) => n === 1 ? acc : aux(n - 1, acc * n)) => aux(n, 1)
);

console.log(
  fact(5) // 120
);

It is questionable whether this is idiomatic Javascript, but it was litteraly the first time I used default parameters in my code.

  • why not const fact = n =>(aux = (n, acc) => n === 1 ? acc : aux(n - 1, acc * n)) => aux(n, 1))()); – Jonas Wilms May 06 '17 at 15:37
  • and why dont u use regular functions? – Jonas Wilms May 06 '17 at 15:39
  • Whoa, what a horrible and clever abuse of syntax :-) I guess you should rather deploy [a transpiler](https://babeljs.io/docs/plugins/transform-do-expressions/) that implements the [`do`-expression proposal](https://gist.github.com/dherman/1c97dfb25179fa34a41b5fff040f9879) – Bergi May 06 '17 at 16:43
0

The following is a kind of sugar...

let x = 1
console.log(x)

Without var, const, or let, we could use functions to bind variables

// let x = 1; console.log(x);
(x => console.log(x)) (1)

Of course this works if you have multiple variables too

(x =>
  (y => console.log(x + y))) (1) (2)

And because JavaScript functions can have more then 1 parameter, you could bind multiple variables using a single function, if desired

((x,y) => console.log(x + y)) (1,2)

As for your ternary expression

true
  ? ((x,y) => console.log(x + y)) (1,2)
  : ((x,y) => console.log(x - y)) (1,2)
// 3

false
  ? ((x,y) => console.log(x + y)) (1,2)
  : ((x,y) => console.log(x - y)) (1,2)
// -1

None of this requires any fanciful syntax or language features either – the following would work on pretty much any implementation of JS that I can think of

true
  ? (function (x,y) { console.log(x + y) }) (1,2)
  : (function (x,y) { console.log(x - y) }) (1,2)
// 3

false
  ? (function (x,y) { console.log(x + y) }) (1,2)
  : (function (x,y) { console.log(x - y) }) (1,2)
// -1
Mulan
  • 129,518
  • 31
  • 228
  • 259