freeCodeCamp/curriculum/challenges/italian/02-javascript-algorithms-an.../functional-programming/understand-the-hazards-of-u...

5.6 KiB

id title challengeType forumTopicId dashedName
587d7b8e367417b2b2512b5d Comprendere i pericoli dell'utilizzo del codice imperativo 1 301241 understand-the-hazards-of-using-imperative-code

--description--

La programmazione funzionale è una buona abitudine. Mantiene il tuo codice facile da gestire e ti salva da bug subdoli. Prima di arrivarci, diamo un'occhiata a un approccio imperativo alla programmazione per evidenziare dove si possono presentare i problemi.

In inglese (e in molte altre lingue), il tempo imperativo viene usato per dare ordini. Allo stesso modo, uno stile imperativo nella programmazione è quello che dà al computer una serie di istruzioni per eseguire un compito.

Spesso le istruzioni cambiano lo stato del programma, ad esempio aggiornando delle variabili globali. Un classico esempio è la scrittura di un ciclo for che dà direttive esatte su come iterare tra gli indici di un array.

Al contrario, la programmazione funzionale è una forma di programmazione dichiarativa. Dici al computer cosa vuoi fare chiamando un metodo o una funzione.

JavaScript offre molti metodi predefiniti che gestiscono le attività comuni in modo da non dover scrivere come il computer dovrebbe eseguirle. Ad esempio, invece di usare il ciclo for menzionato sopra, potresti chiamare il metodo map che gestisce i dettagli di iterazione su un array. Questo aiuta ad evitare errori semantici, come gli errori "Fuori di uno" che sono stati coperti nella sezione Debugging.

Considera lo scenario: stai navigando sul web nel tuo browser e vuoi tracciare le schede che hai aperto. Cerchiamo di modellare questo usando un semplice codice orientato agli oggetti.

Un oggetto Window (finestra) è composto da schede, e di solito hai più di una finestra aperta. I titoli di ogni sito aperto in ogni oggetto Window sono memorizzati in un array. Dopo aver lavorato nel browser (apertura di nuove schede, fusione di finestre e chiusura di schede), desideri visualizzare nella console le schede rimaste aperte. Le schede chiuse vengono rimosse dall'array e le nuove schede vengono aggiunte alla fine (per semplicità).

L'editor di codice mostra un'implementazione di questa funzionalità con funzioni per tabOpen(), tabClose()e join(). L'array tabs è parte dell'oggetto Window che memorizza il nome delle pagine aperte.

--instructions--

Esamina il codice nell'editor. Viene usato un metodo che ha effetti collaterali sul programma, causando un comportamento scorretto. L'elenco finale delle schede aperte, memorizzato in finalTabs.tabs, dovrebbe essere ['FB', 'Gitter', 'Reddit', 'Twitter', 'Medium', 'new tab', 'Netflix', 'YouTube', 'Vine', 'GMail', 'Work mail', 'Docs', 'freeCodeCamp', 'new tab'] ma la lista prodotta dal codice è leggermente differente.

Cambia Window.prototype.tabClose in modo che rimuova la scheda corretta.

--hints--

finalTabs.tabs dovrebbe essere ['FB', 'Gitter', 'Reddit', 'Twitter', 'Medium', 'new tab', 'Netflix', 'YouTube', 'Vine', 'GMail', 'Work mail', 'Docs', 'freeCodeCamp', 'new tab']

assert.deepEqual(finalTabs.tabs, [
  'FB',
  'Gitter',
  'Reddit',
  'Twitter',
  'Medium',
  'new tab',
  'Netflix',
  'YouTube',
  'Vine',
  'GMail',
  'Work mail',
  'Docs',
  'freeCodeCamp',
  'new tab'
]);

--seed--

--seed-contents--

// tabs is an array of titles of each site open within the window
const Window = function(tabs) {
  this.tabs = tabs; // We keep a record of the array inside the object
};

// When you join two windows into one window
Window.prototype.join = function(otherWindow) {
  this.tabs = this.tabs.concat(otherWindow.tabs);
  return this;
};

// When you open a new tab at the end
Window.prototype.tabOpen = function(tab) {
  this.tabs.push('new tab'); // Let's open a new tab for now
  return this;
};

// When you close a tab
Window.prototype.tabClose = function(index) {

  // Only change code below this line

  const tabsBeforeIndex = this.tabs.splice(0, index); // Get the tabs before the tab
  const tabsAfterIndex = this.tabs.splice(index + 1); // Get the tabs after the tab

  this.tabs = tabsBeforeIndex.concat(tabsAfterIndex); // Join them together

  // Only change code above this line

  return this;
 };

// Let's create three browser windows
const workWindow = new Window(['GMail', 'Inbox', 'Work mail', 'Docs', 'freeCodeCamp']); // Your mailbox, drive, and other work sites
const socialWindow = new Window(['FB', 'Gitter', 'Reddit', 'Twitter', 'Medium']); // Social sites
const videoWindow = new Window(['Netflix', 'YouTube', 'Vimeo', 'Vine']); // Entertainment sites

// Now perform the tab opening, closing, and other operations
const finalTabs = socialWindow
  .tabOpen() // Open a new tab for cat memes
  .join(videoWindow.tabClose(2)) // Close third tab in video window, and join
  .join(workWindow.tabClose(1).tabOpen());
console.log(finalTabs.tabs);

--solutions--

const Window = function(tabs) {
  this.tabs = tabs;
};

Window.prototype.join = function(otherWindow) {
  this.tabs = this.tabs.concat(otherWindow.tabs);
  return this;
};

Window.prototype.tabOpen = function(tab) {
  this.tabs.push('new tab');
  return this;
};

Window.prototype.tabClose = function(index) {
  const tabsBeforeIndex = this.tabs.slice(0, index);
  const tabsAfterIndex = this.tabs.slice(index + 1);

  this.tabs = tabsBeforeIndex.concat(tabsAfterIndex);
  return this;
 };

const workWindow = new Window(['GMail', 'Inbox', 'Work mail', 'Docs', 'freeCodeCamp']);
const socialWindow = new Window(['FB', 'Gitter', 'Reddit', 'Twitter', 'Medium']);
const videoWindow = new Window(['Netflix', 'YouTube', 'Vimeo', 'Vine']);

const finalTabs = socialWindow
  .tabOpen()
  .join(videoWindow.tabClose(2))
  .join(workWindow.tabClose(1).tabOpen());