JSLint. The Good Parts. http://www.JSLint.com/ WARNING! JSLint - - PowerPoint PPT Presentation

jslint
SMART_READER_LITE
LIVE PREVIEW

JSLint. The Good Parts. http://www.JSLint.com/ WARNING! JSLint - - PowerPoint PPT Presentation

Syntaxation JavaScript: The Universal Virtual Machine JSLint. The Good Parts. http://www.JSLint.com/ WARNING! JSLint will hurt your feelings. Syntax is the least important aspect of programming language design. Syntax is the least


slide-1
SLIDE 1

Syntaxation

slide-2
SLIDE 2

JavaScript:

The Universal Virtual Machine

slide-3
SLIDE 3

JSLint.

The Good Parts. http://www.JSLint.com/

slide-4
SLIDE 4

WARNING!

JSLint will hurt your feelings.

slide-5
SLIDE 5

Syntax is the least important aspect of programming language design.

slide-6
SLIDE 6

Syntax is the least important aspect of programming language design.

Fashion is the least important aspect of clothing design.

slide-7
SLIDE 7

Programming Languages:

An Interpreter-Based Approach

Samuel N. Kamin [1990]

Lisp APL Scheme SASL Clu Smalltalk Prolog

slide-8
SLIDE 8

Minimal Syntax

slide-9
SLIDE 9

Lisp (fname arg1 arg2)

slide-10
SLIDE 10

Smalltalk 80

  • bject name1: arg name2: arg2
  • bject operator arg

[ var | block ]

slide-11
SLIDE 11

IF Statement

And yet don't look too good, nor talk too wise

slide-12
SLIDE 12

C FORTRAN IF(A-B)20,20,10 10 A=B 20 CONTINUE

slide-13
SLIDE 13

C FORTRAN IV IF(A.LE.B)GO TO 30 A=B 30 CONTINUE

slide-14
SLIDE 14

comment ALGOL 60; if a>b then begin a:=b end;

slide-15
SLIDE 15

// BCPL IF A > B { A := B }

slide-16
SLIDE 16

/* B */ if (a > b) { a = b; }

slide-17
SLIDE 17
  • - Ada

if a > b then a := b; end if;

slide-18
SLIDE 18

¢ Algol 68 ¢ if a > b then a := b fi

slide-19
SLIDE 19

Emotional Style

Fashionable Tolerance

  • f Syntaxtic Ambiguity
slide-20
SLIDE 20

a ☁ b ♥ c ((a ☁ b) ♥ c) (a ☁ (b ♥ c))

slide-21
SLIDE 21

Binding Power

