Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Javascript: le parti buone

weLaika
April 11, 2016

Javascript: le parti buone

Tutti i linguaggi di programmazione contengono parti “buone” e parti “cattive”. JavaScript è stato sviluppato in dieci giorni e dopo la sua standardizzazione era ormai troppo tardi per corregge alcuni problemi di design.
Lavorare con framework JavaScript non ci esime dal conoscere a fondo le parti “buone” del linguaggio.
In questo talk prenderemo alcuni concetti dal famoso libro “JavaScript: The Good Parts” di D. Crockford, con un occhio di riguardo per ECMAScript 2015 (ES6).

weLaika

April 11, 2016
Tweet

More Decks by weLaika

Other Decks in Technology

Transcript

  1. Slides' conventions (function () { 'use strict'; // slides' code

    }()); 2 Torino Coding Society 11/04/2016 - @delphaber
  2. Slides' conventions $ node -v v.5.10.1 Examples which include ES6

    code need to be transpiled first with https:/ /babeljs.io/repl. 3 Torino Coding Society 11/04/2016 - @delphaber
  3. Method invocation pattern var forrest = { name: 'Forrest', run:

    function() { console.log('Run ' + this.name + ', run!'); } }; forrest.run(); forrest['run'](); => "Run Forrest, run!" 6 Torino Coding Society 11/04/2016 - @delphaber
  4. Function invocation pattern #1 function sum(a, b) { return a

    + b; } console.log(sum(5, 10)); => 15 8 Torino Coding Society 11/04/2016 - @delphaber
  5. Function invocation pattern #2 var forrest = { chocolatesCount: 10,

    eat: function() { function randomAmount() { return Math.floor((Math.random() * this.chocolatesCount) + 1); } this.chocolatesCount -= randomAmount(); } }; forrest.eat(); console.log("Chocolates left:", forrest.chocolatesCount); 9 Torino Coding Society 11/04/2016 - @delphaber
  6. Function invocation pattern #2 return Math.floor((Math.random() * this.chocolatesCount) + 1);

    ^ TypeError: Cannot read property 'chocolatesCount' of undefined 10 Torino Coding Society 11/04/2016 - @delphaber
  7. Function invocation pattern #2 Without 'use strict', this is bound

    to the global object. function randomAmount() { return Math.floor((Math.random() * this.chocolatesCount) + 1); } this.chocolatesCount -= randomAmount(); => Chocolates left: NaN 11 Torino Coding Society 11/04/2016 - @delphaber
  8. Function invocation pattern #2 Solution #1 [...] eat: function() {

    var that = this; function randomAmount() { return Math.floor((Math.random() * that.chocolatesCount) + 1); } this.chocolatesCount -= randomAmount(); } [...] forrest.eat(); 13 Torino Coding Society 11/04/2016 - @delphaber
  9. Function invocation pattern #2 Solution #2 [...] eat: function() {

    function randomAmount() { return Math.floor((Math.random() * this.chocolatesCount) + 1); } this.chocolatesCount -= randomAmount.apply(this); } [...] forrest.eat(); 14 Torino Coding Society 11/04/2016 - @delphaber
  10. Function invocation pattern #2 Solution #3 ( ES5 ) [...]

    eat: function() { var randomAmount = function () { return Math.floor((Math.random() * this.chocolatesCount) + 1); }.bind(this); this.chocolatesCount -= randomAmount(); } [...] forrest.eat(); 15 Torino Coding Society 11/04/2016 - @delphaber
  11. Function invocation pattern #2 Solution #4 ( ES6 ) [...]

    eat: function() { var randomAmount = () => Math.floor((Math.random() * this.chocolatesCount) + 1); this.chocolatesCount -= randomAmount(); } [...] forrest.eat(); 16 Torino Coding Society 11/04/2016 - @delphaber
  12. Contructor invocation pattern function Person(name) { this.name = name; }

    var forrest = new Person("Forrest"); console.log(forrest.name); => "Forrest" 18 Torino Coding Society 11/04/2016 - @delphaber
  13. Apply, Call and Bind1 invocation pattern 1 Actually it doesn't

    invoke, but creates a new function. 19 Torino Coding Society 11/04/2016 - @delphaber
  14. Apply, Call and Bind invocation pattern var forrest = {

    name: 'Forrest', run: function(arg1, arg2) { console.log('Run ' + this.name + ', run!'); } }; var bubba = { name: 'Bubba' }; forrest.run.apply(bubba, ["arg1", "arg2"]); forrest.run.call(bubba, "arg1", "arg2"); var newRun = forrest.run.bind(bubba, "arg1", "arg2"); newRun(); => Run Bubba, run! 20 Torino Coding Society 11/04/2016 - @delphaber
  15. Function scope function init() { var name = "Forrest"; function

    printName() { console.log(name); } printName(); } init(); 22 Torino Coding Society 11/04/2016 - @delphaber
  16. Function scope var x = 10; var y = 20;

    if (true) { var x = 0; console.log("Inner block: " + x); //0 console.log("Inner block: " + y); //20 } console.log("Inner block: " + x); //0 console.log("Inner block: " + y); //20 23 Torino Coding Society 11/04/2016 - @delphaber
  17. Block scope (ES6) var x = 10; let y =

    20; if (true) { let x = 0; console.log("Inner block: " + x); //0 console.log("Inner block: " + y); //20 } console.log("Outer block: " + x); //10 console.log("Outer block: " + y); //20 24 Torino Coding Society 11/04/2016 - @delphaber
  18. Closures In other words, the function defined in the closure

    'remembers' the environment in which it was created. — MDN 26 Torino Coding Society 11/04/2016 - @delphaber
  19. Closure Example function init() { var name = "Forrest"; function

    logName() { console.log(name); } return logName; } var logName = init(); logName(); => "Forrest" 27 Torino Coding Society 11/04/2016 - @delphaber
  20. Use closure to hide implementation var forrest = (function() {

    var privateCounter = 10; return { chocolatesCount: function() { return privateCounter; }, eat: function() { privateCounter -= 1; } }; }()); forrest.eat(); console.log("Chocolates left:", forrest.chocolatesCount()); => "Chocolates left: 9" 28 Torino Coding Society 11/04/2016 - @delphaber
  21. Common mistake with closures var ids = ["div-1", "div-2"]; for(var

    i=0; i < ids.length; i++) { var divId = ids[i]; document.getElementById(divId).onclick = function() { alert("You clicked " + divId); }; } Clicking on div-1: "You clicked div-2" Clicking on div-2: "You clicked div-2" 29 Torino Coding Society 11/04/2016 - @delphaber
  22. Prototype Inheritance function Person(spec) { this.name = spec.name; } Person.prototype.run

    = function() { console.log('Run ' + this.name + ', run!'); }; Person.prototype.citizenship = "Italian"; 31 Torino Coding Society 11/04/2016 - @delphaber
  23. Prototype Inheritance console.log(Person.prototype); Object {citizenship: "Italian"} citizenship: "Italian" constructor: function

    Person(spec) run: function() __proto__: Object constructor: function Object() hasOwnProperty: function hasOwnProperty() isPrototypeOf: function isPrototypeOf() toString: function toString() __proto__ : null ... 32 Torino Coding Society 11/04/2016 - @delphaber
  24. Prototype Inheritance var forrest = new Person({name: "Forrest"}); console.log(forrest.citizenship); //

    "Italian" console.log(forrest.hasOwnProperty("citizenship")); //false forrest.citizenship = "American"; console.log(forrest.citizenship); // "American" console.log(forrest.hasOwnProperty("citizenship")); //true delete forrest.citizenship; console.log(forrest.citizenship); // "Italian" console.log(forrest.hasOwnProperty("citizenship")); //false 34 Torino Coding Society 11/04/2016 - @delphaber
  25. Prototype Inheritance (Complete Example) function Soldier(spec) { Person.call(this, spec); this.weapons

    = spec.weapons || []; } Soldier.prototype = Object.create(Person.prototype); Soldier.prototype.constructor = Soldier; Soldier.prototype.fire = function() { this.weapons.forEach(function(w) { console.log("Fired", w); }); }; var lieutenantDan = new Soldier({name: "Dan", weapons: ["bar42", "beretta"]}); lieutenantDan.run(); //Run Dan, run! lieutenantDan.fire(); //Fired bar42 //Fired beretta 35 Torino Coding Society 11/04/2016 - @delphaber
  26. Prototype Inheritance (Complete Example) console.log(Soldier.prototype) Person {} constructor: function Soldier(spec)

    fire: function() __proto__: Object citizenship: "Italian" constructor: function Person(spec) run: function() __proto__: Object ... 36 Torino Coding Society 11/04/2016 - @delphaber
  27. More good parts in ES6 • Modules (export, import) •

    Destructuring Assignment • Default Parameter Values • Rest Parameter http:/ /es6-features.org/ 37 Torino Coding Society 11/04/2016 - @delphaber
  28. Thanks! • JavaScript: The Good Parts (Douglas Crockford) - http:/

    /www.amazon.it/dp/0596517742 • The Better Parts - https:/ /youtu.be/PSGEjv3Tqo0 • ECMAScript 6 New Features - http:/ /es6- features.org • MDN - https:/ /developer.mozilla.org/en-US/docs/ Web/JavaScript 38 Torino Coding Society 11/04/2016 - @delphaber