Hrátky s Javascriptem

Funkce vyšších řádů

Martin Polák

github.com/nigol/slides

slides.nigol.cz

Malý kvíz ;)

Co bude v proměnné 'r' po vyhodnocení?

	      
function fun(a) {
  return function(b) {
    return a + b;
  }
}

var r = fun(1);
	      
	    

Správně, r = function(b) {...

Malý kvíz ;)

Jaký je rozdíl mezi:

		    
function fun(a, b) {
  return a + b;
}
		    
		  
		    
var fun = function(a, b) {
  return a + b;
}
		    
		  

Správně, žádný.

Funkce vyšších řádů?

Funkce jsou rovnocenným datovým typem. Můžeme je ukládat do proměnných, předávat jako parametr jiné funkci nebo vracet jako výsledek funkce.

K čemu je to dobré?

  • Přináší další možnost abstrakce.
  • Umožňuje znovupoužitelnost kódu i bez "klasických" OOP technik.
  • Můžeme do jazyka přidat nové konstrukce (např. OOP), aniž bychom museli měnit překladač jazyka.
  • Je to zábava :).
  • ...

Historie

Trocha teorie
(nikoho nezabije)

Lexikální rozsah platnosti

	      
	      function fun(a) {
	        return function(b) {
	          return a + b;
	        }
	      }
	      
	    
Prostředí fun(a)
Proměnné: a
Prostředí function(b)
Proměnné: b

Volné a vázané proměnné

	      
	      function fun(a) {
	        return function(b) {
	          return a + b;
	        }
	      }
	      
	    
  1. Ve funkci fun(a) je pouze vázaná proměnná a.
  2. Ve funkci function(b) je b vázaná proměnná, a je volná.

Volné a vázané proměnné

Prostředí fun(a)
Proměnné: a
Prostředí function(b)
Proměnné: b
a + b;
Vyhodnocení proměnných
  1. Pokud je nalezena proměnná v aktuálním prostředí, použije se její hodnota.
  2. Jinak se hledá v lexikálně nadřazeném prostředí. Pokud je nalezena, použije se její hodnota.
  3. Pokud není proměnná nalezena ani v nadřazených prostředích → chyba.

Volné a vázané proměnné

Důsledky
  • Definice proměnných může být překryta v podřízených prostředích (pozor).
  • Snadné skládání funkcí.
  • Lze provádět statickou analýzu kódu s ohledem na potenciálně problémový obsah proměnných.
  • ...

Trocha praxe
(už vůbec ne)

Skládání funkcí (currying)

Každá funkce s 1 a více parametry se dá přepsat jako složení funkcí s 1 parametrem.

		    
function fun(a, b) {
  return a + b;
}
		    
		  
		    
function fun(a) {
  return function(b) {
    return a + b;
  }
}
		    
		  
Znovupoužitelnost kódu
	      
function calcBuilder(fn) {
  return function(a, b) {
    return fn(a, b);
  }
}

var add = calcBuilder(function(a, b) {
  return a + b;
});

var mul = calcBuilder(function(a, b) {
  return a * b;
});
	      
	    
Návrhové vzory: Interceptor
	      
function funkce() {
  console.log("Logika funkce.");
}

function interc(fn) {
  return function() {
    console.log("Start");
    fn();
    console.log("Stop");
  }
}

var intercepted = interc(funkce);
	      
	    
Asynchronní kód
	      
fetch("https://www.hella.com")
  .then(function(re) {
    return re.text();
  })		
  .then(function(dt) {
    console.log(dt.substring(0, 100));
  });		
	      
	    

Díky za pozornost!