10 = += -= 20 ? 40 && || 50 === < > <= >= !== 60 + - 70 * / 80 unary 90 . [ (

slide-22
SLIDE 22

word

variable? statement keyword?

  • perator?

special form?

slide-23
SLIDE 23

( )

Function definition and invocation Grouping Separation

slide-24
SLIDE 24

Parsing

Theory of Formal Languages

slide-25
SLIDE 25

Tokens are objects

prototype ← symbol ← token advance() advance(id)

slide-26
SLIDE 26

a = b + c;

Weave a stream of tokens into a tree

a = b + c

slide-27
SLIDE 27

Top Down Operator Precedence

  • Vaughan Pratt [POPL 1973]
  • simple to understand
  • trivial to implement
  • easy to use
  • extremely efficient
  • very flexible
  • beautiful
slide-28
SLIDE 28

Why have you never heard of this?

  • Preoccupation with BNF grammars and

their various offspring, along with their related automata and theorems.

  • Requires a functional programming

language.

  • LISP community did not want syntax.
  • JavaScript is a functional language with a

community that likes syntax.

slide-29
SLIDE 29

What do we expect to see to the left of the token?

left denotation led null denotation nud

slide-30
SLIDE 30
  • only nud

! ~ typeof { prefix

  • only led

* . = === infix, suffix

  • nud & led

+ - ( [

slide-31
SLIDE 31

var prototype_token = { nud: function () { this.error("Undefined."); }, led: function (left) { this.error("Missing operator."); }, error: function(message) { ... }, lbp: 0 // left binding power };

slide-32
SLIDE 32

var symbol_table = {}; function symbol(id, bp) { var s = symbol_table[id]; bp = bp || 0; if (s) { if (bp >= s.lbp) { s.lbp = bp; } } else { s = Object.create(prototype_token); s.id = s.value = id; s.lbp = bp; symbol_table[id] = s; } return s; }

slide-33
SLIDE 33

symbol(":"); symbol(";"); symbol(","); symbol(")"); symbol("]"); symbol("}"); symbol("else"); symbol("(end)"); symbol("(word)");

slide-34
SLIDE 34

symbol("+", 60).led = function (left) { this.first = left; this.second = expression(60); this.arity = "binary"; return this; };

slide-35
SLIDE 35

symbol("*", 70).led = function (left) { this.first = left; this.second = expression(70); this.arity = "binary"; return this; };

slide-36
SLIDE 36

function infix(id, bp, led) { var s = symbol(id, bp); s.led = led || function (left) { this.first = left; this.second = expression(bp); this.arity = "binary"; return this; }; return s; }

slide-37
SLIDE 37

infix("+", 60); infix("-", 60); infix("*", 70); infix("/", 70); infix("===", 50); infix("!==", 50); infix("<", 50); infix("<=", 50); infix(">", 50); infix(">=", 50);

slide-38
SLIDE 38

infix("?", 20, function led(left) { this.first = left; this.second = expression(0); advance(":"); this.third = expression(0); this.arity = "ternary"; return this; });

slide-39
SLIDE 39

function infixr(id, bp, led) { var s = symbol(id, bp); s.led = led || function (left) { this.first = left; this.second = expression(bp - 1); this.arity = "binary"; return this; }; return s; }

slide-40
SLIDE 40

function assignment(id) { return infixr(id, 10, function (left) { if (left.arity !== "name" && left.id !== "." && left.id !== "[") { left.error("Bad lvalue."); } this.first = left; this.second = expression(9); this.assignment = true; this.arity = "binary"; return this; }); } assignment("="); assignment("+="); assignment("-=");

slide-41
SLIDE 41

function prefix(id, nud) { var s = symbol(id); s.nud = nud || function () { this.first = expression(80); this.arity = "unary"; }; return s; } prefix("+"); prefix("-"); prefix("!"); prefix("typeof");

slide-42
SLIDE 42

prefix("(", function () { var e = expression(0); advance(")"); return e; });

slide-43
SLIDE 43

Statement denotation

first null denotation fud

slide-44
SLIDE 44

function statement() { var exp, tok = token; if (tok.fud) { advance(); return tok.fud(); } exp = expression(0); if (!exp.assignment && exp.id !== "(") { exp.error("Bad expression statement."); } advance(";"); return exp; }

slide-45
SLIDE 45

function statements() { var array = []; while (token.nud || token.fud) { a.push(statement()); } return array; }

slide-46
SLIDE 46

function block() { advance("{"); var a = statements(); advance("}"); return a; }

slide-47
SLIDE 47

function stmt(id, f) { var s = symbol(id); s.fud = f; return s; }

slide-48
SLIDE 48

stmt("if", function () { advance("("); this.first = expression(0); advance(")"); this.second = block(); if (token.id === "else") { advance("else"); this.third = token.id === "if" ? statement() : block(); } this.arity = "statement"; return this; });

slide-49
SLIDE 49

stmt("if", function () { this.first = expression(0); this.second = block(); if token.id === "else" { advance("else"); this.third = token.id === "if" ? statement() : block(); } // BCPL this.arity = "statement"; return this; });

slide-50
SLIDE 50

stmt("if", function () { this.first = expression(0); advance("then"); this.second = statements(); if token.id === "else" then advance("else"); this.third = statements(); fi // Algol 68 advance("fi"); this.arity = "statement"; return this; });

slide-51
SLIDE 51

function expression(rbp) { var left, tok = token; advance(); left = tok.nud(); while (rbp < token.lbp) { tok = token; advance(); left = tok.led(left); } return left; }

slide-52
SLIDE 52

a = b + c;

Weave a stream of tokens into a tree

a = b + c

slide-53
SLIDE 53

a = b + c;

{ id: "=", arity: "binary", first: {id: "a", arity: "word"}, second: { id: "+", arity: "binary", first: {id: "b", arity: "word"}, second: {id: "c", arity: "word"} } }

slide-54
SLIDE 54

a = b + c;

statements() statement() expression(0) a.nud() while 0 < =.lbp =.led(a) expression(10) b.nud() while 10 < +.lbp +.led(b) expression(60) c.nud()

slide-55
SLIDE 55

a.b = c;

Weave a stream of tokens into a tree

a = b . c

slide-56
SLIDE 56

a.b = c;

{ id: "=", arity: "binary", first: { id: ".", arity: "binary", first: {id: "a", arity: "word"}, second: {id: "b", arity: "word"} }, second: {id: "c", arity: "word"} }

slide-57
SLIDE 57

a.b = c;

statements() statement() expression(0) a.nud() while 0 < ..lbp ..led(a) expression(90) b.nud() while 90 < =.lbp while 0 < =.lbp =.led(a.b) expression(60) c.nud()

slide-58
SLIDE 58

Top Down Operator Precedence

  • It is easy to build parsers with it.
  • It is really fast because it does almost

nothing.

  • It is fast enough to use as an interpreter.
  • Dynamic: Build DSLs with it.
  • Extensible languages.
  • No more reserved words.
slide-59
SLIDE 59

Advice for language designers

slide-60
SLIDE 60

Minimalism

  • Conceptual
  • Notational

Don't be cryptic

  • Error resistant

Confusion free

  • Readable

Can be easily and correctly understood by a reader

slide-61
SLIDE 61

Innovate

  • We already have many Java-like

languages.

CokeBottle cokeBottle = new CokeBottle();

  • Select your features carefully.
  • Beware of Sometimes Useful.
  • Avoid universality.
  • Manage complexity.
  • Promote quality.
slide-62
SLIDE 62

Innovate

  • Make new mistakes.
  • Let the language teach you.
  • Embrace Unicode.
  • Leap forward.
  • Forgotten treasure:

State machines, constraint engines.

  • Exploit parallelism.
  • Distributed programming: clouds & cores.
  • Have fun.
slide-63
SLIDE 63

;

slide-64
SLIDE 64

https://github.com/douglascrockford/TDOP https://github.com/douglascrockford/JSLint Beautiful Code: Leading Programmers Explain How They Think [Chapter 9] Oram & Wilson O'Reilly

slide-65
SLIDE 65

Thank you and good night.