píšete JavaScript a najednou si s hrůzou a hrůzou uvědomíte, že jste napsali obrovskou funkci. Stalo se to nejlepším z nás. Nyní přichází téměř nezastavitelné nutkání oddělit funkci na menší kousky.
Velké funkce znamenají spoustu povinností na jednom místě a případně i kód, takže je to dobrý nápad sám o sobě. Ale chcete funkci rozdělit tak, aby neztratila svůj význam ani kontext. Chcete – li to provést, musíte myslet na metodu řetězení-nazývanou také řetězení funkcí. Tento článek vysvětlí, co tím myslím.
předpoklady
než začneme, zde je několik konceptů JavaScriptu, které již potřebujete znát:
- Arrow functions
- Array methods
- asynchronní funkce
nejzkušenější vývojáři budou mít určité zkušenosti s metodami Array
, jako je map, reduce a filter. Pravděpodobně jste již narazili na něco takového:
const food = ;// This type of usage is very commonfood .map(item => item.type) .reduce((result, fruit) => { result.push(fruit); return ; }, );// result:
metoda řetězení se stane, když chcete volat více funkcí pomocí stejného objektu a jeho odkazu. Ve výše uvedeném příkladu metoda pole map
vrací Array
, která má impozantní počet metod.
protože vrátíte odkaz ukazující na Array
, budete mít přístup ke všem vlastnostem Array
. Je to stejný princip, který používáte pro vlastní metodu řetězení.
lepší pochopení tohoto
nebudu pokrývat všechny nuance this
, ale je dobré pochopit, proč this
funguje tak, jak funguje. Bez ohledu na to, jak jste zkušení, Klíčové slovo to může být těžké pochopit. Často je to důvod, proč věci nefungují tak, jak od nich očekáváte.
zde je podstata: this
bude vždy ukazovat na aktuální scope
nebo instanci, odkud je volána. Příklad:
const dog = { is: null, log: () => console.log(this.is), bark() { this.is = "woofing"; this.log(); return this; }, walk() { this.is = "walking"; this.log(); return this; }, eat() { this.is = "eating"; this.log(); return this; }};dog .bark() .eat() .walk();
když píšete funkci, jako je tato (bez slovní hříčky), možná budete chtít řetězové metody, které souvisejí s objektem. Objekt dog
má 3 metody: walk
, bark
a eat
. Pokaždé, když volám některou z jeho funkcí, konzola by měla ukázat reprezentaci toho, co pes dělá v ten pravý okamžik.
ale s tím je problém. Pokud jej spustíte v prohlížeči, zjistíte, že nefunguje podle očekávání. Je to proto, že funkce arrow používají lexikální rozsahy, kde this
odkazuje na okolní rozsah-v tomto případě window
, nikoli na samotný objekt.
abychom to vyřešili, měli bychom použít anonymní volání funkce k reprezentaci vlastnosti log
:
// instead of this: log: () => console.log(this.is),// use this: log() { console.log(this.is); }
nyní bude rozsah this
psa přístupný uvnitř funkce.
pomocí třídy
můžete dosáhnout stejného výsledku pomocí tříd:
class Dog { is = null; log() { console.log(this.is); } bark() { this.is = "woofing"; this.log(); return this; } walk() { this.is = "walking"; this.log(); return this; } eat() { this.is = "eating"; this.log(); return this; }}const dog = new Dog();dog .bark() .eat() .walk();
použití prototypu
pokud musíte použít prototyp, udělejte to tímto způsobem:
function Dog() {}Dog.prototype.is = null;Dog.prototype.log = function() { console.log(this.is);};Dog.prototype.bark = function() { this.is = "woofing"; this.log(); return this;};Dog.prototype.walk = function() { this.is = "walking"; this.log(); return this;};Dog.prototype.eat = function() { this.is = "eating"; this.log(); return this;};const dog = new Dog();dog .bark() .eat() .walk();
A Co Asynchronní Funkce?
async
funkce jsou syntetický cukr pro sliby a generátory. Když deklarujete funkci async
, víte, že vrátí slib. Z tohoto důvodu budete mít také přístup ke všem metodám slibu.
const requests = { user: null, action: null, log(something) { console.log(this); }, async getUser() { this.user = await new Promise(resolve => { setTimeout(() => { resolve("Douglas Pires"); }, 1000); }); this.log("user"); return this; }, async registerAction() { this.action = await new Promise(resolve => { setTimeout(() => { resolve("programming stuff"); }, 1000); }); this.log("action"); return this; }};requests.getUser().then(() => requests.registerAction());
není však dobrý nápad spojit spoustu slibů dohromady. Doporučuji použít spoustu await
klíčových slov. Je to jednodušší a bude váš kód mnohem čitelnější.
await requests.getUser(); // Douglas Piresawait requests.registerAction(); // programming
a zde budete mít přístup ke stejným vlastnostem:
console.log(requests.user); // Douglas Piresconsole.log(requests.action); // programming
na závěr
funkce řetězení se hodí, když musíte manipulovat s objektem. Je to také praktický způsob, jak zlepšit čitelnost vašeho kódu. Nicméně, jak jste viděli výše, měli byste řetěz moudře.
v tomto článku jsme hovořili o this
, třídách, prototypech a async
funkcích v kontextu řetězení javascriptových metod. Doufám, že jste si vybrali několik užitečných tipů a nyní jste o tomto tématu lépe informováni. Můj repozitář se všemi kódy na řetězení metod JavaScriptu najdete zde. Uvidíme se v příštím příspěvku!
užili jste si čtení tohoto článku? Neváhejte sdílet na sociálních médiích pomocí tlačítek níže. Alternativně jsem také psal o tom, jak můžete vytvořit generátor barevných palet pomocí Nuxt a Vuetify. Jdi se na to podívat!