<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>Forem: mpodlasin</title>
    <description>The latest articles on Forem by mpodlasin (@mpodlasin).</description>
    <link>https://forem.com/mpodlasin</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F444444%2Fef88b85a-07f5-471a-9938-8236dea9d98d.png</url>
      <title>Forem: mpodlasin</title>
      <link>https://forem.com/mpodlasin</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://forem.com/feed/mpodlasin"/>
    <language>en</language>
    <item>
      <title>1 Month Vim Only Challenge - Week 4 (Finale)</title>
      <dc:creator>mpodlasin</dc:creator>
      <pubDate>Sun, 21 Nov 2021 15:52:29 +0000</pubDate>
      <link>https://forem.com/mpodlasin/1-month-vim-only-challenge-week-4-finale-5dhg</link>
      <guid>https://forem.com/mpodlasin/1-month-vim-only-challenge-week-4-finale-5dhg</guid>
      <description>&lt;p&gt;This is the last article in my vim miniseries.&lt;/p&gt;

&lt;p&gt;For the last month, I've been doing a "1 Month Vim Only Challenge", where I forced myself to use vim for 1 month, both in my free time as well as at work.&lt;/p&gt;

&lt;p&gt;In the previous articles, I was telling you about the &lt;a href="https://mpodlasin.com/articles/vim-challenge-kickoff"&gt;reasons&lt;/a&gt; why I started the challenge in the first place. I was also &lt;a href="https://mpodlasin.com/articles/vim-week-i"&gt;relating&lt;/a&gt; my &lt;a href="https://mpodlasin.com/articles/vim-weeks-ii-and-iii"&gt;experiences&lt;/a&gt; while doing the challenge.&lt;/p&gt;

&lt;p&gt;And now the challenge comes to an end, as the fourth week of using vim ends. As I've said in the first article, this means that it is time for me to make the ultimate decision:&lt;/p&gt;

&lt;p&gt;After using vim, and vim only, for 1 month straight, do I want to go back to using a "regular" editor/IDE like VSCode? Was using vim an unbearable experience? Do I look forward to never having to press &lt;code&gt;:wq&lt;/code&gt; ever again?&lt;/p&gt;

&lt;p&gt;Or did I fall in love with vim so much that I plan to use it for the rest of my life? Does using a mouse cause nausea in me now? Do I want to keep my fingers in the home row even if my room is on fire?&lt;/p&gt;

&lt;p&gt;Well, let's not keep you on the edge of your seat anymore. Time to give you...&lt;/p&gt;

&lt;h3&gt;
  
  
  The Answer
&lt;/h3&gt;

&lt;p&gt;I... I have no idea.&lt;/p&gt;

&lt;p&gt;No, seriously. You would think that after 1 month I would be leaning strongly towards one side or another. That's what I thought back then as well.&lt;/p&gt;

&lt;p&gt;The thing is that if you are trying to replicate - let's say - VSCode setup, vim will get you to like 90% or 95%. Meaning that it will mostly work nicely and flawlessly. But there will still be 5% to 10% of little annoyances, awkward UI/UX, or tiny bugs. Nothing major, nothing that would block you from doing the actual job done. But still enough for me to think with reverence about VSCode from time to time.&lt;/p&gt;

&lt;p&gt;On the other hand, you &lt;em&gt;are&lt;/em&gt; getting very real benefits with vim. The minimalism of the setup (my .vimrc is still tiny and I love it). How lightweight vim is. How just absurdly configurable and extendable it is. &lt;/p&gt;

&lt;p&gt;I guess if I were to summarise the benefits of vim in one sentence, it would be this: &lt;/p&gt;

&lt;p&gt;You can truly make vim your own. &lt;/p&gt;

&lt;p&gt;You can have two people using vim and their setup would be completely different. You could have a minimalist, distraction-free setup with only bare necessities installed. And at the same time, you could turn vim into the craziest, most robust, multiwindow IDE packed with many, many features, including your own, custom functionalities, coded in the vim scripting language.&lt;/p&gt;

&lt;p&gt;So if I am to make a rational decision of whether I should stick to using vim, I have to answer the question do the benefits of vim outweigh for me this 5-10% of awkwardness that it has compared to VSCode.&lt;/p&gt;

&lt;p&gt;And at this point, I really don't feel equipped to answer this question.&lt;/p&gt;

&lt;h3&gt;
  
  
  It Has To Feel Natural
&lt;/h3&gt;

&lt;p&gt;In the first article of the series, I wrote that the main criterion for me will be "Does coding in vim feel natural to me now?"&lt;/p&gt;

&lt;p&gt;But this also turned out to be more difficult to answer than I initially expected.&lt;/p&gt;

&lt;p&gt;The thing is that most of the time it does feel natural. But then you also encounter those moments when you want to do something that would be trivial in VSCode and... you realize you are using vim. You have to google for a key that does what you want. Or you have to start looking for a plugin that has the desired functionality. Or - in the most extreme cases - you realize that you have to write a little script in the vim scripting language, or at the very least copy someone's script from stack overflow.&lt;/p&gt;

&lt;p&gt;Now, again, those moments happen relatively rarely, especially as you keep progressing in your vim journey. But they do happen nevertheless, so I cannot say that using vim is completely natural for me at this point. I still have this slight anxiety that I will start working on a task at my day job and I will have troubles, because something will turn out to be difficult, or at least awkward, in vim.&lt;/p&gt;

&lt;p&gt;But on the other hand, most of the time I don't think about the fact that I am using vim at all. Most of the time it &lt;em&gt;is&lt;/em&gt; natural. Vim's controls feel very straightforward at this point. This is ironic because controls are probably the thing that scares people the most from using vim. For me, it really wasn't an issue at all. Even with knowing just the most basic commands, you can get a lot done. And it only gets better as you continue to use the editor.&lt;/p&gt;

&lt;p&gt;So, to summarise, even the criterium of "feeling natural" can't push me towards an ultimate decision. On some level, it feels incredibly natural, on some level it doesn't.&lt;/p&gt;

&lt;h3&gt;
  
  
  So?
&lt;/h3&gt;

&lt;p&gt;Well, but I have to make a decision, don't I?&lt;/p&gt;

&lt;p&gt;Yes. And I will.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;I am sticking with vim for now.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;From what I've written so far, it is not an "unquestionable win" for vim though. I still have lots of doubts, lots of issues to solve, lots of awkward spots to go through.&lt;/p&gt;

&lt;p&gt;I am however willing to give vim a few more weeks of a "trial period" because there was indeed lots of stuff that vim impressed me with.&lt;/p&gt;

&lt;p&gt;So I'll continue to use it, but not in a "challenge" mode anymore. If I encounter any issues that stop me from doing actual work or slow me down considerably, I will not be afraid to reinstall VSCode. It's important to note that VSCode does have an extension allowing you to use vim controls. So I might go in this direction at some point.&lt;/p&gt;

&lt;p&gt;Turning "using vim" into a challenge was a great idea because otherwise, I would bail out much, much earlier.&lt;/p&gt;

&lt;p&gt;But on the other hand, it stops me to evaluate things objectively, because I am literally forcing myself to use it. I plan now to stop forcing myself. I will just continue to use it if I feel like it. And after a few months, it will be clear if it actually won my heart over or not.&lt;/p&gt;

&lt;h3&gt;
  
  
  Final Words
&lt;/h3&gt;

&lt;p&gt;So this is how I am finishing my little "1 Month Vim Only Challenge" article series.&lt;/p&gt;

&lt;p&gt;I know that this is a slightly disappointing finale, where I failed to provide you more definite answers.&lt;/p&gt;

&lt;p&gt;But I hope that this gives you a good idea of what to expect when getting into vim.&lt;/p&gt;

&lt;p&gt;You will likely be pleasantly surprised, but not immediately won over at the same time. Whether you decide to stick with vim will be largely dependent on your personal preferences, style of work, what kind of tooling do you need, etc.&lt;/p&gt;

&lt;p&gt;Me personally, even though I am still not sure if I will continue to use vim forever, I definitely don't regret participating in this little challenge. It showed me how mature vim community and vim tooling are. It showed me that you are not insane if you are using vim on a daily basis. It's much closer to VSCode experience than you might initially think.&lt;/p&gt;

&lt;p&gt;And even if I decide to go back to VSCode at some point, I always have vim knowledge and experience under my belt. And there might be some moments when it could turn out to be helpful, if not necessary. Editing stuff over ssh for example. Or if they fire me and I will have to sell my MacBook and go back to coding on my ancient ThinkPad that can barely handle running VSCode...&lt;/p&gt;

&lt;p&gt;Anyways. I hope you enjoyed this little series and I encourage you to try the same thing on your own. You might get surprised how much you will enjoy working in vim!&lt;/p&gt;

&lt;p&gt;Cover Photo by &lt;a href="https://unsplash.com/@rockthechaos?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;Kolleen  Gladden&lt;/a&gt; on &lt;a href="https://unsplash.com/s/photos/finish-line?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;Unsplash&lt;/a&gt;&lt;/p&gt;

</description>
      <category>vim</category>
      <category>productivity</category>
      <category>watercooler</category>
      <category>programming</category>
    </item>
    <item>
      <title>1 Month Vim Only Challenge - Weeks 2 and 3</title>
      <dc:creator>mpodlasin</dc:creator>
      <pubDate>Mon, 15 Nov 2021 10:38:42 +0000</pubDate>
      <link>https://forem.com/mpodlasin/1-month-vim-only-challenge-weeks-2-and-3-3bcl</link>
      <guid>https://forem.com/mpodlasin/1-month-vim-only-challenge-weeks-2-and-3-3bcl</guid>
      <description>&lt;p&gt;This article is part of my series "1 Month Vim Only Challenge", where I force myself to use vim for 1 month and, at the same time, create articles talking about my progress, challenges, and frustrations.&lt;/p&gt;

&lt;p&gt;You can read the two previous articles &lt;a href="https://mpodlasin.com/articles/vim-challenge-kickoff"&gt;here&lt;/a&gt; and &lt;a href="https://mpodlasin.com/articles/vim-week-i"&gt;here&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Note that this article is not a tutorial or anything like that. It's just a collection of my purely subjective experiences while doing the challenge.&lt;/p&gt;

&lt;h3&gt;
  
  
  Crisis in Vim City
&lt;/h3&gt;

&lt;p&gt;The two previous articles in the series were very optimistic. I was motivated to do the challenge and the first week went shockingly smooth.&lt;/p&gt;

&lt;p&gt;However, it's probably not a surprise that in the second and third weeks everything started becoming more challenging. Energy and attitude from the first week slowly disappeared. I lost my rose-colored glasses and started noticing more and more problems with my workflow and setup.&lt;/p&gt;

&lt;p&gt;The thing is, the two past weeks were extremely busy for me, both at work as well as in private life. At work, we are getting close to finishing an important project, so I had to stay focused on that. And on top of that, I decided to travel to Turkey for one week, in order to meet my coworkers.&lt;/p&gt;

&lt;p&gt;Lack of free time, combined with pressures of delivering the project, made using vim very difficult for me. In fact, I was close to giving up multiple times. The only thing that stopped me was the fact that I framed this whole thing as a "challenge".&lt;/p&gt;

&lt;p&gt;I didn't do that by accident when I was starting this series. I knew that there will be moments when using vim will become difficult, especially at work. So I decided to do it as a challenge, in order to literally force myself to go through the toughest times.&lt;/p&gt;

&lt;p&gt;And it worked. As of now, I still haven't reinstalled VSCode and haven't used it even once. Yes, I am still writing this article in vim.:w&lt;/p&gt;

&lt;p&gt;So what exactly were the problems? Let's mention some stuff, in no particular order.&lt;/p&gt;

&lt;h3&gt;
  
  
  Working On Multiple Files
&lt;/h3&gt;

&lt;p&gt;For the longest time, I didn't know that vim has tabs functionality. I just used windows, which splits your view into multiple subwindows, effectively giving each file less and less space on the screen.&lt;/p&gt;

&lt;p&gt;In the beginning, using windows was good enough for me. However, even this simple setup was awkward, because default keyboard shortcuts to navigate between windows are very, very uncomfortable. Pressing &lt;code&gt;Ctrl+W&lt;/code&gt; while staying in the home row gives a solid stretch to your fingers... Try it!&lt;/p&gt;

&lt;p&gt;Currently, I am trying to force myself to use tabs more. They are much better than windows - including better navigation shortcuts. And yet, for some bizarre reason, I still fall back to using windows again and again. I am not sure why.&lt;/p&gt;

&lt;p&gt;Maybe it's the weird way directories are abbreviated in the name of the tab? Or the fact that the project tree disappears when you open a new tab because it operates on a tab per-tab basis?&lt;/p&gt;

&lt;p&gt;Or perhaps, like most things in vim, it's really just a matter of getting used to. But as it stands, I still do feel a certain "awkwardness" when working with projects that require me to have multiple files open at the same time.&lt;/p&gt;

&lt;h3&gt;
  
  
  Navigating Large Projects
&lt;/h3&gt;

&lt;p&gt;NERDTree, which I am using as my filesystem tree plugin, is very pleasant to work with and well documented. However, I still find it awkward to use the keyboard for navigating large directory structures. I believe I was much faster with a mouse.&lt;/p&gt;

&lt;p&gt;To give you some context, the repositories I am currently working in can be massive. Those are often monorepos, containing multiple separate packages.&lt;/p&gt;

&lt;p&gt;Perhaps this is just a matter of time, but for now, I feel that this way of navigating files inhibits me, &lt;em&gt;especially&lt;/em&gt; when I have to find a file fast.&lt;/p&gt;

&lt;p&gt;What would help me would be also some kind of global file search. Vim has some built-in stuff for that, like &lt;code&gt;:grep&lt;/code&gt; command, but... I never really got it to work. &lt;/p&gt;

&lt;p&gt;And even if I did, the UX of that command is frankly horrible, requiring you to type the command with a searched phrase &lt;em&gt;and then&lt;/em&gt; type a second command, which shows you the search results. Why? Just give me a command where I can write something like &lt;code&gt;:gs "some searched term"&lt;/code&gt; and see all the results immediately, preferably with a "jump to file" functionality.&lt;/p&gt;

&lt;p&gt;Now, I have seen some plugins doing that, which looked extremely promising, but the installation and/or setup turned out to be a bit trickier than I expected. So this is also something I would have to devote some time to.&lt;/p&gt;

&lt;h3&gt;
  
  
  Working With TS Tooling
&lt;/h3&gt;

&lt;p&gt;In the last article, I was very positive about the TypeScript tooling that I started using.&lt;/p&gt;

&lt;p&gt;However, I started discovering some limitations fairly quickly. Those limitations led me to install another plugin - &lt;a href="https://github.com/neoclide/coc.nvim"&gt;coc.nvim&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;This extension is very interesting because it promises to "Make your Vim/Neovim as smart as VSCode."&lt;/p&gt;

&lt;p&gt;It's a more general plugin, that - rather than supporting a single language or functionality - allows you to extend vim in a very similar way as you would extend VSCode. As far as I understand it, underneath it uses the same tooling that VSCode uses. Because of that, support for - let's say - TypeScript is virtually the same in vim and VSCode. Autocomplete works the same way, autoimports work the same way, etc.&lt;/p&gt;

&lt;p&gt;This is an amazing idea because it utilizes the great and battle-tested work that was already done for VSCode.&lt;/p&gt;

&lt;p&gt;As I've said, the installation itself is very simple. But - as the authors of the extension themselves recommend - you still have to do some keybindings configuration, in order to get the most out of it.&lt;/p&gt;

&lt;p&gt;Because of that, I still don't really know how to achieve certain results using this plugin. I don't know for example how to check the inferred type of an expression. I also have trouble with identifying if my file has currently any TS errors because it is presented on a per-line basis and I can't see all the lines in the file at the same time.&lt;/p&gt;

&lt;p&gt;Funnily enough, I still have the previous TS plugin installed. Mostly because I got used to how well some stuff worked there. On the flip side, the plugin started acting crazy in some (admittedly rare) cases. Presumably, because it didn't successfully detect which TypeScript version I am using in each package of the multirepo (?).&lt;/p&gt;

&lt;p&gt;So even though both of those tools are very impressive and mature, even here I will have to do additional work of learning and configuring stuff, in order to make the workflow perfect.&lt;/p&gt;

&lt;h3&gt;
  
  
  Working With Eslint
&lt;/h3&gt;

&lt;p&gt;There are still more things that I need to somehow solve. Because at work we are working on a pretty big multirepo, even the linting command runs very long. Of course most of my coworkers mitigate that by using a VSCode with an extension that lints a specific file during editing.&lt;/p&gt;

&lt;p&gt;There exist of course some vim (or coc.nvim!) plugins that do the same thing, I just didn't put aside some time to try one out. &lt;/p&gt;

&lt;p&gt;And my fear - based on the TypeScript plugins that I talked about - would be that even after installation, I would have to do some additional configuration work just to make everything work seamlessly.&lt;/p&gt;

&lt;h3&gt;
  
  
  Yes, It's All My Fault
&lt;/h3&gt;

&lt;p&gt;At this point, I know what you are thinking. "Well, what's the problem? You just have to properly set up the plugins or add new ones and everything will work just as you would like it!".&lt;/p&gt;

&lt;p&gt;And that's true. It's all my fault. But that's exactly the whole point of my article. If I had even a little bit of free time, setting up the workflow with vim would be simply fun.&lt;/p&gt;

&lt;p&gt;But when you have to balance work and private life at the same time, it's surprisingly difficult to devote even twenty minutes to set up a particular plugin.&lt;/p&gt;

&lt;p&gt;What keeps happening is that I start setting something up - say, I install a specific plugin. But then there is still a some configuration that I should do. And how to configure those plugins is often a bit poorly documented &lt;em&gt;and/or&lt;/em&gt; just simply looks intimidating for a newcomer.&lt;/p&gt;

&lt;p&gt;This makes it difficult to assess how long a certain configuration will take. It might be a breeze and take ten minutes, or it might turn out that things are more complex than expected, and you will have to spend a whole day, trying to get some plugin to work.&lt;/p&gt;

&lt;p&gt;And yes, &lt;em&gt;I know&lt;/em&gt; that most of the time, it will just take ten to twenty minutes. Those plugins are well maintained and have solid communities behind them. But when you have tasks at work that you need to execute ASAP, it's super difficult to make a rational decision and devote some time to configure your tooling.&lt;/p&gt;

&lt;p&gt;On top of that, this ten to twenty minutes involves only one plugin. And, as you've seen before, I have problems involving at least few of them. So it would take me even more time to configure everything the way I'd like to.&lt;/p&gt;

&lt;p&gt;The ultimate point here is simple - if you are going to take a deep dive into vim, make sure that you have enough free time to really learn and configure it properly. If you reserve some time, this process will be much more enjoyable. But if you are speeding through plugin documentation, because you have work that needs to get done, using vim might become challenging, and simply unpleasant.&lt;/p&gt;

&lt;p&gt;It just isn't a "plug and play" tool. It gives you lots of freedom regarding configurability, remapping keybindings, etc. But this power comes also with a more demanding setup process.&lt;/p&gt;

&lt;p&gt;With great power comes great responsibility, I guess.&lt;/p&gt;

&lt;h3&gt;
  
  
  PS
&lt;/h3&gt;

&lt;p&gt;It is now the end of the weekend, as I am writing this last paragraph.&lt;/p&gt;

&lt;p&gt;Just to be fair to the vim community, I need to mention that I have finally set aside some time to do more configuration work. &lt;/p&gt;

&lt;p&gt;Most of the problems I've mentioned were easily solvable. It took me not more than 2 hours to solve around 80% of my issues&lt;/p&gt;

&lt;p&gt;So the fear and anxiety were mostly unwarranted.&lt;/p&gt;

&lt;p&gt;This however further emphasizes my ultimate point of the article - make sure to set aside some time devoted to configuring your vim setup. Don't tell yourself that you will "do it during work hours" etc. Devote solid 2, 3 hours in the week and put actual effort into reading docs and figuring out how the tooling works.&lt;/p&gt;

&lt;p&gt;This will make using vim during actual work hours much more seamless and pleasant.&lt;/p&gt;

&lt;p&gt;Cover Photo by &lt;a href="https://unsplash.com/@tjump?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;Nik Shuliahin&lt;/a&gt; on &lt;a href="https://unsplash.com/s/photos/sad?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;Unsplash&lt;/a&gt;&lt;/p&gt;

</description>
      <category>vim</category>
      <category>watercooler</category>
      <category>productivity</category>
      <category>programming</category>
    </item>
    <item>
      <title>1 Month Vim Only Challenge - Week 1</title>
      <dc:creator>mpodlasin</dc:creator>
      <pubDate>Sun, 31 Oct 2021 07:13:58 +0000</pubDate>
      <link>https://forem.com/mpodlasin/1-month-vim-only-challenge-week-1-355h</link>
      <guid>https://forem.com/mpodlasin/1-month-vim-only-challenge-week-1-355h</guid>
      <description>&lt;p&gt;It's currently Saturday. &lt;/p&gt;

&lt;p&gt;Exactly one week ago I have started my &lt;a href="https://twitter.com/search?q=%231MonthVimOnlyChallenge"&gt;#1MonthVimOnlyChallenge&lt;/a&gt;. I removed all other editors/IDEs from my computer and I forced myself to use vim for exactly 1 month, documenting my journey on the way. I plan to write short  weekly articles and I am posting regular updates on my &lt;a href="https://twitter.com/m_podlasin"&gt;Twitter&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Let's answer the big questions first.&lt;/p&gt;

&lt;p&gt;Did I give up? Nope.&lt;/p&gt;

&lt;p&gt;Am I still writing this article in vim? Absolutely!:w&lt;/p&gt;

&lt;p&gt;Am I enjoying myself? 100 percent!!!&lt;/p&gt;

&lt;p&gt;In the article, I will summarize my various observations regarding using vim on a daily basis. This is not a tutorial, not a guide, just some random thoughts and feelings, in more or less random order.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Setup
&lt;/h2&gt;

&lt;p&gt;Probably the most surprising thing for me is that my setup is still fairly simple. I do plan to complicate it in the following week, to challenge myself a bit, but what I currently have already allowed me to be productive, even at my day job.&lt;/p&gt;

&lt;p&gt;This is probably the moment where everyone expects me to show off my vim config. And I could to that, but there isn't really a point. The config is literally just a few lines. It just enables a few basic options, like syntax highlighting, showing line numbers, etc. Nothing beyond your standard "Write Your Own Vim Config" articles, that you can find hundreds of online.&lt;/p&gt;

&lt;p&gt;Plugins are, I feel, more interesting. Without the plugins, vim is really just a basic text editor, even though it does have some built-in handling for languages like C, Java, and even JavaScript. However, my first attempts to open a TypeScript file without any plugins, literally hanged the vim window, presumably because syntax highlighting got very, very confused.&lt;/p&gt;

&lt;p&gt;This immediately went away after I've installed &lt;a href="https://github.com/leafgarland/typescript-vim"&gt;typescript-vim&lt;/a&gt;, which provides syntax highlighting and other basic handling of TypeScript files. This immediately made vim work great with my TypeScript projects.&lt;/p&gt;

&lt;p&gt;The installation of plugins is extremely easy. Essentially you just have to do a &lt;code&gt;git clone&lt;/code&gt; into a proper directory and you are done! This seems to be a new-ish thing, introduced in vim 8. You can see that plugins still support various "vim plugin managers", which tells me that back in the day installing and managing those plugins was a huge pain in the ass. Now it's luckily trivial.&lt;/p&gt;

&lt;p&gt;Finding the plugins is also easy. I just googled "vim typescript" and immediately saw links to GitHub repos.&lt;/p&gt;

&lt;p&gt;typescript-vim plugin only gives you basic capabilities - it doesn't include autocompletion, type-checking inside the file, etc. That's where &lt;a href="https://github.com/Quramy/tsuquyomi"&gt;tsuquyomi&lt;/a&gt; comes in. It promises that it will "make your vim a TypeScript IDE". I am not sure if I would go &lt;em&gt;that&lt;/em&gt; far, but it does give you many capabilities that you expect in a modern TS editor - autocomplete, navigation to type definitions, compilation errors that appear in the file, etc.&lt;/p&gt;

&lt;p&gt;Functionally this stuff allows you to do the same things you would do in VSCode, but bear in mind that the UI/UX is... well... not as streamlined.&lt;/p&gt;

&lt;p&gt;I don't know who decided that triggering autocomplete menu should be done by pressing &lt;code&gt;Ctrl+X&lt;/code&gt; &lt;em&gt;and then&lt;/em&gt; &lt;code&gt;Ctrl+O&lt;/code&gt;. It's the least friendly and effective keyboard shortcut I could think of. Once you get used to it, it's not horrible, but next week I will almost for sure look into remapping that.&lt;/p&gt;

&lt;p&gt;On the other hand, I love how "go to definition" functionality is handled, where &lt;code&gt;Ctrl+]&lt;/code&gt; immediately takes you to the definition of an expression you are currently pointing at with your cursor. And then &lt;code&gt;Ctrl+t&lt;/code&gt; immediately takes you back to the exact place where you pressed &lt;code&gt;Ctrl+]&lt;/code&gt;. This makes navigating TS files fast, pleasant, and efficient.&lt;/p&gt;

&lt;p&gt;There is also some stuff that is lacking, or at the very least I still don't know how to do it yet.&lt;/p&gt;

&lt;p&gt;I still don't know how to see the inferred type of expression I am hovering over. I tried googling that, but I've seen some intimidating answers, mentioning stuff like &lt;code&gt;coc.nvim&lt;/code&gt; etc. So I gave up back then but I plan to go back to it soon.&lt;/p&gt;

&lt;p&gt;Also, I don't know how to do autoimports. Autoimport is a feature that frankly changed my life a few years ago. I could just type in the name of the value/class/interface/whatever and proper import would automagically appear at the top of the file. I want that, I need that, so this week I will attempt to research that as well.&lt;/p&gt;

&lt;h2&gt;
  
  
  Limitation Is A Blessing
&lt;/h2&gt;

&lt;p&gt;Apart from what I've mentioned above, I have also installed &lt;a href="https://github.com/preservim/nerdtree"&gt;NERDTree&lt;/a&gt;, which is a plugin for navigating directories and files. &lt;/p&gt;

&lt;p&gt;And I also started experimenting with some Haskell/PureScript stuff, but this is at an earlier stage because I am doing that only in my free time, outside of work.&lt;/p&gt;

&lt;p&gt;Oh, and I also have &lt;a href="https://github.com/cocopon/iceberg.vim"&gt;iceberg&lt;/a&gt; color scheme installed, because the default syntax highlighting colors are a bit too flamboyant for my taste.&lt;/p&gt;

&lt;p&gt;But other than that - this is it! I have nothing more so far. And this simple setup - a few lines of vim config, 3 plugins (in my day job), and 1 color scheme - already get me like 80% to where I would like to be. I am kind of expecting that getting from 80% to 90% will be more difficult than getting from 0% to 80%, but we will see next week.&lt;/p&gt;

&lt;p&gt;And quite frankly, limitations can be sometimes good. I still remember my CS professor, who used to discourage us from using syntax highlighting. He claimed that it made us dumber, and stopped us from actively thinking about the syntax. I don't know how much truth was in that in the end, but I did notice, that certain limitations of vim forced me to think more during coding. This especially relates to navigating large projects, working concurrently on multiple files, and writing imports by hand. &lt;/p&gt;

&lt;p&gt;1 week is not a long time and I do plan to improve those aspects of my vimming in the following days. However, if I didn't, I wouldn't be surprised if, over a longer period of time, those limitations would give me a better understanding of the layout of my projects. Where certain files and modules are stored, how they relate to each other, how the dependency tree looks like etc.&lt;/p&gt;

&lt;p&gt;It's kind of like using Grammarly for writing, which is helping me on a daily basis, but also tanking my actual writing skills, because I am using my brain less.&lt;/p&gt;

&lt;h2&gt;
  
  
  This Hurts!
&lt;/h2&gt;

&lt;p&gt;After the first 2 days of the vim challenge, I started having pronounced wrist pains. This scared the sh** out of me.&lt;/p&gt;

&lt;p&gt;I was having similar pains before, but using vim seemed to aggravate it. Not surprising really, when you think about it. Vim forces you to stay in the home row more and reach for the mouse less.&lt;/p&gt;

&lt;p&gt;I am quite confused at this point because the mantra of touch-typing is "stay in the home row". But the issues I had made apparent that reaching for the mouse, or changing hands position from time to time is actually a good thing - it allows you to relax your muscles for a bit, instead of constantly staying in the same, a bit strenuous, position. &lt;/p&gt;

&lt;p&gt;Contrargument here would be of course that the home row position shouldn't be strenuous at all. You either have to change your technique or setup in order to make sure that's the case.&lt;/p&gt;

&lt;p&gt;Now, this of course is not an issue with the vim itself. Quite the opposite, vim helped me identify that the ergonomics of my writing are still suboptimal.&lt;/p&gt;

&lt;p&gt;Luckily the pains didn't really appear after those first two days. If they do, however, I am planning on trying out a split keyboard. I wanted to do that for the longest time now, and perhaps vim will push me to finally do it.&lt;/p&gt;

&lt;p&gt;And I want to see people's faces in a cafe, where I take out this bizarre keyboard and turn on a program that looks like a hacker's console. I am half expecting them to turn on VPNs at this point or something.&lt;/p&gt;

&lt;h2&gt;
  
  
  Vimming In Vim
&lt;/h2&gt;

&lt;p&gt;Let's talk a bit about using vim itself. So far I was mostly touching on tangential topics like setup etc.&lt;/p&gt;

&lt;p&gt;But how does it feel, to use vim, with its bizarre user interface, daily, including work?&lt;/p&gt;

&lt;p&gt;Not bad actually. Bear in mind, I've already used vim during my university days, so the learning curve was much, &lt;em&gt;much&lt;/em&gt; lower for me this time.&lt;/p&gt;

&lt;p&gt;I just did some basic tutorials on the weekend, which they are plenty of out there. Many of them are interactive and/or involve some gamification aspect, which made the whole "relearning" process engaging and fun.&lt;/p&gt;

&lt;p&gt;Vim has two basic modes - regular and insert. And I've noticed that, when using vim, my brain also works in two different modes, depending on the situation.&lt;/p&gt;

&lt;p&gt;In a "regular" mode, I am simply working, not thinking much about the fact that I am currently using vim. Reaching this stage is actually much, much easier than you would expect. I think that people really overblow how complex basic vimming is. If you can wrap your head around using "WASD" for playing video games, you will equally easily switch to "HJKL" for navigating a text file.&lt;/p&gt;

&lt;p&gt;The second mode is what I call a "golf" mode. Those are moments, where I actually slow down and attempt to do something in a smarter, more terse way. Those are fun little challenges throughout the day, that can break you out from the monotony of constant, mindless coding. &lt;/p&gt;

&lt;p&gt;And the best thing about this is that slowly, over time, golf mode skills are bleeding over to a regular mode. You start using certain techniques and shortcuts more and more often until they become second nature and a part of your regular mode arsenal.&lt;/p&gt;

&lt;p&gt;It really works just amazing and it gives you a real promise of becoming, over time, more and more efficient in coding.&lt;/p&gt;

&lt;p&gt;I guess the only problem here for me is that - especially in my day job - I find myself not going into the golf mode nearly enough. When there is a pressure of finishing tasks, fixing bugs, and delivering sprints it can be hard to allow yourself for a relaxing golfing break. But this is, again, a me problem rather than a vim problem.&lt;/p&gt;

&lt;p&gt;Apart from that, I believe that working in those two modes really can make you faster and more efficient over time.&lt;/p&gt;

&lt;h2&gt;
  
  
  Vim Anxiety
&lt;/h2&gt;

&lt;p&gt;During this week I've posted a joke on Twitter. I have written: &lt;/p&gt;

&lt;p&gt;"If you want to get a promotion, using vim is the best way. It discourages you from writing code, so you start doing more managerial and executive tasks."&lt;/p&gt;

&lt;p&gt;And although I wrote this as a joke, it wasn't by accident. There is a (quite substantial) grain of truth in that.&lt;/p&gt;

&lt;p&gt;I really did notice myself doing much more code reviews, research, and general "managerial" tasks. And I quickly realized that this is simply due to "vim anxiety". Even though on a logical level I know I can use vim and perform basically any task in it, I still have this thought at the back of my head, telling me that it will be unpleasant, awkward, and more difficult, compared to if I was using the good old VSCode.&lt;/p&gt;

&lt;p&gt;I've also noticed that I am scared of doing pair programming where I show people my editor. You know this effect - when people are looking at your hands, suddenly your brain starts working at 5% of usual capacity. So imagine using vim &lt;em&gt;and&lt;/em&gt; having people look at your monitor. This would be probably the most challenging thing imaginable.&lt;/p&gt;

&lt;p&gt;And funnily enough, I will probably &lt;em&gt;have to&lt;/em&gt; do it this week, because I pledged to my coworkers that I will prepare some kind of tutorial for them...&lt;/p&gt;

&lt;p&gt;So... wish me luck! Next week I will tell you how it all went.&lt;/p&gt;

&lt;p&gt;Cover Photo by &lt;a href="https://unsplash.com/@slmnbj?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;Salmen Bejaoui&lt;/a&gt; on &lt;a href="https://unsplash.com/s/photos/trekking?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;Unsplash&lt;/a&gt;&lt;/p&gt;

</description>
      <category>vim</category>
      <category>productivity</category>
      <category>watercooler</category>
      <category>programming</category>
    </item>
    <item>
      <title>1 Month Vim Only Challenge - The Whats and The Whys</title>
      <dc:creator>mpodlasin</dc:creator>
      <pubDate>Mon, 25 Oct 2021 13:05:29 +0000</pubDate>
      <link>https://forem.com/mpodlasin/1-month-vim-only-challenge-the-whats-and-the-whys-5209</link>
      <guid>https://forem.com/mpodlasin/1-month-vim-only-challenge-the-whats-and-the-whys-5209</guid>
      <description>&lt;h2&gt;
  
  
  The Whats
&lt;/h2&gt;

&lt;p&gt;Two days ago, on Friday evening, I uninstalled VSCode and officially started my &lt;a href="https://twitter.com/search?q=%231MonthVimOnlyChallenge"&gt;#1MonthVimOnlyChallenge&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;In fact, I am currently writing this article in vim.:w&lt;/p&gt;

&lt;p&gt;My plan is to use vim as my editor/IDE of choice for 1 month. No matter what happens, no matter where it leads me - for 1 month I am not allowed to use any other IDE/coding editor/text editor. Only vim is allowed, although I will probably check out neovim as well at some point.&lt;/p&gt;

&lt;p&gt;This includes my personal stuff - coding side projects, writing articles etc. - but, perhaps more importantly, this includes my day job as well. And between my day job and personal stuff, I do &lt;em&gt;a lot&lt;/em&gt; of writing on a daily basis, including weekends. So that means &lt;em&gt;a lot&lt;/em&gt; of vim over the next 30 days.&lt;/p&gt;

&lt;p&gt;This article serves as a kickoff for this project. I plan to follow it up with 3 or 4 short articles, released on a weekly basis, documenting my progress, setup and reflections on using vim as a primary editor.&lt;/p&gt;

&lt;p&gt;In the last article of the series, I plan to make the ultimate decision. &lt;/p&gt;

&lt;p&gt;Either I will go back to the usual way of doing things, or I will stick with vim for the foreseeable future. Nothing is predetermined here. My decision will fully depend on how the next 30 days will go.&lt;/p&gt;

&lt;p&gt;Apart from weekly articles, I also plan to do more current updates on &lt;a href="https://twitter.com/m_podlasin"&gt;Twitter&lt;/a&gt;. There, on a daily basis, in real-time I will be sharing my thoughts and experiences of using vim.&lt;/p&gt;

&lt;p&gt;Now, at this point, it's important to stress that I am not going into this challenge completely fresh. I've already used vim during my university years, the last time around 6 years ago. However, during that period, I never got to a point where using vim would actually bring me significant productivity benefits. It also never felt 100% natural. &lt;/p&gt;

&lt;p&gt;So &lt;strong&gt;this&lt;/strong&gt; will be the barrier I will try to cross. I don't have to become a vim expert. I don't have to be the fastest programmer out there. The main question after 30 days will be this: &lt;/p&gt;

&lt;p&gt;Does this feel natural to me?&lt;/p&gt;

&lt;h2&gt;
  
  
  The Whys
&lt;/h2&gt;

&lt;p&gt;There are actually quite a few reasons why I am trying to attempt such a challenge at this point in my life. So I'll try to summarize them briefly, as a list in no particular order.&lt;/p&gt;

&lt;h3&gt;
  
  
  1. I Want to Spice Things Up
&lt;/h3&gt;

&lt;p&gt;I love my current job. But at a certain level of experience, many programming tasks become mundane and, frankly, a bit boring.&lt;/p&gt;

&lt;p&gt;So I am trying to spice things up for myself. Make things more interesting. Make things a bit harder, more challenging.&lt;/p&gt;

&lt;p&gt;Sometimes it's important to switch things up just for the sake of switching things up. It's like changing the wallpaper on a computer. There is no real reason to do that. But sometimes you just want to make things feel fresh again. And sometimes just changing the wallpaper can feel like literally having a brand new computer.&lt;/p&gt;

&lt;h3&gt;
  
  
  2. I Underuse VSCode Anyways
&lt;/h3&gt;

&lt;p&gt;Recently my colleagues at work started sharing what VSCode plugins they use. Most of them had &lt;strong&gt;at least&lt;/strong&gt; ten plugins installed and running. Meanwhile, I had... one.&lt;/p&gt;

&lt;p&gt;Last week a junior dev asked me what was a keyboard shortcut to do a fairly basic task in VSCode. I didn't know. I realized I don't know &lt;em&gt;almost any&lt;/em&gt; shortcuts.&lt;/p&gt;

&lt;p&gt;So you can see that, even though I've used VSCode literally for years now, I significantly underuse it. I might invest some time in order to fix that. But if I have to exert effort, I might as well do it in a direction that interests me more. Which is vim.&lt;/p&gt;

&lt;h3&gt;
  
  
  3. I Like The Command Line
&lt;/h3&gt;

&lt;p&gt;This probably relates to the fact that I am used to using the command line, rather than GUI tools. I enjoy it and, depending on the tool, sometimes I feel it gives me a better grasp of how things are working under the hood.&lt;/p&gt;

&lt;p&gt;I use git in the command line exclusively. It's funny to me because people are scared of using git in the command line, while I am scared to use git in any of the GUI incarnations. I just have trust issues.&lt;/p&gt;

&lt;p&gt;I also very, &lt;em&gt;very&lt;/em&gt;, &lt;strong&gt;very&lt;/strong&gt; rarely use a GUI debugger, which is one of the most common arguments people give me for using a solid IDE. I belong to the good old &lt;code&gt;console.log&lt;/code&gt; school of debugging. No matter how much people are joking about that, and how much amateurish it seems, for me, 99% of debugging is always the question of "what value this variable has at a certain point?". &lt;/p&gt;

&lt;p&gt;And for that, &lt;code&gt;console.log&lt;/code&gt; was always more than enough for me. Probably because I do mostly front-end/browser stuff, where such logging is particularly easy and powerful.&lt;/p&gt;

&lt;h3&gt;
  
  
  4. I Want To See Where Vim Is At These Days
&lt;/h3&gt;

&lt;p&gt;Now, there obviously &lt;em&gt;are&lt;/em&gt; capabilities of VSCode which I am using extensively. Those are mostly related to the exceptional TypeScript support that VSCode has. So everything from syntax highlighting, through autoimports and autocomplete, up to hovering over stuff to see the inferred types.&lt;/p&gt;

&lt;p&gt;And that's where frankly my curiosity gets me. I want to see where vim is at these days when it comes to integration with other tools.&lt;/p&gt;

&lt;p&gt;Vim has a plugin system and a big, very involved community creating those plugins. Bare vim is very simple, but I want to see how far you can push vim these days. Is it really possible to transform this command line text editor into a fully-featured IDE? And if so, how difficult will that be?&lt;/p&gt;

&lt;p&gt;I am curious about answers to those questions, so - apart from simply learning vim and writing in vim - I plan to invest significant time into researching and testing various plugins. &lt;/p&gt;

&lt;p&gt;I am dying to see how the vim I am using now - just a few days into the challenge - will differ from the one I will use in one month.&lt;/p&gt;

&lt;h3&gt;
  
  
  5. I Want To See If The "Holy Grail" Is Real
&lt;/h3&gt;

&lt;p&gt;Vim, as exotic and bizarre as it might seem, has a great promise.&lt;/p&gt;

&lt;p&gt;It promises that - if you exert significant enough effort - in the end, it will make you faster and more productive than a regular text editor. It will transform you from a human being and make you one with the text you are writing and editing, to the point where you will not feel that there is a keyboard separating you.&lt;/p&gt;

&lt;p&gt;It might take a long time, almost for sure more than 1 month. But in principle it's possible - promises vim and its followers.&lt;/p&gt;

&lt;p&gt;So I want to test that promise. Of course, as I just mentioned, reaching this "holy grail" proficiency might take a lot longer than 1 month.&lt;/p&gt;

&lt;p&gt;But writing daily for 30 days straight should at least give me a glimpse of such mastery. It should at least convince me that &lt;em&gt;it is&lt;/em&gt; possible.&lt;/p&gt;

&lt;p&gt;And that's probably what I am curious about the most. What is the answer? I'll tell you in 30 days.&lt;/p&gt;

&lt;p&gt;Cover Photo by &lt;a href="https://unsplash.com/@igorrodrigues?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;Igor Rodrigues&lt;/a&gt; on &lt;a href="https://unsplash.com/s/photos/challenge?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;Unsplash&lt;/a&gt;&lt;/p&gt;

</description>
      <category>vim</category>
      <category>productivity</category>
      <category>watercooler</category>
      <category>programming</category>
    </item>
    <item>
      <title>Haskell - The Most Gentle Introduction Ever (Part II)</title>
      <dc:creator>mpodlasin</dc:creator>
      <pubDate>Sun, 24 Oct 2021 12:40:25 +0000</pubDate>
      <link>https://forem.com/mpodlasin/haskell-the-most-gentle-introduction-ever-part-ii-7lm</link>
      <guid>https://forem.com/mpodlasin/haskell-the-most-gentle-introduction-ever-part-ii-7lm</guid>
      <description>&lt;p&gt;This is the second article in my little series explaining the basics of Haskell.&lt;/p&gt;

&lt;p&gt;If you haven't yet, I would recommend you to read &lt;a href="https://mpodlasin.com/articles/haskell-i"&gt;the first article&lt;/a&gt;, before diving into this one.&lt;/p&gt;

&lt;p&gt;So far we've learned the basics of defining functions and datatypes, as well as using them, all based on the Haskell &lt;code&gt;Bool&lt;/code&gt; type.&lt;/p&gt;

&lt;p&gt;In this article, we will deepen our understanding of functions in particular, while also learning a bit about built-in Haskell types representing numbers.&lt;/p&gt;

&lt;h4&gt;
  
  
  Type of Number 5
&lt;/h4&gt;

&lt;p&gt;Before we begin this section, I must warn you. In the previous article, I purposefully used the &lt;code&gt;Bool&lt;/code&gt; type, due to its simplicity. &lt;/p&gt;

&lt;p&gt;You might think that types representing numbers would be equally simple in Haskell. However, that's not &lt;em&gt;really&lt;/em&gt; the case.&lt;/p&gt;

&lt;p&gt;Not only does Haskell have quite a lot of types representing numbers, but there is also a significant effort in the language to make those types as interoperable with each other as possible. Because of that, there is a certain amount of complexity, which can be confusing to beginners.&lt;/p&gt;

&lt;p&gt;To see that, type in the following in the &lt;code&gt;ghci&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;:t 5
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You would probably expect to see something simple and concrete, like &lt;code&gt;Number&lt;/code&gt; or &lt;code&gt;Int&lt;/code&gt;. However, what we see is this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Num&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Quite confusing, isn't it? &lt;/p&gt;

&lt;p&gt;For a brief second try to ignore that whole &lt;code&gt;Num p =&amp;gt;&lt;/code&gt; part. If it wasn't there, what we would see, would be just &lt;code&gt;5 :: p&lt;/code&gt; So what is written here is that the value &lt;code&gt;5&lt;/code&gt; has type &lt;code&gt;p&lt;/code&gt;. &lt;/p&gt;

&lt;p&gt;This is the first time we see the name of the type being written using a small letter. That's important. Indeed, &lt;code&gt;p&lt;/code&gt; is not a specific type. It is a &lt;em&gt;type variable&lt;/em&gt;. This means that &lt;code&gt;p&lt;/code&gt; can be potentially many different, concrete types.&lt;/p&gt;

&lt;p&gt;It wouldn't however make sense for &lt;code&gt;5&lt;/code&gt; to have - for example - &lt;code&gt;Bool&lt;/code&gt; type. That's why &lt;code&gt;Num p =&amp;gt;&lt;/code&gt; part is also written in the type description. It basically says that this &lt;code&gt;p&lt;/code&gt; has to be a &lt;em&gt;numeric&lt;/em&gt; type. &lt;/p&gt;

&lt;p&gt;So, overall, &lt;code&gt;5&lt;/code&gt; has type &lt;code&gt;p&lt;/code&gt;, as long as &lt;code&gt;p&lt;/code&gt; is a &lt;em&gt;numeric&lt;/em&gt; type. For example, writing &lt;code&gt;5 :: Bool&lt;/code&gt; would be forbidden, thanks to that restriction.&lt;/p&gt;

&lt;p&gt;The exact mechanism at play here will not be discussed right now. We still have to cover a few basics before we can explain it fully and in detail. But perhaps you've heard it about it already - it's called &lt;em&gt;typeclasses&lt;/em&gt;. We will learn about typeclasses very soon. After we do, this whole type description will be absolutely clear to you.&lt;/p&gt;

&lt;p&gt;For now, however, we don't need to go into specifics. Throughout this article, we will use concrete, specific types, so that you don't get confused. I am just warning you about the existence of this mechanism so that you don't get unpleasantly surprised and discouraged when you investigate the types of functions or values on your own. &lt;/p&gt;

&lt;p&gt;Which I encourage you to do! Half of reading Haskell is reading the types, and you should be getting used to that.&lt;/p&gt;

&lt;h4&gt;
  
  
  Functions and Operators
&lt;/h4&gt;

&lt;p&gt;Let's begin by doing some simple operations on numbers, familiar from other programming languages.&lt;/p&gt;

&lt;p&gt;We can, for example, add two numbers. Writing in &lt;code&gt;ghci&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;results in a fairly reasonable answer:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;12&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;But to get a deeper insight into what is happening there, let's write a "wrapper" function for adding numbers.&lt;/p&gt;

&lt;p&gt;We will call it &lt;code&gt;add&lt;/code&gt; and we will use it like so:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As a result, we should see the same answer as just a moment ago:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;12&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We would like to, of course, begin with a type signature of that function. What could it potentially be?&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="o"&gt;???&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As I mentioned before, Haskell has many different types available for numerical values. &lt;/p&gt;

&lt;p&gt;Let's say that we want to work only with integers for now. Even for integers, there are multiple types to choose from.&lt;/p&gt;

&lt;p&gt;The two most basic ones are &lt;code&gt;Integer&lt;/code&gt; and &lt;code&gt;Int&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;Int&lt;/code&gt; is a type that is "closer to the machine". It's a so-called fixed precision integer type. This means that - depending on the architecture of your computer - each &lt;code&gt;Int&lt;/code&gt; will have a limited number of bits reserved for its value. Going out of those bounds can result in errors. This is a type very similar to C/C++ &lt;code&gt;int&lt;/code&gt; type.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;Integer&lt;/code&gt; on the other hand is an arbitrary precision integer type. This means that the values can potentially get bigger than those of &lt;code&gt;Int&lt;/code&gt;. Haskell will just reserve more memory if that becomes necessary. So those integers are "arbitrarily" large, but, of course, only in principle - if you completely run out of computer memory, nothing can save you.&lt;/p&gt;

&lt;p&gt;At the first glance, it would seem that &lt;code&gt;Integer&lt;/code&gt; has some clear advantages. That being said, &lt;code&gt;Int&lt;/code&gt; is still being widely used where memory efficiency is important or where we have high confidence that numbers will not become too large.&lt;/p&gt;

&lt;p&gt;For now, we will use the &lt;code&gt;Integer&lt;/code&gt; type. We can finally write the signature of our function:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;What we have written here is probably a bit confusing at the first glance. &lt;/p&gt;

&lt;p&gt;So far, we've only written declarations of functions that accept a single value and return a single value.&lt;/p&gt;

&lt;p&gt;But when adding numbers, we have to accept &lt;em&gt;two&lt;/em&gt; values as parameters (two numbers to add) and then return a single result (a sum of those numbers). So in our type signature, the first two &lt;code&gt;Integer&lt;/code&gt; types represent parameters and the last &lt;code&gt;Integer&lt;/code&gt; represents the return value:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="cm"&gt;{- 1st parameter -}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="cm"&gt;{- 2nd parameter -}&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="cm"&gt;{- return value -}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;(By the way, you can see here what syntax we've used to add comments to our code.)&lt;/p&gt;

&lt;p&gt;Let's now write the implementation:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;
&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Simple, right?&lt;/p&gt;

&lt;p&gt;Create a file called &lt;code&gt;lesson_02.hs&lt;/code&gt; and write down that definition. Next, load the file in &lt;code&gt;ghci&lt;/code&gt; (by running &lt;code&gt;:l lesson_02.hs&lt;/code&gt;) and type:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As expected, you will see the reasonable response:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;12&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I will now show you a neat trick. If your function accepts two arguments - like it is the case with &lt;code&gt;add&lt;/code&gt; - you can use an "infix notation" to call a function. Write:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="p"&gt;`&lt;/span&gt;&lt;span class="n"&gt;add&lt;/span&gt;&lt;span class="p"&gt;`&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You will again see &lt;code&gt;12&lt;/code&gt; as a response.&lt;/p&gt;

&lt;p&gt;Note that we didn't have to change the definition of &lt;code&gt;add&lt;/code&gt; in any way to do that. We just used backticks and we were immediately able to use it in infix notation. &lt;/p&gt;

&lt;p&gt;You can use this feature with literally any function that accepts two parameters - this is not a feature restricted only to functions operating on numbers.&lt;/p&gt;

&lt;p&gt;At this point those two calls:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="p"&gt;`&lt;/span&gt;&lt;span class="n"&gt;add&lt;/span&gt;&lt;span class="p"&gt;`&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;and&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;look eerily similar.&lt;/p&gt;

&lt;p&gt;That's not an accident. &lt;/p&gt;

&lt;p&gt;Indeed, you can do the reverse, and call the &lt;code&gt;+&lt;/code&gt; operator as you would call a regular function - in front of the parameters. If it's an operator, you just have to wrap it in parentheses:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Try it in &lt;code&gt;ghci&lt;/code&gt;. This works and returns &lt;code&gt;12&lt;/code&gt; again!&lt;/p&gt;

&lt;p&gt;Perhaps you already know where am I going with this. &lt;/p&gt;

&lt;p&gt;I am trying to show you that the built-in &lt;code&gt;+&lt;/code&gt; operator is indeed just a regular function. &lt;/p&gt;

&lt;p&gt;There are of course syntactical differences (like using backticks or parentheses for certain calls), but conceptually it is good to think of &lt;code&gt;+&lt;/code&gt; as being no different than &lt;code&gt;add&lt;/code&gt;. Both are functions that work on the &lt;code&gt;Integer&lt;/code&gt; type - accept two &lt;code&gt;Integer&lt;/code&gt; numbers and return an &lt;code&gt;Integer&lt;/code&gt; number as a result.&lt;/p&gt;

&lt;p&gt;Indeed, you can even investigate the type of an operator in &lt;code&gt;ghci&lt;/code&gt;, just as you would investigate the type of &lt;code&gt;add&lt;/code&gt; function.&lt;/p&gt;

&lt;p&gt;Typing:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="o"&gt;:&lt;/span&gt;&lt;span class="n"&gt;t&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;+&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;results in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;(+) :: Num a =&amp;gt; a -&amp;gt; a -&amp;gt; a
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This means that &lt;code&gt;+&lt;/code&gt; has type &lt;code&gt;a -&amp;gt; a -&amp;gt; a&lt;/code&gt;, where &lt;code&gt;a&lt;/code&gt; has to be a numeric type. So it's a function that accepts two parameters of numeric type &lt;code&gt;a&lt;/code&gt; and returns the result of the same type.&lt;/p&gt;

&lt;p&gt;I hope that at this point it makes sense why it is beneficial for the &lt;code&gt;+&lt;/code&gt; operator to have such an abstract definition. A clear benefit &lt;code&gt;+&lt;/code&gt; has over our custom &lt;code&gt;add&lt;/code&gt; function is that &lt;code&gt;+&lt;/code&gt; works on &lt;em&gt;any&lt;/em&gt; numeric type. No matter if it's &lt;code&gt;Integer&lt;/code&gt;, &lt;code&gt;Int&lt;/code&gt;, or any other type that somehow represents a number - &lt;code&gt;+&lt;/code&gt; can be used on it. Meanwhile, our &lt;code&gt;add&lt;/code&gt; function works only on &lt;code&gt;Integer&lt;/code&gt; types. For example, if you try to call it on - very similar - &lt;code&gt;Int&lt;/code&gt; numbers, the call will fail.&lt;/p&gt;

&lt;p&gt;So you can see that complexity introduced in number types doesn't come out of nowhere. It keeps the code typesafe, while still allowing huge flexibility. Types might seem complex, but this makes writing actual implementations a breeze.&lt;/p&gt;

&lt;h4&gt;
  
  
  Partial Application
&lt;/h4&gt;

&lt;p&gt;Let's go back to the type of &lt;code&gt;add&lt;/code&gt; function, which is probably still friendlier to read at this point.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The way we have written the type definition here might be surprising to you. We see two &lt;code&gt;-&amp;gt;&lt;/code&gt; arrows in the definition, almost suggesting that we are dealing with two functions.&lt;/p&gt;

&lt;p&gt;And indeed we are!&lt;/p&gt;

&lt;p&gt;To increase the readability even more, we can use the fact that &lt;code&gt;-&amp;gt;&lt;/code&gt; is right-associative. This means that our type definition is equivalent to this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Let's focus on the part that is outside of the parentheses first:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;...&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This says that &lt;code&gt;add&lt;/code&gt; is a function that accepts an &lt;code&gt;Integer&lt;/code&gt; and returns &lt;em&gt;something&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;What is that &lt;em&gt;something&lt;/em&gt;? To find out, we have to look inside the parentheses:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's again a function! This one also accepts an &lt;code&gt;Integer&lt;/code&gt; as an argument. And as a result, it returns another &lt;code&gt;Integer&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;So if we look at the type of &lt;code&gt;add&lt;/code&gt; again:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;we see that - in a certain sense - I was lying to you the whole time! &lt;/p&gt;

&lt;p&gt;I was saying that this is how we describe a function that accepts two parameters. But that's false! There is no function that accepts two parameters here! &lt;/p&gt;

&lt;p&gt;There is only a function that accepts a single parameter and then... returns another function! &lt;/p&gt;

&lt;p&gt;And then that second function accepts yet another parameter and &lt;em&gt;just then&lt;/em&gt; returns a result!&lt;/p&gt;

&lt;p&gt;To state the same thing in terms of another language, here is how you would write a regular function that accepts two parameters in JavaScript:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;y&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;x&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;y&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;However what we are creating in Haskell is something closer to this JavaScript code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;x&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;y&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;x&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;y&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Note how we have two functions here, each accepting only a single parameter.&lt;/p&gt;

&lt;p&gt;In the code snippet above, function &lt;code&gt;add&lt;/code&gt; accepts parameter &lt;code&gt;x&lt;/code&gt; and the second, anonymous, function accepts the parameter &lt;code&gt;y&lt;/code&gt;. There is no function here that accepts two parameters.&lt;/p&gt;

&lt;p&gt;So, based on what we have said so far, in Haskell we should be able to call the &lt;code&gt;add&lt;/code&gt; function with only one parameter and get a function, right?&lt;/p&gt;

&lt;p&gt;Let's try that in &lt;code&gt;ghci&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Regrettably, we get an error message:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;interactive&amp;gt;:108:1: error:
 • No instance for (Show (Integer -&amp;gt; Integer))
 arising from a use of ‘print’
 (maybe you haven't applied a function to enough arguments?)
 • In a stmt of an interactive GHCi command: print it
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;But that doesn't happen, because we did something wrong. The problem arises, because &lt;code&gt;add 5&lt;/code&gt; returns - as we stated - a function, and Haskell doesn't know how to print functions.&lt;/p&gt;

&lt;p&gt;We can however check the type of the &lt;code&gt;add 5&lt;/code&gt; expression and this way convince ourselves that this indeed works:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;:t add 5
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As a result, we see:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So it's a success! The expression &lt;code&gt;add 5&lt;/code&gt; has type &lt;code&gt;Integer -&amp;gt; Integer&lt;/code&gt;, just as we wanted!&lt;/p&gt;

&lt;p&gt;We can convince ourselves even more that that's the case, by calling that &lt;code&gt;add 5&lt;/code&gt; function on a number:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Oh... Wait. We just discovered something! &lt;/p&gt;

&lt;p&gt;It was probably confusing so far why Haskell has this strange way of calling functions on values, especially on multiple values. We were just separating them by space, like so:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;f&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="n"&gt;z&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now it becomes clear, that Haskell simply deals with single-argument functions all the time, and calling a function on multiple values is simply an illusion!&lt;/p&gt;

&lt;p&gt;Our call:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;is equivalent to:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;First, we apply &lt;code&gt;add&lt;/code&gt; to &lt;code&gt;5&lt;/code&gt; and as a result, we get a function of type &lt;code&gt;Integer -&amp;gt; Integer&lt;/code&gt;, as we've just seen.&lt;/p&gt;

&lt;p&gt;Then we apply that new function (&lt;code&gt;add 5&lt;/code&gt;) on a value &lt;code&gt;7&lt;/code&gt;. As a result, we get an &lt;code&gt;Integer&lt;/code&gt; - number &lt;code&gt;12&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Note that this means that in Haskell function call is left-associative:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Contrasting with what we found out before - that type definition of function is right-associative:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;It is of course done this way so that we get a sane default. Thanks to those properties, in the case of both defining and calling the &lt;code&gt;add&lt;/code&gt; function, we can simply forget about parentheses:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;How else can we convince ourselves that the result of calling &lt;code&gt;add 5&lt;/code&gt; is an actual, working function? Well... let's give a name to that function and use it that way!&lt;/p&gt;

&lt;p&gt;In your &lt;code&gt;lesson_02.hs&lt;/code&gt; file add the following line:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;addFive&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Load the file in &lt;code&gt;ghci&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;First let's investigate the type one more time, just to be sure what we are dealing with:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;:t addFive
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This gives us:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;addFive&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Exactly what we expected after applying the &lt;code&gt;add&lt;/code&gt; function to one argument.&lt;/p&gt;

&lt;p&gt;We could have also written down that type definition explicitly in our file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;addFive&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;
&lt;span class="n"&gt;addFive&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;add&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Do that to convince yourself that it all compiles when written this way.&lt;/p&gt;

&lt;p&gt;Now you can use your, highly specific, &lt;code&gt;addFive&lt;/code&gt; function to... add five to integers.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;addFive&lt;/span&gt; &lt;span class="mi"&gt;7&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This results in the expected:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;12&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now, I am sure this example with adding the number five seems a bit silly to you, and rightfully so.&lt;/p&gt;

&lt;p&gt;But I hope that it shows you the power of partial application in Haskell, where you can easily use highly general functions, accepting a higher number of parameters, to create something more specific and fitting your particular needs.&lt;/p&gt;

&lt;p&gt;For example, you can imagine a function that needs some kind of complex configuration in order to work - let's call it &lt;code&gt;imaginaryFunction&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Let's assume that this configuration is some kind of data structure of type &lt;code&gt;ComplexConfiguration&lt;/code&gt;. We can make that configuration the first argument of our function:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;imaginaryFunction&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;ComplexConfiguration&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;OtherParameter&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Result&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Why do we want to pass it as a parameter instead of just having it "hardcoded" inside the function? Who knows, perhaps different versions of our app need different configurations. Or perhaps we just need to change its value in our unit test suite.&lt;/p&gt;

&lt;p&gt;If we do that, then, in the actual app, we can simply apply &lt;code&gt;imaginaryFunction&lt;/code&gt; to a specific &lt;code&gt;ComplexConfiguration&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;configuredImaginaryFunction&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;imaginaryFunction&lt;/span&gt; &lt;span class="n"&gt;config&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After that, we can use the &lt;code&gt;configuredImaginaryFunction&lt;/code&gt; directly, without the need to &lt;em&gt;explicitly&lt;/em&gt; import &lt;code&gt;config&lt;/code&gt; object, whenever we want to use &lt;code&gt;imaginaryFunction&lt;/code&gt; in our code. Haskell just carries that config around for us! &lt;/p&gt;

&lt;p&gt;Sweet!&lt;/p&gt;

&lt;h4&gt;
  
  
  More Numbers and Operations
&lt;/h4&gt;

&lt;p&gt;This section will be far from a complete rundown, but I still want to quickly take you up to speed with basic operations on numbers in Haskell.&lt;/p&gt;

&lt;p&gt;So far we've covered two numeric types - &lt;code&gt;Integer&lt;/code&gt; and &lt;code&gt;Int&lt;/code&gt; and we've shown that we can add them.&lt;/p&gt;

&lt;p&gt;Just as in other languages, we can also subtract and multiply them in the usual way.&lt;/p&gt;

&lt;p&gt;So:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;results in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;3&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;while:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;5&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;results in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;15&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Other popular number types are &lt;code&gt;Float&lt;/code&gt; and &lt;code&gt;Double&lt;/code&gt;. Those are number types that can represent numbers beyond simple integers. The main difference between &lt;code&gt;Float&lt;/code&gt; and &lt;code&gt;Double&lt;/code&gt; is how big their storage capacity is. Most of the time you will likely use &lt;code&gt;Double&lt;/code&gt; unless you have some specific reason to use &lt;code&gt;Float&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;Float&lt;/code&gt; and &lt;code&gt;Double&lt;/code&gt; values can be added, subtracted, and multiplied just like &lt;code&gt;Int&lt;/code&gt; and &lt;code&gt;Integer&lt;/code&gt; values.&lt;/p&gt;

&lt;p&gt;Let's see some examples, just to make ourselves comfortable with that:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="mf"&gt;0.1&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;results in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mf"&gt;1.0&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="mf"&gt;0.1&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;result in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mf"&gt;1.1&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Note that in Haskell's standard library there are  &lt;em&gt;much more&lt;/em&gt; numeric types available. Some of them are fairly common, others are fairly specific. There are also many more built-in functions. &lt;/p&gt;

&lt;p&gt;This section was just meant to make you comfortable with making simple operations on basic number types. In the future we will come back to numbers for sure - there is a great deal of interesting type-level stuff at play here, and we will want to cover that for sure!&lt;/p&gt;

&lt;h4&gt;
  
  
  Identity
&lt;/h4&gt;

&lt;p&gt;Let's now take a small break from numbers and go back to our beloved booleans.&lt;/p&gt;

&lt;p&gt;Previously, we have written a &lt;code&gt;not&lt;/code&gt; function, which was negating the booleans - converting &lt;code&gt;True&lt;/code&gt; to &lt;code&gt;False&lt;/code&gt; and &lt;code&gt;False&lt;/code&gt; to &lt;code&gt;True&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;But what if we wanted to do... the opposite?&lt;/p&gt;

&lt;p&gt;What if we wanted to create a function that... returns &lt;code&gt;True&lt;/code&gt; when passed &lt;code&gt;True&lt;/code&gt; and returns &lt;code&gt;False&lt;/code&gt; when passed &lt;code&gt;False&lt;/code&gt;? &lt;/p&gt;

&lt;p&gt;This might sound a bit nonsensical. In a way, this function would do literally nothing. However, we will see that it will have a tremendous educational value for us, so let's curb our doubts and let's try to write it anyway.&lt;/p&gt;

&lt;p&gt;First, let's start with the name and type signature as all Haskell programming should.&lt;/p&gt;

&lt;p&gt;In mathematics, a function that takes a value and returns the exact same value is usually called an identity function. Since this one will operate on the &lt;code&gt;Bool&lt;/code&gt; type, we will call it &lt;code&gt;boolIdentity&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;boolIdentity&lt;/code&gt; will receive a single argument of type &lt;code&gt;Bool&lt;/code&gt; and return the same thing, so... &lt;code&gt;Bool&lt;/code&gt; as well! Therefore its type signature is this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;boolIdentity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now let's get started with actual implementation. Your first instinct might be to write something like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;boolIdentity&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;span class="n"&gt;boolIdentity&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This will work perfectly fine and is a valid solution, but there is a way to write the same thing in a more terse way. &lt;/p&gt;

&lt;p&gt;After all, we are returning the same value that we are receiving as a parameter, so we can simply write:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;boolIdentity&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the end, our whole definition looks like that:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;boolIdentity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;span class="n"&gt;boolIdentity&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Write that down in your &lt;code&gt;lesson_02.hs&lt;/code&gt; file and reload the file in &lt;code&gt;ghci&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;You can convince yourself that our function works, by running it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;boolIdentity&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This call results in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And at the same time &lt;code&gt;boolIdentity False&lt;/code&gt; returns &lt;code&gt;False&lt;/code&gt; (hopefully not surprisingly).&lt;/p&gt;

&lt;p&gt;Now let's create a similar function, but for numbers - let's say for &lt;code&gt;Integer&lt;/code&gt; type. We want a function that will take an &lt;code&gt;Integer&lt;/code&gt; value and return the same value. For example, if we call it with &lt;code&gt;5&lt;/code&gt;, we want to see &lt;code&gt;5&lt;/code&gt; again.&lt;/p&gt;

&lt;p&gt;Let's call it &lt;code&gt;integerIdentity&lt;/code&gt;. Let's begin by writing the type signature:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;integerIdentity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This was simple.&lt;/p&gt;

&lt;p&gt;Now let's think about the implementation. Well... we want to take the parameter passed to the function and... just return it!&lt;/p&gt;

&lt;p&gt;So we get:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;identityInteger&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;But... but this is exactly the same implementation as in the case of identity for &lt;code&gt;Bool&lt;/code&gt; values!&lt;/p&gt;

&lt;p&gt;Let's compare the two:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;boolIdentity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;span class="n"&gt;boolIdentity&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;integerIdentity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;
&lt;span class="n"&gt;integerIdentity&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Everything looks the same. The only difference here is the types. In the first function, we operate on the &lt;code&gt;Bool&lt;/code&gt; type. In the second we operate on the &lt;code&gt;Integer&lt;/code&gt; type.&lt;/p&gt;

&lt;p&gt;Now, if only there was a way to write that function only once. In the current state of things, we would have to write an identity function for each type in existence, which... sounds daunting, to say the least.&lt;/p&gt;

&lt;p&gt;It luckily turns out that Haskell does have a mechanism to deal with that easily. Not only that - we've already encountered that mechanism!&lt;/p&gt;

&lt;p&gt;Remember how the type of number &lt;code&gt;5&lt;/code&gt; was &lt;code&gt;Num p =&amp;gt; p&lt;/code&gt;? The &lt;code&gt;p&lt;/code&gt; in the type description was a type variable - basically a placeholder for actual, concrete types. &lt;/p&gt;

&lt;p&gt;We've also seen that the &lt;code&gt;+&lt;/code&gt; operator was quite general - it could be called on &lt;em&gt;any&lt;/em&gt; numeric type. It also had a type variable in its type signature.&lt;/p&gt;

&lt;p&gt;So the question is, can we use a type variable, to write the most generic version of the identity function possible? The answer is... absolutely!&lt;/p&gt;

&lt;p&gt;Let's remove the two previous identity functions and replace them with only one:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;identity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;
&lt;span class="n"&gt;identity&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Note how we used &lt;code&gt;a&lt;/code&gt; as a type variable here. The 3 type definitions we've seen so far, share the same "shape". You can see that the type definitions of identity for &lt;code&gt;Bool&lt;/code&gt; type and for &lt;code&gt;Integer&lt;/code&gt; type both "fit" this new type definition if you imagine variable &lt;code&gt;a&lt;/code&gt; being a placeholder for other types:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;boolIdentity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;integerIdentity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;identity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Let's run the code in &lt;code&gt;ghci&lt;/code&gt; and convince ourselves that we can indeed use this new, generic identity on both &lt;code&gt;Bool&lt;/code&gt; and &lt;code&gt;Integer&lt;/code&gt; values:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;identity&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;works and results in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;True
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And at the same time:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;identity&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;works as well and results in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="mi"&gt;5&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;At this point, it's important to emphasize a certain point. Given the implementation that we've used for the identity function:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;identity&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;we could &lt;strong&gt;not&lt;/strong&gt; give it, for example, the following type:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;identity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Integer&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This type definition in itself is not absurd. You can easily imagine functions that accept integers and return true or false (for example based on some condition).&lt;/p&gt;

&lt;p&gt;However, in this particular case, where we take argument &lt;code&gt;x&lt;/code&gt; and immediately return it, without doing anything else, it's clearly impossible for &lt;code&gt;x&lt;/code&gt; to "magically" change the type.&lt;/p&gt;

&lt;p&gt;And this fact &lt;strong&gt;is&lt;/strong&gt; reflected even in the most generic type definition of identity:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;identity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Note that this definition states that &lt;code&gt;identity&lt;/code&gt; accepts a value of type &lt;code&gt;a&lt;/code&gt; and returns a value &lt;strong&gt;of that same type&lt;/strong&gt; - namely &lt;code&gt;a&lt;/code&gt; again.&lt;/p&gt;

&lt;p&gt;On the flip side, the following definition:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;identity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;wouldn't be allowed. In fact, it won't compile, with an error, part of which says:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Couldn't match expected type ‘b’ with actual type ‘a’
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So the compiler literally says that in place of &lt;code&gt;b&lt;/code&gt; there should be the type variable &lt;code&gt;a&lt;/code&gt; present.&lt;/p&gt;

&lt;p&gt;That's because - given the current implementation - it's impossible for the value named &lt;code&gt;x&lt;/code&gt; to just change the type out of nowhere.&lt;/p&gt;

&lt;p&gt;And indeed, when Haskell infers the type of untyped code, it goes for the most general interpretation possible.&lt;/p&gt;

&lt;p&gt;You can convince yourself of that, by removing the type definition from &lt;code&gt;lesson_02.hs&lt;/code&gt; file, and leaving only the implementation:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;identity&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And then compiling it in &lt;code&gt;ghci&lt;/code&gt; and checking the type of &lt;code&gt;identity&lt;/code&gt; by running:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;:t identity
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As an answer you will see:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;identity&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is exactly the same type definition that we wrote by hand. It simply uses a different letter (&lt;code&gt;p&lt;/code&gt; instead of &lt;code&gt;a&lt;/code&gt;).&lt;/p&gt;

&lt;p&gt;At the very end of this section, it would be good to mention, that you don't actually have to define the &lt;code&gt;identity&lt;/code&gt; function by yourself. We only did it for educational purposes.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;Prelude&lt;/code&gt; - the standard library for Haskell - has it always available for you under the shorter name &lt;code&gt;id&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;To convince yourself of that, write the following in &lt;code&gt;ghci&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;:t id
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As a response you will see, more than familiar now, type:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;id :: a -&amp;gt; a
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h4&gt;
  
  
  Conclusion
&lt;/h4&gt;

&lt;p&gt;In the second part of "The Most Gentle Introduction Ever" to Haskell, we used operators and functions on numbers and discovered that they are in fact almost the same. We've also seen that there are no functions of multiple variables in Haskell - they are just functions that return other functions. &lt;/p&gt;

&lt;p&gt;And at the end, we expanded our understanding of what a type definition can be, by showing the simplest possible usage of type variables - using the identity function as an example.&lt;/p&gt;

&lt;p&gt;All those things were meant to make you feel more comfortable with the concept of a function in Haskell. And in the future article, we will use a similar approach to enhance our understanding of algebraic data structures, especially custom ones.&lt;/p&gt;

&lt;p&gt;So see you next time and thanks for reading!&lt;/p&gt;

</description>
      <category>haskell</category>
      <category>functional</category>
      <category>tutorial</category>
      <category>codenewbie</category>
    </item>
    <item>
      <title>Haskell - The Most Gentle Introduction Ever</title>
      <dc:creator>mpodlasin</dc:creator>
      <pubDate>Thu, 29 Jul 2021 19:13:49 +0000</pubDate>
      <link>https://forem.com/mpodlasin/haskell-the-most-gentle-introduction-ever-32ho</link>
      <guid>https://forem.com/mpodlasin/haskell-the-most-gentle-introduction-ever-32ho</guid>
      <description>&lt;h3&gt;
  
  
  Who Is This Article For?
&lt;/h3&gt;

&lt;p&gt;This article is the first in (hopefully) a series on functional programming in Haskell.&lt;/p&gt;

&lt;p&gt;It doesn't assume any previous knowledge of Haskell or even functional programming for that matter.&lt;/p&gt;

&lt;p&gt;It does however assume that you can already program in &lt;strong&gt;some&lt;/strong&gt; programming language.&lt;/p&gt;

&lt;p&gt;If you feel fairly comfortable in a language like JavaScript, Python, Java, C/C++, or anything similar, you are more than capable of going through this tutorial. You can rest assured that everything will be explained slowly and carefully.&lt;/p&gt;

&lt;p&gt;The main point of this series will be to highlight the differences between Haskell and those "typical" languages that I've mentioned. So the less you know about Haskell and/or functional programming, the more illuminating and mindbending those articles will be for you.&lt;/p&gt;

&lt;p&gt;I will also be showing you how learning Haskell can benefit you in writing better code even when using other, more mainstream languages. If you feel stuck when it comes to your programming skills and if you feel like you haven't been stretching your coding muscles lately - Haskell will be perfect for you! &lt;/p&gt;

&lt;p&gt;Whether you are a senior coding veteran or a junior dev that barely started your career, Haskell will push you to be an all-around better programmer. If you need more convincing, in the past I've written about &lt;a href="https://dev.to/mpodlasin/5-practical-reasons-why-your-next-programming-language-to-learn-should-be-haskell-gc"&gt;why it is beneficial to learn Haskell&lt;/a&gt;, even if you don't plan to code in it professionally.&lt;/p&gt;

&lt;p&gt;Are you ready? Let's go then!&lt;/p&gt;

&lt;h3&gt;
  
  
  Installing Haskellers Toolbelt
&lt;/h3&gt;

&lt;p&gt;If you are on this journey with me, we'll begin by installing some software needed to run Haskell.&lt;/p&gt;

&lt;p&gt;But if you are still unsure/unconvinced, you don't have to do even that. I will be keeping all the examples as simple as possible, so it will be enough to just use a REPL like &lt;a href="https://replit.com/languages/haskell"&gt;this one&lt;/a&gt;. The only thing you need to do there is to empty the file in the REPL - we will start from scratch - and run &lt;code&gt;ghci&lt;/code&gt; command in the terminal. You are ready now, so if you don't want to install Haskell tools on your computer, you can safely omit the rest of this section.&lt;/p&gt;

&lt;p&gt;Still here? All in on learning Haskell? Awesome!&lt;/p&gt;

&lt;p&gt;The download section on &lt;a href="https://haskell.org"&gt;haskell.org&lt;/a&gt; can be a bit confusing, so I would recommend you to go straight to &lt;a href="https://www.haskell.org/ghcup/"&gt;ghcup&lt;/a&gt; page. You just have to copy the script from the website, paste it to your terminal and run it.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;ghcup&lt;/code&gt; is a "Haskell toolchain installer". This means that it allows you to easily install and manage various tools related to Haskell.&lt;/p&gt;

&lt;p&gt;The installation process guides you by hand - you will just have to answer a few questions. &lt;/p&gt;

&lt;p&gt;The installer will ask you about installing secondary packages - &lt;code&gt;stack&lt;/code&gt; and &lt;code&gt;hls&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;hls&lt;/code&gt; is "Haskell Language Server". It allows IDE plugins and extensions to work seamlessly with Haskell. So it's worth having it since the very beginning.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;stack&lt;/code&gt; is a build tool that allows you to create isolated Haskell projects easily. This would be massive overkill for simple, one-file scripts that we will be writing at the beginning. However, once we move on to writing more complex programs, Stack will be extremely helpful. Whether you prefer to install it now or later - it's up to you.&lt;/p&gt;

&lt;p&gt;After running the script, you can test if everything went well by running the &lt;code&gt;ghci&lt;/code&gt; command in your terminal.&lt;/p&gt;

&lt;p&gt;We've mentioned quite a few tools so far, but &lt;code&gt;ghci&lt;/code&gt; is the one that we will &lt;em&gt;actually&lt;/em&gt; use in this article. It is an interactive environment for running Haskell code. &lt;code&gt;ghc&lt;/code&gt; (no "i" at the end!) stands for Glasgow Haskell Compiler. &lt;code&gt;ghc&lt;/code&gt; is in fact its own command, that will allow us to compile code into binary executables.&lt;/p&gt;

&lt;p&gt;However, if we just want to play around with code and test some stuff, an &lt;em&gt;interactive&lt;/em&gt; &lt;code&gt;ghc&lt;/code&gt; - called &lt;code&gt;ghci&lt;/code&gt; - is perfect for that, because it allows us to run Haskell code without the compilation step. On top of that, it has some handy commands which we will use today.&lt;/p&gt;

&lt;p&gt;If you type in &lt;code&gt;ghci&lt;/code&gt; in the terminal and get an error, it likely means that your terminal doesn't know how to find the &lt;code&gt;ghci&lt;/code&gt; binary. You might have to close and reopen the terminal window after finishing the installation.&lt;/p&gt;

&lt;p&gt;If it's still not working, then - depending on the environment you are using - you will have to edit your &lt;code&gt;.bashrc&lt;/code&gt; or &lt;code&gt;.zshrc&lt;/code&gt; file.&lt;/p&gt;

&lt;p&gt;Luckily &lt;code&gt;ghcup&lt;/code&gt; is very tidy - it just installs everything in a single directory, in my case &lt;code&gt;/Users/mateusz.podlasin/.ghcup&lt;/code&gt;. In that directory, there is a &lt;code&gt;bin&lt;/code&gt; folder. You need to point the terminal you are using to that folder.&lt;/p&gt;

&lt;p&gt;So, in my case, I had to add the following line to my &lt;code&gt;.zshrc&lt;/code&gt; file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;export PATH="/Users/mateusz.podlasin/.ghcup/bin:$PATH"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After closing the terminal and opening it again, running &lt;code&gt;ghci&lt;/code&gt; should now result in the following output:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;GHCi, version 8.10.5: https://www.haskell.org/ghc/ :? for help
Prelude&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If you see this, you are ready to begin our Haskell adventure.&lt;/p&gt;

&lt;h3&gt;
  
  
  Playing With Booleans
&lt;/h3&gt;

&lt;p&gt;A boolean (in Haskell named &lt;code&gt;Bool&lt;/code&gt;) is one of the simplest and most familiar types that a programmer encounters regularly. No matter what programming language you've used previously, you likely know booleans very well.&lt;/p&gt;

&lt;p&gt;That's why they will be perfect for learning the basics of Haskell.&lt;/p&gt;

&lt;p&gt;In Haskell boolean values are written starting with a big letter, so we have &lt;code&gt;True&lt;/code&gt; and &lt;code&gt;False&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;In &lt;code&gt;ghci&lt;/code&gt; you can type in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;:t True
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;:t&lt;/code&gt; is a &lt;code&gt;ghci&lt;/code&gt; command for checking the type of a value. Note that this command is not a part of Haskell itself, just a &lt;code&gt;ghci&lt;/code&gt; functionality.&lt;/p&gt;

&lt;p&gt;After clicking enter, as a result, you will see:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;True :: Bool
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You can read &lt;code&gt;::&lt;/code&gt; as "has type". So this line says that the value True has type Bool.&lt;/p&gt;

&lt;p&gt;Just to make sure we understand that correctly, let's check the type of value False:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;:t False
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We see:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;False :: Bool
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As you probably anticipated, the value False has type Bool as well. So True and False are of the same type. And in Haskell - quite reasonably - True and False are the &lt;em&gt;only&lt;/em&gt; values of the type Bool.&lt;/p&gt;

&lt;p&gt;Contrary to &lt;code&gt;:t&lt;/code&gt;, the &lt;code&gt;&amp;lt;value&amp;gt; :: &amp;lt;type&amp;gt;&lt;/code&gt; syntax &lt;em&gt;is&lt;/em&gt; a part of Haskell language. And this should already hint at something to you. If a language has a dedicated syntax to express the sentence "&amp;lt;value&amp;gt; has type &amp;lt;type&amp;gt;", it means that this language probably treats types fairly seriously. &lt;/p&gt;

&lt;p&gt;As we will soon see, types are at the very heart of programming in Haskell. As a matter of fact, sometimes when coding in Haskell you will be thinking about types &lt;em&gt;more&lt;/em&gt; than about actual values!&lt;/p&gt;

&lt;p&gt;And while we are here, note that the name of the type - &lt;code&gt;Bool&lt;/code&gt; - is also written starting with a big letter in Haskell, just like the names of values. This will be important later.&lt;/p&gt;

&lt;p&gt;Let's now start writing some actual code. We will still use &lt;code&gt;ghci&lt;/code&gt; to run it, but we need to write it in an actual file.&lt;/p&gt;

&lt;p&gt;Create a file called &lt;code&gt;lesson_1.hs&lt;/code&gt; (in REPL I linked, the file is already created for you and is called &lt;code&gt;main.hs&lt;/code&gt;). Note the &lt;code&gt;.hs&lt;/code&gt; suffix, which represents Haskell source code files.&lt;/p&gt;

&lt;p&gt;You can create that file anywhere you want. You can also edit it with any text editor you desire. &lt;/p&gt;

&lt;p&gt;I would recommend using &lt;a href="https://code.visualstudio.com"&gt;Visual Studio Code&lt;/a&gt;. After installing VS Code, immediately go to the "Extensions" tab (on the left) and install the "Haskell" extension. It will give you many handy features. It will for example start displaying the types of values you hover over. If you have trouble with the extension "not detecting &lt;code&gt;ghc&lt;/code&gt;", remember to edit the PATH in the &lt;code&gt;.bashrc&lt;/code&gt;/&lt;code&gt;.zshrc&lt;/code&gt; file, just like I described in the setup section. After that restart the editor.&lt;/p&gt;

&lt;p&gt;After you've created the file, make sure to be - using the terminal - in the same directory where the file is located. To do that, you can leave &lt;code&gt;ghci&lt;/code&gt; by running &lt;code&gt;:q&lt;/code&gt;. Then switch directories to a proper one and run the &lt;code&gt;ghci&lt;/code&gt; command once again. &lt;/p&gt;

&lt;p&gt;In &lt;code&gt;ghci&lt;/code&gt; try loading the file, by running:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;:l lesson_1.hs
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Even though your file doesn't have any code in it just yet, you should see a success message like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;[1 of 1] Compiling Main ( lesson_1.hs, interpreted )
Ok, one module loaded.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If you don't see that, you've likely run &lt;code&gt;ghci&lt;/code&gt; in a different directory than your file is located.&lt;/p&gt;

&lt;p&gt;But if you see the message, you are ready to begin coding!&lt;/p&gt;

&lt;p&gt;So we have types (&lt;code&gt;Bool&lt;/code&gt;) and values (&lt;code&gt;True&lt;/code&gt; and &lt;code&gt;False&lt;/code&gt;). What can we do with them? The most basic thing, known from other languages, would be to assign a value to a variable.&lt;/p&gt;

&lt;p&gt;Write the following line in &lt;code&gt;lesson_1.hs&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now load it again in &lt;code&gt;ghci&lt;/code&gt; with the same command as before - &lt;code&gt;:l lesson_1.hs&lt;/code&gt; (remember to save the file beforehand).&lt;/p&gt;

&lt;p&gt;In &lt;code&gt;ghci&lt;/code&gt; you can now type:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;x
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As a response you will see:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;True
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This shows that, indeed, we assigned the value True to the variable x.&lt;/p&gt;

&lt;p&gt;Now let's do something that might surprise you and that will show you just like radically different Haskell is from "regular" languages.&lt;/p&gt;

&lt;p&gt;In &lt;code&gt;lesson_1.hs&lt;/code&gt; file let's write:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Load it again in &lt;code&gt;ghci&lt;/code&gt;. You will see the following output:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;[1 of 1] Compiling Main ( lesson_1.hs, interpreted )

test.hs:2:1: error:
 Multiple declarations of ‘x’
 Declared at: lesson_1.hs:1:1
 lesson_2.hs:2:1
 |
2 | x = False
 | ^
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The most important part of that error message says that there are &lt;em&gt;Multiple declarations of ‘x’&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;It turns out that in Haskell, once you've assigned a value to a variable, you can't overwrite it or change it in any way. Ever.&lt;/p&gt;

&lt;p&gt;If it's a Bool, you can't change it from True to False. If it's a number (which we will cover in future articles), you can't change its value. For example, you can't even increase the value of a numeric variable by one!&lt;/p&gt;

&lt;p&gt;This sounds incredibly radical to someone used to traditional, imperative programming. Idioms like:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;i++;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;or&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;someBoolean = !someBoolean;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;etc. are so prevalent in those languages that thought of only assigning a value to a variable once sounds... well... frankly just crazy!&lt;/p&gt;

&lt;p&gt;Is it even possible to write actual, real-world programs with a language like this? &lt;/p&gt;

&lt;p&gt;The answer is absolutely, and we will see that quite soon. But for now, you just have to accept that - once assigned a value - you can't ever change that variable anymore.&lt;/p&gt;

&lt;p&gt;You've likely heard about immutability at this point. I already wrote about &lt;a href="https://dev.to/mpodlasin/functional-programming-in-js-part-ii-immutability-vanilla-js-immutable-js-and-immer-2ccm"&gt;immutability in JavaScript&lt;/a&gt; for example.&lt;/p&gt;

&lt;p&gt;That's the thing though. In those other, imperative languages immutability has to be introduced via some library or specific programming approach. &lt;/p&gt;

&lt;p&gt;It's exactly the reverse in Haskell. Here immutability is the default and you have to use libraries or certain methods to achieve mutable variables/state.&lt;/p&gt;

&lt;p&gt;That might sound cumbersome, but it's not an accident that the principle of immutability became so popular even in the mainstream, "mutable by default" languages. It really makes your code less buggy, safer, and more predictable.&lt;/p&gt;

&lt;p&gt;Ok, enough of talky talk. So we know that once created, we can't alter that variable. But it is by no means useless. We can now call some functions using it.&lt;/p&gt;

&lt;p&gt;Remove the &lt;code&gt;x = False&lt;/code&gt; line from your file, so that loading the file in &lt;code&gt;ghci&lt;/code&gt; works again and &lt;code&gt;x&lt;/code&gt; has the value True.&lt;/p&gt;

&lt;p&gt;Then run the following in &lt;code&gt;ghci&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;not&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As an answer you will see:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;False
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now, if you've coded in Python or a language with similar syntax, you might think that &lt;code&gt;not&lt;/code&gt; is some special, reserved keyword for negating booleans.&lt;/p&gt;

&lt;p&gt;No. In Haskell, &lt;code&gt;not&lt;/code&gt; is just a regular function.&lt;/p&gt;

&lt;p&gt;In a typical language, a function call would look something like that:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;not(x)
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;But this is not the case in Haskell. In Haskell, you write the function name, and then - instead of parenthesis - you provide arguments by separating them with a single space.&lt;/p&gt;

&lt;p&gt;So to call a function &lt;code&gt;f&lt;/code&gt; on a variable &lt;code&gt;x&lt;/code&gt; you would write:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;f&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If &lt;code&gt;f&lt;/code&gt; accepted two parameters, instead of typical &lt;code&gt;f(x, y)&lt;/code&gt; you would write:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;f&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If &lt;code&gt;f&lt;/code&gt; accepted three parameters, you would write:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;f&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="n"&gt;z&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And so on. You get the idea.&lt;/p&gt;

&lt;p&gt;Let's go back to our &lt;code&gt;not&lt;/code&gt; function. We called it on a variable, but nothing is preventing us from calling it on values directly.&lt;/p&gt;

&lt;p&gt;In &lt;code&gt;ghci&lt;/code&gt; type:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;not&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;and you will see:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;False
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Typing:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;not&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;results in the response:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;True
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now, just as values, functions have types as well. We can investigate the type of &lt;code&gt;not&lt;/code&gt; function in the same way we investigated the types of True and False - using the &lt;code&gt;:t&lt;/code&gt; command in &lt;code&gt;ghci&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Type:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;:t not
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;and you will see the following answer:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;not :: Bool -&amp;gt; Bool
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We again see the &lt;code&gt;::&lt;/code&gt; symbol, which means "has type". We see the Bool type mentioned twice. &lt;/p&gt;

&lt;p&gt;The only new symbol here is &lt;code&gt;-&amp;gt;&lt;/code&gt;. As you probably expect, &lt;code&gt;&amp;lt;something&amp;gt; -&amp;gt; &amp;lt;something else&amp;gt;&lt;/code&gt; reads as "function from &amp;lt;something&amp;gt; to &amp;lt;something else&amp;gt;".&lt;/p&gt;

&lt;p&gt;So the output that we got from &lt;code&gt;ghci&lt;/code&gt; can be read as "&lt;code&gt;not&lt;/code&gt; has the type of function from Bool to Bool". Or, more naturally, "&lt;code&gt;not&lt;/code&gt; &lt;em&gt;is&lt;/em&gt; a function from Bool to Bool".&lt;/p&gt;

&lt;p&gt;This shouldn't be surprising. When we call &lt;code&gt;not&lt;/code&gt; on a Bool value, we expect to see the Bool value as a result - the "opposite" of what we've passed. If we called &lt;code&gt;not True&lt;/code&gt; and got &lt;code&gt;15&lt;/code&gt; as an answer, we would be extremely confused, wouldn't we?&lt;/p&gt;

&lt;h3&gt;
  
  
  Writing Functions
&lt;/h3&gt;

&lt;p&gt;At this point, I would like to prove to you that there is nothing magical about &lt;code&gt;not&lt;/code&gt;. If it's just a regular function, you should be able to write it by yourself, right?&lt;/p&gt;

&lt;p&gt;Yup, and that's exactly what we will do right now. We will write our first Haskell function!&lt;/p&gt;

&lt;p&gt;We will do that in our &lt;code&gt;lesson_1.hs&lt;/code&gt; file.&lt;/p&gt;

&lt;p&gt;Under the &lt;code&gt;x&lt;/code&gt; definition, write the following line:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt; &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Let's break down what is happening here a little bit. &lt;/p&gt;

&lt;p&gt;First, we have something that looks exactly like a call of a function - beginning with the name (&lt;code&gt;myNot&lt;/code&gt;), and later the parameters of the function, separated by spaces. In this particular case, we have only one parameter, which we named &lt;code&gt;x&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Next, we have an assignment (&lt;code&gt;=&lt;/code&gt; character), after which we write the actual function - the part which we call "function body". In this case, the function body is just a simple &lt;code&gt;if then else&lt;/code&gt; expression. Let's break it down.&lt;/p&gt;

&lt;p&gt;Right after the &lt;code&gt;if&lt;/code&gt; keyword we have to provide a condition. Our condition is really &lt;code&gt;x == True&lt;/code&gt;. You probably recognize &lt;code&gt;==&lt;/code&gt; from other languages. In Haskell it means the same thing - it's an equality operator. &lt;/p&gt;

&lt;p&gt;But &lt;code&gt;x == True&lt;/code&gt; is equivalent to simply writing &lt;code&gt;x&lt;/code&gt;. After all, if &lt;code&gt;x == True&lt;/code&gt; evaluates to True, this means that &lt;code&gt;x&lt;/code&gt; itself has the value of True. So we can just write &lt;code&gt;x&lt;/code&gt; as our condition, for brevity.&lt;/p&gt;

&lt;p&gt;If the condition in &lt;code&gt;if then else&lt;/code&gt; (our &lt;code&gt;x&lt;/code&gt;) evaluates to &lt;code&gt;True&lt;/code&gt;, the function will return the value after the &lt;code&gt;then&lt;/code&gt; keyword. If it evaluates to &lt;code&gt;False&lt;/code&gt;, the function will return the value after the &lt;code&gt;else&lt;/code&gt; keyword. Quite simple.&lt;/p&gt;

&lt;p&gt;Note that in Haskell &lt;code&gt;if then else&lt;/code&gt; is an &lt;em&gt;expression&lt;/em&gt;. This means that in the end, it evaluates to a value - one of the two provided after "then" and "else" keywords. In JavaScript for example this means that it has more common with a ternary operator, rather than regular &lt;code&gt;if/else&lt;/code&gt; &lt;em&gt;statement&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;The following code in JavaScript:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;someVariable&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;condition&lt;/span&gt; &lt;span class="p"&gt;?&lt;/span&gt; &lt;span class="nx"&gt;firstValue&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;secondValue&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;would be therefore equivalent to the following in Haskell:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;someVariable&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;condition&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="n"&gt;firstValue&lt;/span&gt; &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;secondValue&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Let's return to the definition of our function:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt; &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I will admit that I've used &lt;code&gt;x&lt;/code&gt; as a parameter name here just to confuse you a little bit. For a second you might think that there is a naming conflict between &lt;code&gt;x&lt;/code&gt; that we defined earlier and the &lt;code&gt;x&lt;/code&gt; from the function.&lt;/p&gt;

&lt;p&gt;You can however convince yourself that that's not true, by loading the file again in &lt;code&gt;ghci&lt;/code&gt;. It loads properly, without any errors. On top of that, our newly defined function &lt;code&gt;myNot&lt;/code&gt; actually works.&lt;/p&gt;

&lt;p&gt;Calling in &lt;code&gt;ghci&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;returns&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;False
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;and vice versa.&lt;/p&gt;

&lt;p&gt;We can even use the function on our &lt;code&gt;x&lt;/code&gt; variable defined above it.&lt;/p&gt;

&lt;p&gt;Running:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;myNot x
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;results in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;False
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That is correct because in the file we assigned &lt;code&gt;x&lt;/code&gt; to &lt;code&gt;True&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;So there is no naming conflict, but &lt;em&gt;it is&lt;/em&gt; true that we are "shadowing" the &lt;code&gt;x&lt;/code&gt; variable. If we now wanted to use it in the function body, we couldn't, because we decided to give the same name to the function parameter.&lt;/p&gt;

&lt;p&gt;So, just for clarity, let's change the name of the function parameter to &lt;code&gt;b&lt;/code&gt; (as in "boolean").&lt;/p&gt;

&lt;p&gt;The whole file looks now like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;

&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt; &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This will help us not get confused.&lt;/p&gt;

&lt;p&gt;Perhaps the function definition that we came up with is not at all what you expected. We moaned for so long about the importance of types, but now we've written something that borderline looks like untyped Python. What's going on? Where are those scary types?&lt;/p&gt;

&lt;p&gt;It turns out that Haskell's type system is so powerful, that most of the time it can &lt;em&gt;infer&lt;/em&gt; what should be the type of a function - or a value - you've written. Save the file, load it in &lt;code&gt;ghci&lt;/code&gt; and write:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;t: myNot
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You will see:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;myNot :: Bool -&amp;gt; Bool
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So indeed your custom &lt;code&gt;myNot&lt;/code&gt; function has the same type as the original &lt;code&gt;not&lt;/code&gt;. But how Haskell came to that conclusion?&lt;/p&gt;

&lt;p&gt;It's quite straightforward.&lt;/p&gt;

&lt;p&gt;Since you wrote &lt;code&gt;if x then ...&lt;/code&gt;, using &lt;code&gt;x&lt;/code&gt; as a condition, Haskell knew that parameter &lt;code&gt;x&lt;/code&gt; had to be a Bool. That's because Haskell is (again!) quite strict here and only the value of type Bool can be used as a condition in the &lt;code&gt;if then else&lt;/code&gt; construct. (Note that we've written &lt;em&gt;"as a condition"&lt;/em&gt; here! It's completely fine to provide values of other types after &lt;code&gt;then&lt;/code&gt; and &lt;code&gt;else&lt;/code&gt; keywords - we will see that in future articles.)&lt;/p&gt;

&lt;p&gt;And at the same time, you wrote &lt;code&gt;then False else True&lt;/code&gt;. Here, in both cases ("then" case and "else" case) you are returning a Bool. Therefore the output of your function has type Bool as well.&lt;/p&gt;

&lt;p&gt;Those two facts combined bring us to a conclusion that the type of &lt;code&gt;myNot&lt;/code&gt; has to be &lt;code&gt;Bool -&amp;gt; Bool&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Haskell inference is extremely good and the compiler may only have problems if you write something that is inherently vague.&lt;/p&gt;

&lt;p&gt;And yet it is still recommended to put the type signature of the function in the code. You will see that in the vast majority of Haskell codebases the types are always written explicitly.&lt;/p&gt;

&lt;p&gt;You can do it by writing the type of the function above its definition:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt; &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt; 
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Writing down the type in the code has some major advantages.&lt;/p&gt;

&lt;p&gt;First of all, it increases the readability of the code. Types are incredibly useful as documentation of what your function does. In Haskell, you will often be able to find out what a given function does simply by looking at its name and type signature. No need to read the implementation!&lt;/p&gt;

&lt;p&gt;Function called &lt;code&gt;not&lt;/code&gt; that has type &lt;code&gt;Bool -&amp;gt; Bool&lt;/code&gt;? It surely must be a function negating the booleans!&lt;/p&gt;

&lt;p&gt;Second of all, it's valuable to write the type of the function before writing the function definition itself. If you do that, Haskell's type system will "guide you" and help validate that your code works as expected.&lt;/p&gt;

&lt;p&gt;After all, inferred type of a function may differ from what you have intended. &lt;/p&gt;

&lt;p&gt;Writing the type beforehand is almost like sketching or designing a function, before actually writing it. Personally, I find that writing down the type first often gives me a better idea of how to implement the function.&lt;/p&gt;

&lt;p&gt;This is an example of a skill that Haskell teaches you, that you can easily transfer to other languages. Even when I'm writing untyped JavaScript, I still always start by thinking about what kind of type signature my function will have. This helps me to write code faster and make fewer bugs, even though I have to be my own type-checker in that case.&lt;/p&gt;

&lt;p&gt;So we have successfully replicated the &lt;code&gt;not&lt;/code&gt; function - &lt;code&gt;myNot&lt;/code&gt; has the same type &lt;em&gt;and&lt;/em&gt; behaves in the same way. Running &lt;code&gt;myNot True&lt;/code&gt; evaluates to &lt;code&gt;False&lt;/code&gt;, running &lt;code&gt;myNot False&lt;/code&gt; evaluates to &lt;code&gt;True&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;But let's stay on this topic a bit longer and try to write the same function in a completely different manner.&lt;/p&gt;

&lt;p&gt;Let's write:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt;
&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You can check for yourself that this loads properly in the &lt;code&gt;ghci&lt;/code&gt;. You can also test that &lt;code&gt;myNot&lt;/code&gt; still behaves the same as before.&lt;/p&gt;

&lt;p&gt;What is happening here?&lt;/p&gt;

&lt;p&gt;We used what is known as pattern matching.&lt;/p&gt;

&lt;p&gt;Instead of declaring the parameter of the function as a variable named &lt;code&gt;b&lt;/code&gt;, we can avoid naming it entirely and simply substitute it with a value that will be provided to the function once it's called.&lt;/p&gt;

&lt;p&gt;When we make a call &lt;code&gt;myNot True&lt;/code&gt;, Haskell looks for a definition that "fits" such a call. In this case, it's the first line (not counting the type signature). If we make a call &lt;code&gt;myNot False&lt;/code&gt;, then it's the second line that &lt;em&gt;matches&lt;/em&gt; that call. Hence the name "pattern matching".&lt;/p&gt;

&lt;p&gt;Hopefully, it's clear that if you call &lt;code&gt;myNot&lt;/code&gt; with a variable, not an actual value, pattern matching will still work just fine. In that case, Haskell simply evaluates the value of the variable and performs pattern matching then.&lt;/p&gt;

&lt;p&gt;So with this new definition, calling:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Still properly returns:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;False
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So we have two versions of the same function:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt; &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt;
&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;For all intents and purposes, these two functions behave in the same way (and have the same type). Which one you prefer depends entirely on you.&lt;/p&gt;

&lt;p&gt;Do you want to see yet another way to write the same function? Here you go:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;
 &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt;
 &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;otherwise&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Arguably this way of writing the function looks the most exotic.&lt;/p&gt;

&lt;p&gt;It uses what is known as "guards". A guard is basically a condition, which is placed between &lt;code&gt;|&lt;/code&gt; and &lt;code&gt;=&lt;/code&gt; characters. When the condition is satisfied, a function body that is defined after &lt;code&gt;=&lt;/code&gt; gets executed.&lt;/p&gt;

&lt;p&gt;In our case, the first guard is &lt;code&gt;b == True&lt;/code&gt;. But - just as before - we can write the same condition as simply &lt;code&gt;b&lt;/code&gt;. If &lt;code&gt;b&lt;/code&gt; is True, this condition is satisfied and the function body that returns False will be executed.&lt;/p&gt;

&lt;p&gt;Otherwise (so when &lt;code&gt;b&lt;/code&gt; is not True), the function body that returns True will be executed.&lt;/p&gt;

&lt;p&gt;Interestingly, there is nothing magical about the keyword &lt;code&gt;otherwise&lt;/code&gt;. (Are you noticing a pattern here, where some "feature" of the language is not really a feature, but simply something coded in that language?)&lt;/p&gt;

&lt;p&gt;You can convince yourself that this is true by writing &lt;code&gt;otherwise&lt;/code&gt; in the &lt;code&gt;ghci&lt;/code&gt; console. As a response you will see:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;True
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Yup. &lt;code&gt;otherwise&lt;/code&gt; is nothing more than a regular variable, holding the value True! Just as our &lt;code&gt;x&lt;/code&gt; is!&lt;/p&gt;

&lt;p&gt;So, without the &lt;code&gt;otherwise&lt;/code&gt; our "guarded" version of the function would look like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;
 &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt;
 &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Just as in &lt;code&gt;if then else&lt;/code&gt;, a condition &lt;em&gt;has to&lt;/em&gt; be a Bool value. If the last condition is set to True, like it's the case here, it will always hold and therefore it will act as a catchall case if the guards above it fail. Calling it &lt;code&gt;otherwise&lt;/code&gt; is just done to make this a bit more readable.&lt;/p&gt;

&lt;p&gt;One more thing to mention here is that we used indentation. You see that lines starting with &lt;code&gt;|&lt;/code&gt; characters are moved a bit to the right. If we didn't do it and wrote the code like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;
&lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt;
&lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;we would get an error while loading that file in &lt;code&gt;ghci&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;test.hs:3:1: error: parse error on input ‘|’
 |
3 | | b = False
 | ^
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Indenting code makes it more readable for humans and - as you can see - also helps the compiler understand that a given line is still a part of the definition that began in the previous line.&lt;/p&gt;

&lt;p&gt;How much you indent the code is not important to the compiler - it has to be at least one space. But adding a few more spaces is better to keep the code nicely formatted for humans.&lt;/p&gt;

&lt;p&gt;So we have written &lt;code&gt;myNot&lt;/code&gt; in 3 different ways. Which one you prefer depends on you. Nevertheless, it's extremely valuable to get to know all 3 constructs that we've used - if then else, pattern matching and guards - because they appear almost all the time in Haskell code.&lt;/p&gt;

&lt;p&gt;We used them in separation here, but in the future, you will see that you can mix those constructs in various ways, especially when writing more complex code.&lt;/p&gt;

&lt;h3&gt;
  
  
  Creating Types and Values
&lt;/h3&gt;

&lt;p&gt;So far we have written a custom &lt;code&gt;not&lt;/code&gt; function for the &lt;code&gt;Bool&lt;/code&gt; type. But what if we could recreate the &lt;code&gt;Bool&lt;/code&gt; type itself, as well as its values? Is it even possible?&lt;/p&gt;

&lt;p&gt;Indeed, it's possible and even simple. Let's create a &lt;code&gt;MyBool&lt;/code&gt; type. It will have two values - &lt;code&gt;MyTrue&lt;/code&gt; and &lt;code&gt;MyFalse&lt;/code&gt;. It might seem that we are getting a bit possessive here (wink, wink), but that's only to avoid conflicts with already existing names.&lt;/p&gt;

&lt;p&gt;At the top of our &lt;code&gt;lesson_1.hs&lt;/code&gt; file let's write:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="kr"&gt;data&lt;/span&gt; &lt;span class="kt"&gt;MyBool&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;MyTrue&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="kt"&gt;MyFalse&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Easy right?&lt;/p&gt;

&lt;p&gt;After you load that file in the &lt;code&gt;ghci&lt;/code&gt;, you can run &lt;code&gt;:t MyTrue&lt;/code&gt; to doublecheck that &lt;code&gt;MyTrue&lt;/code&gt; has type &lt;code&gt;MyBool&lt;/code&gt;, mirroring how &lt;code&gt;True&lt;/code&gt; has type &lt;code&gt;Bool&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;MyTrue :: MyBool
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The same is true for &lt;code&gt;MyFalse&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;MyFalse :: MyBool
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Unfortunately, I lied to you &lt;em&gt;a bit&lt;/em&gt;. If you type this in &lt;code&gt;ghci&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;MyTrue
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You will see a mysterious message:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;interactive&amp;gt;:68:1: error:
 • No instance for (Show MyBool) arising from a use of ‘print’
 • In a stmt of an interactive GHCi command: print it
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;It happens because &lt;code&gt;ghci&lt;/code&gt; tries to simply print the value, but... It doesn't know how!&lt;/p&gt;

&lt;p&gt;This is part of the language that will cover in future articles. Luckily we don't have to worry about it for now. Haskell can create sane default for printing, you just have to command it to do that, by adding the following line to type definition:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="kr"&gt;data&lt;/span&gt; &lt;span class="kt"&gt;MyBool&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;MyTrue&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="kt"&gt;MyFalse&lt;/span&gt;
 &lt;span class="kr"&gt;deriving&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;Show&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If you now call &lt;code&gt;ghci&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;MyTrue
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;It will simply print back:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;MyTrue
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As I said - a sane default. In the future, we will learn how to customize that printing capability, but for now, it's perfectly fine.&lt;/p&gt;

&lt;p&gt;You can now write functions that operate on this brand new type, just as we wrote a function for the built-in &lt;code&gt;Bool&lt;/code&gt; type.&lt;/p&gt;

&lt;p&gt;So if we wanted &lt;code&gt;myNot&lt;/code&gt; to work on that custom &lt;code&gt;MyBool&lt;/code&gt; type, we would do it like that:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;MyBool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;MyBool&lt;/span&gt;
&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="kt"&gt;MyTrue&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;MyFalse&lt;/span&gt;
&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="kt"&gt;MyFalse&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;MyTrue&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We simply replaced all occurrences of &lt;code&gt;Bool&lt;/code&gt; with &lt;code&gt;MyBool&lt;/code&gt;, all occurrences of &lt;code&gt;True&lt;/code&gt; with &lt;code&gt;MyTrue&lt;/code&gt;, and all occurrences of &lt;code&gt;False&lt;/code&gt; with &lt;code&gt;MyFalse&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;We now have both a built-in version (&lt;code&gt;Bool&lt;/code&gt;) and a custom version (&lt;code&gt;MyBool&lt;/code&gt;) of a boolean type. Wouldn't it be convenient to write functions to switch between them?&lt;/p&gt;

&lt;p&gt;Let's do it!&lt;/p&gt;

&lt;p&gt;First let's write a &lt;code&gt;boolToMyBool&lt;/code&gt; function. It will take a regular, Haskell &lt;code&gt;Bool&lt;/code&gt; and transform it to our custom &lt;code&gt;MyBool&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;boolToMyBool&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;MyBool&lt;/span&gt;
&lt;span class="n"&gt;boolToMyBool&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="kt"&gt;MyTrue&lt;/span&gt; &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="kt"&gt;MyFalse&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And let's write a function that will do the reverse:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myBoolToBool&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;MyBool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;span class="n"&gt;myBoolToBool&lt;/span&gt; &lt;span class="kt"&gt;MyTrue&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;span class="n"&gt;myBoolToBool&lt;/span&gt; &lt;span class="kt"&gt;MyFalse&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We used two different ways to write a function on purpose here. Note that we wouldn't be able to use &lt;code&gt;if then else&lt;/code&gt; with &lt;code&gt;MyBool&lt;/code&gt; type as a conditional, because it works only on the built-in &lt;code&gt;Bool&lt;/code&gt; type.&lt;/p&gt;

&lt;p&gt;But on the other hand, we can use pattern matching in both, because pattern matching works with custom-defined values without any problems.&lt;/p&gt;

&lt;p&gt;Great. We can now transform back and forth between built-in and custom types. Let's try that.&lt;/p&gt;

&lt;p&gt;Load the file in &lt;code&gt;ghci&lt;/code&gt; with both definitions and run:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;boolToMyBool&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You will see &lt;code&gt;MyTrue&lt;/code&gt; as a response.&lt;/p&gt;

&lt;p&gt;Now let's try to transform the same value back. Let's write:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myBoolToBool&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;boolToMyBool&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You will see &lt;code&gt;True&lt;/code&gt; as the response. &lt;/p&gt;

&lt;p&gt;What happened here is that we converted &lt;code&gt;True&lt;/code&gt; to &lt;code&gt;MyTrue&lt;/code&gt; using the &lt;code&gt;boolToMyBool&lt;/code&gt; function (inside the parenthesis), and then we took that result and converted it back to &lt;code&gt;True&lt;/code&gt; using the &lt;code&gt;myBoolToBool&lt;/code&gt; function, all in a single expression.&lt;/p&gt;

&lt;p&gt;Is it a bit nonsensical example? Perhaps, but it shows us how we can chain multiple function calls.&lt;/p&gt;

&lt;p&gt;In fact, the brackets around the first function call are important.&lt;/p&gt;

&lt;p&gt;Try to run the following in &lt;code&gt;ghci&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myBoolToBool&lt;/span&gt; &lt;span class="n"&gt;boolToMyBool&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The compiler will show a fairly elaborate error message, but if you read it carefully, you will find the following sentence:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;The function ‘myBoolToBool’ is applied to two arguments,
 but its type ‘MyBool -&amp;gt; Bool’ has only one
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Ha, so we found what is the problem. Indeed, our code looks as if we are trying to apply the &lt;code&gt;myBoolToBool&lt;/code&gt; function to two parameters - &lt;code&gt;boolToMyBool&lt;/code&gt; and &lt;code&gt;True&lt;/code&gt;. Remember how &lt;code&gt;f x y&lt;/code&gt; was representing calling a function &lt;code&gt;f&lt;/code&gt; on two parameters? That's exactly what we are doing here! In that case, &lt;code&gt;f&lt;/code&gt; is &lt;code&gt;myBoolToBool&lt;/code&gt;, &lt;code&gt;x&lt;/code&gt; is &lt;code&gt;boolToMyBool&lt;/code&gt; and &lt;code&gt;y&lt;/code&gt; is &lt;code&gt;True&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;We have to show the compiler that we want to apply the &lt;code&gt;myBoolToBool&lt;/code&gt; function to a &lt;em&gt;single&lt;/em&gt; parameter. And that parameter is a result of calling &lt;code&gt;boolToMyBool&lt;/code&gt; on &lt;code&gt;True&lt;/code&gt;. So we wrap that call in parenthesis to make that clearer (both to the compiler and us):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myBoolToBool&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;boolToMyBool&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Can we use those conversion functions for something more practical than needlessly translating booleans back and forth? Absolutely - we can use them to rewrite our &lt;code&gt;myNot&lt;/code&gt; implementation once again.&lt;/p&gt;

&lt;p&gt;We can use the fact that the &lt;code&gt;Bool&lt;/code&gt; type has already the &lt;code&gt;not&lt;/code&gt; function defined. It works exactly how we want, it just operates on different types. So let's take a &lt;code&gt;MyBool&lt;/code&gt; value, convert it to &lt;code&gt;Bool&lt;/code&gt;, use &lt;code&gt;not&lt;/code&gt; on it, and then convert it back to &lt;code&gt;MyBool&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;MyBool&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;MyBool&lt;/span&gt;
&lt;span class="n"&gt;myNot&lt;/span&gt; &lt;span class="n"&gt;mb&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;boolToMyBool&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;not&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;myBoolToBool&lt;/span&gt; &lt;span class="n"&gt;mb&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Let's review step by step how that function works.&lt;/p&gt;

&lt;p&gt;Since it's a function of type &lt;code&gt;MyBool -&amp;gt; MyBool&lt;/code&gt;, its argument is a &lt;code&gt;MyBool&lt;/code&gt; - that's why we called it &lt;code&gt;mb&lt;/code&gt;. We pass that variable to a function - &lt;code&gt;myBoolToBool mb&lt;/code&gt; - and as a result, we are getting something of type &lt;code&gt;Bool&lt;/code&gt;. Then we are applying &lt;code&gt;not&lt;/code&gt; on it, by writing &lt;code&gt;not (myBoolToBool x)&lt;/code&gt;. Note that at this step the type doesn't change - we are feeding &lt;code&gt;not&lt;/code&gt; a &lt;code&gt;Bool&lt;/code&gt; and getting a &lt;code&gt;Bool&lt;/code&gt; again, since &lt;code&gt;not&lt;/code&gt; is of type &lt;code&gt;Bool -&amp;gt; Bool&lt;/code&gt;. At the end we convert back to &lt;code&gt;MyBool&lt;/code&gt;, by writing &lt;code&gt;boolToMyBool (not (myBoolToBool x))&lt;/code&gt; - which is the return value of our function.&lt;/p&gt;

&lt;p&gt;This could be again summarised as follows:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="n"&gt;mb&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;MyBool&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;myBoolToBool&lt;/span&gt; &lt;span class="n"&gt;mb&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;not&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;myBoolToBool&lt;/span&gt; &lt;span class="n"&gt;mb&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Bool&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight haskell"&gt;&lt;code&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;boolToMyBool&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;not&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;myBoolToBool&lt;/span&gt; &lt;span class="n"&gt;mb&lt;/span&gt;&lt;span class="p"&gt;)))&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;MyBool&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This technique of tracking which value has which type is extremely valuable, especially when just starting with Haskell. Whenever you feel lost about how a certain function works, I would encourage you to analyze all the types of all the values in that function. You will discover that when you know all the types well, it's much easier to understand how the code works and what it does.&lt;/p&gt;

&lt;p&gt;This is the second example of a skill that Haskell teaches you, which is immediately transferable to programming in other languages. Even if your day-to-day language is loosely typed and doesn't have types in its actual syntax, you can still use this way of thinking to better understand functions while reading code.&lt;/p&gt;

&lt;p&gt;In time you will discover that this allows you to understand code much faster, especially the code that you haven't written yourself.&lt;/p&gt;

&lt;h3&gt;
  
  
  Conclusion
&lt;/h3&gt;

&lt;p&gt;So we played with Bools in Haskell, serving as our introductory lesson in that language.&lt;/p&gt;

&lt;p&gt;We've learned the basics of Haskell's syntax, we've seen how to create and use functions, and even how to create some simple datatypes.&lt;/p&gt;

&lt;p&gt;In future articles, we will elaborate on those ideas quite a bit, so if you are hooked on Haskell by now (as I hope you are!), I would recommend to follow me on &lt;a href="https://twitter.com/m_podlasin"&gt;Twitter&lt;/a&gt;. I don't run any kind of newsletter email or anything like that, so that's the best way to get notified when a new article drops.&lt;/p&gt;

&lt;p&gt;If you have any questions or comments regarding the article, you can reach me there as well. I would like to keep improving this article so that it serves others as best as possible.&lt;/p&gt;

&lt;p&gt;Thanks for reading and see you soon!&lt;/p&gt;

</description>
      <category>haskell</category>
      <category>functional</category>
      <category>codenewbie</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>I was gone from tech social media for almost half a year. Here is why. (Yes, it was burnout.)</title>
      <dc:creator>mpodlasin</dc:creator>
      <pubDate>Fri, 25 Jun 2021 15:46:16 +0000</pubDate>
      <link>https://forem.com/mpodlasin/i-was-gone-from-tech-social-media-for-almost-half-a-year-here-is-why-yes-it-was-burnout-44ia</link>
      <guid>https://forem.com/mpodlasin/i-was-gone-from-tech-social-media-for-almost-half-a-year-here-is-why-yes-it-was-burnout-44ia</guid>
      <description>&lt;p&gt;I've posted my last tech article on January 24th, 2021.&lt;/p&gt;

&lt;p&gt;I've made my last tweet on January 28th.&lt;/p&gt;

&lt;p&gt;Since then I became silent for almost half a year.&lt;/p&gt;

&lt;p&gt;This article is very important to me because I want to achieve a few things with it:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Explain why I was gone for so long.&lt;/li&gt;
&lt;li&gt;Use it as an opportunity to talk about an &lt;em&gt;extreme&lt;/em&gt; burnout and how to fight it.&lt;/li&gt;
&lt;li&gt;Test with this article if I even want to go back to writing tech-related content.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;If you've ever experienced - or are currently experiencing - burnout, work-related depression, or anything similar, you might find this article relatable. You won't find easy answers in it, because I don't have them. But it may give you some ideas and suggestions to explore further on your own. At least I hope.&lt;/p&gt;

&lt;p&gt;So let's begin!&lt;/p&gt;

&lt;h1&gt;
  
  
  What happened?
&lt;/h1&gt;

&lt;p&gt;Instead of turning this section into an overly long, verbose description of the events, let's focus on the timeline more. I find it quite revealing how things had progressed:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;January 11th, 2021&lt;/strong&gt; - I am making a Twitter thread about burnout. &lt;/p&gt;

&lt;p&gt;This is fascinating to me because at that moment I am still convinced that I am completely and absolutely fine. And yet you can see that my brain is already circulating around the topic of burnout.&lt;/p&gt;

&lt;p&gt;It's as if it is trying to warn me: "man, you have to slow down, otherwise I am going into a shutdown mode soon!".&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;January 14th&lt;/strong&gt; - I am making a Twitter thread about my recent failures related to trying to get into Machine Learning.&lt;/p&gt;

&lt;p&gt;This one is less obvious, but you can still see that my brain continued to focus on negative topics at that time. Burnout, failure, and depression were clearly on my mind. &lt;/p&gt;

&lt;p&gt;And yet, again, at that point I sincerely believed I am "A-okay", not seeing the storm looming just above my head.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;January 24th&lt;/strong&gt; - I am publishing a tech article - the last one in a 3-part series.&lt;/p&gt;

&lt;p&gt;I explicitly state on Twitter that this one was a slog to finish. It's the first article that felt like a pain to get done. I felt no joy in the process and was no longer interested in the topics described in the series.&lt;/p&gt;

&lt;p&gt;Note also that at that time I started making YouTube videos associated with the articles, covering the same concepts in a video form.&lt;/p&gt;

&lt;p&gt;The sheer amount of work - creating an article &lt;em&gt;and&lt;/em&gt; a video almost every week - was so big, that I was basically working all the time. I was spending 8 hours coding at my day job, and then, after the day job was done, I was creating programming-related content.&lt;/p&gt;

&lt;p&gt;So the structure of my day was:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;wake up&lt;/li&gt;
&lt;li&gt;code&lt;/li&gt;
&lt;li&gt;have a meeting about code&lt;/li&gt;
&lt;li&gt;code&lt;/li&gt;
&lt;li&gt;eat crappy takeaway&lt;/li&gt;
&lt;li&gt;write about code&lt;/li&gt;
&lt;li&gt;record talking about code&lt;/li&gt;
&lt;li&gt;sleep&lt;/li&gt;
&lt;li&gt;repeat&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Absolutely unsustainable. And yet even at that point - January 24th - I mostly believed that I am okay. Maybe less motivated and a bit more tired than usual, but nothing crazy.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;February 2nd&lt;/strong&gt; - my team leader writes to me: "Hey I've noticed you seem less energetic &amp;amp; cheerful than you usually are. Is everything going alright? I'm here if there's anything you would like to share."&lt;/p&gt;

&lt;p&gt;I am essentially brushing off his question, saying that I indeed felt less motivated recently, but I will probably feel better after resting on the weekend. &lt;/p&gt;

&lt;p&gt;Oh, how wrong was I...&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;February 8th&lt;/strong&gt; - Monday. I wake up extremely late. Around 3 pm. And I still can't get out of bed. I am just laying there, unable to move at all. Complete shutdown. &lt;/p&gt;

&lt;p&gt;I guess my brain incapacitated me to prevent me from continuing my insane work routine.&lt;/p&gt;

&lt;p&gt;I sleep a bit more, wake up at 5 pm. Since it's winter, it's already getting dark. I am still unable to perform any meaningful tasks. I can't even get out of the bed and wash myself. &lt;/p&gt;

&lt;p&gt;I don't really remember the rest of that day very well. It's likely that I just turned on YouTube or Netflix and that's how I finished the day.&lt;/p&gt;

&lt;p&gt;I provided no info - or even sign of life for that matter - to my team or managers, even though it was a regular workday.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;February 9th&lt;/strong&gt; - Tuesday. The same situation. Waking up late. Not being able to move and do anything meaningful. No shower. No food. Just laying there.&lt;/p&gt;

&lt;p&gt;I manage to motivate myself to contact my boss and ask him for an unpaid leave till the end of the week.&lt;/p&gt;

&lt;p&gt;Everyone at work is super concerned with my situation - I am having conversations with a few people, some on Slack, some on Zoom. Thankfully actually getting a week off turns out to not be a problem at all.&lt;/p&gt;

&lt;h1&gt;
  
  
  How I got out of my burnout
&lt;/h1&gt;

&lt;p&gt;So I hope that by now you realize just how serious my situation was.&lt;/p&gt;

&lt;p&gt;Burnout is a popular word recently, used for a wide variety of conditions. But you can see that in my case it wasn't just simply feeling a bit less motivated or something similar.&lt;/p&gt;

&lt;p&gt;I literally couldn't move or perform the most basic life functions, like cleaning myself, preparing a meal, or even going for a walk.&lt;/p&gt;

&lt;p&gt;I was in some deep, deep s...&lt;/p&gt;

&lt;p&gt;At that point, I was luckily very much aware of the severity of my situation (hard not to be, I guess). &lt;/p&gt;

&lt;p&gt;During my week off I decided to deliberately stay away from anything tech or programming related. No coding, no writing about coding, no twitting about coding. No tech social media at all. Even such little thing as browsing Hacker News - absolutely forbidden.&lt;/p&gt;

&lt;p&gt;I was hoping that this cold turkey tech detox would help. But I was also prepared to seek professional help if after a week I wouldn't feel any better.&lt;/p&gt;

&lt;p&gt;Luckily I did.&lt;/p&gt;

&lt;p&gt;A week later I communicated to my boss that I feel well enough to at least attempt coming back.&lt;/p&gt;

&lt;p&gt;I still took things very, very slow, however. After I came back, I only did coding for work - no side projects or anything like that. &lt;/p&gt;

&lt;p&gt;I was also taking only simpler tasks - the ones I knew I could implement fairly fast and with minimal effort. A complex, big new feature? - pass. A tricky bug to investigate? - pass.&lt;/p&gt;

&lt;p&gt;I also kept staying away from tech social media - both producing content and consuming it. I stopped coding or even thinking about coding after work. Instead, I focused on my non-tech hobbies, which I previously neglected, such as photography.&lt;/p&gt;

&lt;p&gt;And I believe this last thing the most important decision that contributed to my mental health and well-being in the long run.&lt;/p&gt;

&lt;h1&gt;
  
  
  Where I am now and what's next?
&lt;/h1&gt;

&lt;p&gt;Avoiding tech social media and coding beyond the day job worked for me so well, that I did it for nearly half a year. I haven't coded a single side project in that time. I didn't create or read a single tech article (unless it was at work and necessary to do my job). Hell, I haven't even made a single tweet since January!&lt;/p&gt;

&lt;p&gt;And during those last few months, I felt absolutely... amazing. I am now more energetic and effective at my work than before my burnout. I am cranking out issue after issue, solving difficult bugs, contributing to architectural decisions. If you'd see me at my day job, you would never, ever guess that I was in such a bad place just a few months ago.&lt;/p&gt;

&lt;p&gt;Writing this article is the first time I am breaking my "no coding-related activities in my spare time" unspoken rule since my sudden burnout attack.&lt;/p&gt;

&lt;p&gt;If I am being honest, it feels both weird and scary to write this article.&lt;/p&gt;

&lt;p&gt;I know that I have this overly ambitious, creative bug in me. And I am terrified I am awaking it again with this article. I am seriously scared that writing and publishing this single article will again send me on a path of unsustainable workloads and being consumed by programming.&lt;/p&gt;

&lt;p&gt;It seems that some people are more resilient than others and can handle more stress and higher workloads. I see people who work 10 hours a day, create side projects, and write articles regularly on top of that. For someone, it might be funny that I burned out so badly only because I wrote a few articles after work.&lt;/p&gt;

&lt;p&gt;Maybe that's the ultimate lesson though. You have to know yourself and be aware of how much you can handle. And stay honest with yourself to not start biting more than you can chew. &lt;/p&gt;

&lt;p&gt;That's why recreating the timeline of my burnout was so important to me. You can see that as early as few weeks before an actual burnout there were already warning signs present, which I completely ignored. I should have paid more attention to what my brain was telling me.&lt;/p&gt;

&lt;p&gt;So what's next? I don't know. I can say that writing this article felt very good. I guess it was something that I just needed to get off my chest.&lt;/p&gt;

&lt;p&gt;Will I go back to creating actual tech content, however? It's possible. Especially if I manage to find a sustainable tempo and topics which I enjoy writing about.&lt;/p&gt;

&lt;p&gt;But it's also entirely possible that this is the last article I'll ever write.&lt;/p&gt;

&lt;p&gt;And that's fine too.&lt;/p&gt;

&lt;p&gt;Cover Photo by &lt;a href="https://unsplash.com/@jluebke?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;Justin Luebke&lt;/a&gt; on &lt;a href="https://unsplash.com/s/photos/crossroads?utm_source=unsplash&amp;amp;utm_medium=referral&amp;amp;utm_content=creditCopyText"&gt;Unsplash&lt;/a&gt;&lt;/p&gt;

</description>
      <category>watercooler</category>
      <category>mentalhealth</category>
      <category>productivity</category>
      <category>career</category>
    </item>
    <item>
      <title>Generators in JavaScript, Part III - "Advanced" Concepts</title>
      <dc:creator>mpodlasin</dc:creator>
      <pubDate>Sun, 24 Jan 2021 15:56:44 +0000</pubDate>
      <link>https://forem.com/mpodlasin/generators-in-javascript-part-iii-advanced-concepts-ka4</link>
      <guid>https://forem.com/mpodlasin/generators-in-javascript-part-iii-advanced-concepts-ka4</guid>
      <description>&lt;p&gt;This is the last article in our 3 part series, where we are explaining in great detail what are generators and how they work.&lt;/p&gt;

&lt;p&gt;This however doesn't mean that we are finishing dealing with generators just yet. In future articles, as I've been promising for a long time now, we will continue exploring their capabilities, this time in a more practical setting - namely using them with React.&lt;/p&gt;

&lt;p&gt;But before we move on to that, we still need to explain some "advanced" concepts. But don't let the title fool you. The knowledge in this article is absolutely necessary to understand generators deeply. So let's get started!&lt;/p&gt;

&lt;h2&gt;
  
  
  yield expression
&lt;/h2&gt;

&lt;p&gt;So far we only used the &lt;code&gt;yield&lt;/code&gt; keyword either on its own, almost like a &lt;code&gt;return&lt;/code&gt;, or we used it in such a construction:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;variable&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;something&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;But it's important to clarify that you don't have to necessarily write it this way.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;yield something&lt;/code&gt; is an expression, so you can put it wherever an expression would be acceptable in typical JavaScript.&lt;/p&gt;

&lt;p&gt;For example, instead of storing the result of &lt;code&gt;yield something&lt;/code&gt; in a variable, only to later &lt;code&gt;console.log&lt;/code&gt; it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;variable&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;something&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;variable&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;we might have as well simply written it like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;something&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Basically, if there is a place where you would put a variable, you can also use the &lt;code&gt;yield something&lt;/code&gt; expression directly. &lt;/p&gt;

&lt;p&gt;So, for example, all of those examples are correct:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// we used let, instead of const&lt;/span&gt;
&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;x&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;something&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="nx"&gt;someFunction&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;something&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;something&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// do stuff&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After all - as we've seen - &lt;code&gt;yield something&lt;/code&gt; gets "replaced" anyways with the value that you provided as an argument to the &lt;code&gt;next&lt;/code&gt; call. So when writing code with &lt;code&gt;yield&lt;/code&gt; you just have to imagine someone swapping in your code &lt;code&gt;yield something&lt;/code&gt; for an actual value. Does it still look correct? If so, it is also correct with a &lt;code&gt;yield something&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;You have to be careful however when combining &lt;code&gt;yield&lt;/code&gt; with operators, for example with a plus sign.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;yield a + b&lt;/code&gt; actually gets interpreted as &lt;code&gt;yield (a + b)&lt;/code&gt;. If you wanted to yield only &lt;code&gt;a&lt;/code&gt; here, you would have to write &lt;code&gt;(yield a) + b&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;There are some rules of operator precedence, but in my experience, it is best to just get a feel for it, by playing with some examples and getting a lot of practice. Simply make sure to double-check that your code actually yields the values that you are expecting.&lt;/p&gt;

&lt;h2&gt;
  
  
  An iterator is more than just next()...
&lt;/h2&gt;

&lt;p&gt;Before we continue, I have to confess to you something... In my iterators series, I haven't told you &lt;em&gt;the whole&lt;/em&gt; truth about iterators. And now, before we move to generators again, I need to add some things to what I explained so far in my previous articles.&lt;/p&gt;

&lt;p&gt;At this point, you might believe that iterators only possess one method - &lt;code&gt;next&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Although that's the only &lt;em&gt;obligatory&lt;/em&gt; method that they need to have, there are also two methods, which your iterators &lt;em&gt;might&lt;/em&gt; have, if you decide to implement them.&lt;/p&gt;

&lt;p&gt;The first is a &lt;code&gt;return&lt;/code&gt; method. This method is used to notify the iterator, that the consumer has decided to stop the iteration &lt;em&gt;before&lt;/em&gt; it actually finished. It's kind of a declaration that - although the iteration process hasn't fully completed - a consumer doesn't intend to make more &lt;code&gt;next&lt;/code&gt; calls.&lt;/p&gt;

&lt;p&gt;This method is actually called by native JavaScript consumers - like a &lt;code&gt;for ... of&lt;/code&gt; loop - if they stop iteration prematurely. For example when &lt;code&gt;for ... of&lt;/code&gt; loop encounters a &lt;code&gt;break&lt;/code&gt; statement or if an exception is thrown in the loop body.&lt;/p&gt;

&lt;p&gt;Of course, as we said, this method is completely optional, so if a &lt;code&gt;for ... of&lt;/code&gt; loop doesn't find a &lt;code&gt;return&lt;/code&gt; method on its iterator, it will simply do nothing. But if the iterator has such a method, it will be called, to notify it that the iteration process ended faster than expected.&lt;/p&gt;

&lt;p&gt;Let's take a simple infinite iterator, returning integers, starting from zero:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;counterIterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;index&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;

    &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Let's add to it a &lt;code&gt;return&lt;/code&gt; method. Interestingly, &lt;code&gt;return&lt;/code&gt; has to obey the same interface as &lt;code&gt;next&lt;/code&gt;. This means it has to return an object of the shape &lt;code&gt;{ value, done }&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;The only reasonable value for &lt;code&gt;done&lt;/code&gt; here is &lt;code&gt;true&lt;/code&gt; because after &lt;code&gt;return&lt;/code&gt; gets called, the iterator should indeed stop its iteration process. And for a &lt;code&gt;value&lt;/code&gt; let's just stick to good old &lt;code&gt;undefined&lt;/code&gt;. This property will be more important when we move on to generators.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;counterIterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;index&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;

    &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;

    &lt;span class="c1"&gt;// new `return` method&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;return was called&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As you can see, we've also added a log, to find out when that &lt;code&gt;return&lt;/code&gt; method really gets called.&lt;/p&gt;

&lt;p&gt;Let's now run a &lt;code&gt;for ... of&lt;/code&gt; loop with a &lt;code&gt;break&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;counterIterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the loop, we are simply logging the elements returned by the iterator. If numbers returned from it become bigger than 2, we immediately stop the iteration.&lt;/p&gt;

&lt;p&gt;Running this code logs:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;0
1
2
return was called
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So we see that indeed our &lt;code&gt;return&lt;/code&gt; method was called when the &lt;code&gt;break&lt;/code&gt; statement was encountered.&lt;/p&gt;

&lt;p&gt;Let's now try throwing inside the loop:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;try&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;counterIterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="k"&gt;throw&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;error&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;

        &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;catch&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Since we are throwing, we had to wrap our loop in a &lt;code&gt;try-catch&lt;/code&gt; block.&lt;/p&gt;

&lt;p&gt;And no surprises here - the code logs exactly the same output:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;0
1
2
return was called
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So whether it's &lt;code&gt;break&lt;/code&gt; or &lt;code&gt;throw&lt;/code&gt; - if &lt;code&gt;for ... of&lt;/code&gt; loop finishes prematurely, it lets the iterator know by calling its &lt;code&gt;return&lt;/code&gt; method.&lt;/p&gt;

&lt;p&gt;Okay, that's how &lt;code&gt;return&lt;/code&gt; works. But... why it's here in the first place? &lt;code&gt;return&lt;/code&gt; is very useful for doing cleanups. If there is some logic that is &lt;em&gt;critical&lt;/em&gt; for an iterator to perform after the iteration ends, it should be probably put both into &lt;code&gt;return&lt;/code&gt; &lt;em&gt;and&lt;/em&gt; &lt;code&gt;done&lt;/code&gt;. That's because successful iterations - the ones that were running till the end - don't call the &lt;code&gt;return&lt;/code&gt; method, so you need to remember to do a cleanup in both cases.&lt;/p&gt;

&lt;p&gt;We've mentioned that there are &lt;em&gt;two&lt;/em&gt; optional methods that iterators can have. &lt;code&gt;return&lt;/code&gt; is one of them, and the second is &lt;code&gt;throw&lt;/code&gt;. &lt;/p&gt;

&lt;p&gt;&lt;code&gt;throw&lt;/code&gt; also has to obey a similar interface as &lt;code&gt;next&lt;/code&gt; and &lt;code&gt;return&lt;/code&gt;. It's meaning is supposed to be similar to &lt;code&gt;return&lt;/code&gt;. The iterator is informed that the iteration process ends prematurely, but it is also encouraged to raise some kind of an error.&lt;/p&gt;

&lt;p&gt;Intuitively, &lt;code&gt;throw&lt;/code&gt; should be used when something goes really, really wrong. And yet, as we've seen, when &lt;code&gt;for ...of&lt;/code&gt; loop encounters an exception, it calls &lt;code&gt;return&lt;/code&gt;. It turns out that in that case &lt;code&gt;throw&lt;/code&gt; &lt;em&gt;doesn't&lt;/em&gt; get called. That's probably because a typical iterator doesn't really care about &lt;em&gt;why&lt;/em&gt; the iteration process ends earlier than it should - it just does the necessary cleanup and that's it.&lt;/p&gt;

&lt;p&gt;So most of the time, when writing custom iterators, it's perfectly fine to omit &lt;code&gt;throw&lt;/code&gt; and only use &lt;code&gt;return&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;On the other hand, the behavior of generators will actually differ depending on whether we use &lt;code&gt;return&lt;/code&gt; or &lt;code&gt;throw&lt;/code&gt;. We will see that in the following sections.&lt;/p&gt;

&lt;h2&gt;
  
  
  return() with generators
&lt;/h2&gt;

&lt;p&gt;Let's start with running &lt;code&gt;return&lt;/code&gt; on generators first.&lt;/p&gt;

&lt;p&gt;There are no big surprises here. When the generator gets informed via &lt;code&gt;return&lt;/code&gt; call that the iteration process ended early, it just stops from ever returning further values.&lt;/p&gt;

&lt;p&gt;Let's take an infinite "counter" iterator the same as before, but written as a generator:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;counterGenerator&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

    &lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
        &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Let's run it by hand, using &lt;code&gt;next&lt;/code&gt; and &lt;code&gt;return&lt;/code&gt; methods of its iterator:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;counterGenerator&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt; &lt;span class="c1"&gt;// a return method!&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This logs:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="c1"&gt;// logged by `return` call&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So we see, that while we were calling &lt;code&gt;next&lt;/code&gt; methods, the iterator was behaving as usual.&lt;/p&gt;

&lt;p&gt;We then called &lt;code&gt;return&lt;/code&gt;, which immediately resulted in &lt;code&gt;{ value: undefined, done: true }&lt;/code&gt; object. &lt;/p&gt;

&lt;p&gt;And since then, even though we came back to calling the &lt;code&gt;next&lt;/code&gt; method, we couldn't receive further values anymore.&lt;/p&gt;

&lt;p&gt;Now perhaps the iterator doesn't return anything, but the generator itself is still running underneath?&lt;/p&gt;

&lt;p&gt;Let's check it, by adding some logs to the generator function:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;counterGenerator&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

    &lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="c1"&gt;// we are now logging the value&lt;/span&gt;
        &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
        &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
        &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Running the code now results in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="mi"&gt;0&lt;/span&gt;                            &lt;span class="c1"&gt;// from generator&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="mi"&gt;1&lt;/span&gt;                            &lt;span class="c1"&gt;// from generator&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="mi"&gt;2&lt;/span&gt;                            &lt;span class="c1"&gt;// from generator&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So our doubts were unwarranted - the generator actually &lt;em&gt;stops running completely&lt;/em&gt; after we call &lt;code&gt;return&lt;/code&gt; on its iterator.&lt;/p&gt;

&lt;p&gt;Having a &lt;code&gt;return&lt;/code&gt; method on an iterator allowed us to perform some cleanup logic in case the iteration process ended earlier than expected.&lt;/p&gt;

&lt;p&gt;Could we somehow replicate that with generators?&lt;/p&gt;

&lt;p&gt;Indeed, we can use a &lt;code&gt;try-finally&lt;/code&gt; construct for that.&lt;/p&gt;

&lt;p&gt;Let's wrap our generator code in &lt;code&gt;try-finally&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;counterGenerator&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;try&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
            &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;finally&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;finally was called!&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Note that if this was a regular function with a &lt;code&gt;while(true)&lt;/code&gt; loop inside, without any returns or errors, the &lt;code&gt;finally&lt;/code&gt; block would never get executed because we would never finish running the &lt;code&gt;try&lt;/code&gt; block. With generators that's different, because we can now stop executing the &lt;code&gt;try&lt;/code&gt; section "from the outside".&lt;/p&gt;

&lt;p&gt;In our &lt;code&gt;finally&lt;/code&gt; block we have made a simple &lt;code&gt;console.log&lt;/code&gt;. Let's again run the previous &lt;code&gt;next&lt;/code&gt; and &lt;code&gt;return&lt;/code&gt; sequence:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;counterGenerator&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt; &lt;span class="c1"&gt;// a return method&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This logs:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;{ value: 0, done: false }
{ value: 1, done: false }
{ value: 2, done: false }
finally was called!              &amp;lt;- log from finally block
{ value: undefined, done: true }
{ value: undefined, done: true }
{ value: undefined, done: true }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So indeed, the &lt;code&gt;finally&lt;/code&gt; block ran after we've called &lt;code&gt;return&lt;/code&gt; on this generator's iterator. So &lt;code&gt;finally&lt;/code&gt; block is a place that you can use if you want to implement any kind of cleanup logic.&lt;/p&gt;

&lt;p&gt;Now the mystery of why the &lt;code&gt;return&lt;/code&gt; method has to return a &lt;code&gt;{ value, done }&lt;/code&gt; object will be finally (sic!) solved. After all, in regular functions, it's perfectly legal to make a &lt;code&gt;return&lt;/code&gt; statement in a &lt;code&gt;finally&lt;/code&gt; block. Let's try that here, replacing our &lt;code&gt;console.log&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;counterGenerator&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;try&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
            &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;finally&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;123&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Run the code again and you will see in the console:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;123&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="c1"&gt;// result of `return` call&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We see that now the result from the &lt;code&gt;return&lt;/code&gt; method contains an actual value - in this case, a -123 number - instead of &lt;code&gt;undefined&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Ha! So this way the generator can still communicate something to "the outside", even if the iteration process gets somehow interrupted!&lt;/p&gt;

&lt;h2&gt;
  
  
  throw() with generators
&lt;/h2&gt;

&lt;p&gt;Let's now solve the mystery of the &lt;code&gt;throw&lt;/code&gt; method.&lt;/p&gt;

&lt;p&gt;With iterators, it was a bit unclear why actually this method is needed.&lt;/p&gt;

&lt;p&gt;As we've said previously, it's supposed to signalize to the iterator, that the iteration failed in a very bad way and the iterator should raise some kind of error.&lt;/p&gt;

&lt;p&gt;And that's exactly what the generator does!&lt;/p&gt;

&lt;p&gt;Let's wrap our generator code in a &lt;code&gt;try/catch&lt;/code&gt; now, instead of &lt;code&gt;try/finally&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;counterGenerator&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;try&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
            &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="c1"&gt;// now it's a catch&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;catch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;caught error&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;error&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We are prepared to log whatever error will be thrown in our code.&lt;/p&gt;

&lt;p&gt;Let's run the &lt;code&gt;next&lt;/code&gt; calls, but this time we will interrupt them with the &lt;code&gt;throw&lt;/code&gt; method instead of &lt;code&gt;return&lt;/code&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;counterGenerator&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;throw&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt; &lt;span class="c1"&gt;// now it's a throw&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After running this code, you will see:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;{ value: 0, done: false }
{ value: 1, done: false }
{ value: 2, done: false }
caught error undefined           &amp;lt;- log from catch block
{ value: undefined, done: true }
{ value: undefined, done: true }
{ value: undefined, done: true }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So we see that the error was indeed thrown, and that error was... &lt;code&gt;undefined&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;On top of that, just as was the case with the &lt;code&gt;return&lt;/code&gt; method, after calling &lt;code&gt;throw&lt;/code&gt; the generator stops running and it doesn't generate new values anymore.&lt;/p&gt;

&lt;p&gt;We see that the error thrown in the generator was &lt;code&gt;undefined&lt;/code&gt;. Could it possibly be that we can also pass an argument to &lt;code&gt;throw&lt;/code&gt;, which will become our error? Let's try it!&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;counterGenerator&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;throw&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;let's throw a string, why not, it's JS&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We then see in the console:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;{ value: 0, done: false }
{ value: 1, done: false }
{ value: 2, done: false }
caught error let's throw a string, why not, it's JS
{ value: undefined, done: true }
{ value: undefined, done: true }
{ value: undefined, done: true }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So we were right! Whatever you pass into the &lt;code&gt;throw&lt;/code&gt; method as an argument will become the error object that actually gets thrown inside the generator.&lt;/p&gt;

&lt;p&gt;One more thing. Similar to the &lt;code&gt;return&lt;/code&gt; method, a value returned inside the &lt;code&gt;catch&lt;/code&gt; block will become a value that gets returned by the &lt;code&gt;throw&lt;/code&gt; method.&lt;/p&gt;

&lt;p&gt;So this code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;counterGenerator&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;try&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
            &lt;span class="nx"&gt;i&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;catch&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="c1"&gt;// now we return here&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;666&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Will result in this output:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;666&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;      &lt;span class="c1"&gt;// result of `throw` call&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And although it's not visible in this example, I hope it's clear to you exactly in which place the error gets thrown inside our generator. It is exactly the place where the generator gets suspended while waiting for the &lt;code&gt;next&lt;/code&gt; call.&lt;/p&gt;

&lt;p&gt;To show that, let's take this example:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;getNumbers&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

    &lt;span class="k"&gt;try&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;catch&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;We caught error!&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We can start this generator by calling &lt;code&gt;next&lt;/code&gt; for the first time. That &lt;code&gt;next&lt;/code&gt; call returns &lt;code&gt;{ value: 1, done: false }&lt;/code&gt; object and at this point the generator gets suspended on the &lt;code&gt;yield 1;&lt;/code&gt; statement.&lt;/p&gt;

&lt;p&gt;If now the second call to the iterator would be &lt;code&gt;throw&lt;/code&gt;, then the error wouldn't get caught by &lt;code&gt;try-catch&lt;/code&gt;. That's simply because the generator is still on the &lt;code&gt;yield 1;&lt;/code&gt; line, which is not wrapped in a &lt;code&gt;try-catch&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Indeed, running:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumbers&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;throw&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;some error&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;results in an uncaught string  - &lt;code&gt;some error&lt;/code&gt; - appearing in the console.&lt;/p&gt;

&lt;p&gt;If however, you would run &lt;code&gt;next&lt;/code&gt; as a second method, then this second call would return an object &lt;code&gt;{ value: 2, done: false }&lt;/code&gt; and the generator would be suspended on the &lt;code&gt;yield 2;&lt;/code&gt; line.&lt;/p&gt;

&lt;p&gt;If you called the &lt;code&gt;throw&lt;/code&gt; method now, the error &lt;em&gt;would&lt;/em&gt; be caught by &lt;code&gt;try-catch&lt;/code&gt; and you would just see the log from the &lt;code&gt;catch&lt;/code&gt; block.&lt;/p&gt;

&lt;p&gt;So this code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumbers&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;throw&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;some error&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;simply prints:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;We caught error!
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Of course most of the time you won't rely on exactly which statements are supposed to throw. You will just use larger &lt;code&gt;try/catch&lt;/code&gt; blocks. But it's still valuable to understand what exactly is happening here.&lt;/p&gt;

&lt;h2&gt;
  
  
  yield* - yield delegation
&lt;/h2&gt;

&lt;p&gt;By now we got used to the &lt;code&gt;yield&lt;/code&gt; keyword and its behavior doesn't seem strange to us anymore.&lt;/p&gt;

&lt;p&gt;So let's get out of our comfort zone once more and learn about &lt;code&gt;yield*&lt;/code&gt; now.&lt;/p&gt;

&lt;p&gt;Yes, you've read that correctly. Apart from the &lt;code&gt;yield&lt;/code&gt; keyword, you can use also &lt;code&gt;yield*&lt;/code&gt; (`yield with a star character).&lt;/p&gt;

&lt;p&gt;The &lt;code&gt;*&lt;/code&gt; suggests that this construction has something to do with generators. But in fact, it's an operator that works on &lt;em&gt;any&lt;/em&gt; iterable.&lt;/p&gt;

&lt;p&gt;Its mechanism is called "yield delegation". &lt;code&gt;yield*&lt;/code&gt; &lt;em&gt;delegates&lt;/em&gt; execution to another iterable or generator.&lt;/p&gt;

&lt;p&gt;We've started our generators adventure with this simple example:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function* getNumbers() {&lt;br&gt;
    yield 1;&lt;br&gt;
    yield 2;&lt;br&gt;
    yield 3;&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;But using yield delegation we might have written it much simpler:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function* getNumbers() {&lt;br&gt;
    yield* [1, 2, 3];&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Since an array is an iterable, we can call &lt;code&gt;yield*&lt;/code&gt; on it, and at this point, the generator will start behaving as if it was a regular array iterator.&lt;/p&gt;

&lt;p&gt;So running:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
for (let element of getNumbers()) {&lt;br&gt;
    console.log(element)&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;simply logs numbers:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
1&lt;br&gt;
2&lt;br&gt;
3&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;If you think about it, it totally makes sense why another keyword - &lt;code&gt;yield*&lt;/code&gt; - had to be introduced.&lt;/p&gt;

&lt;p&gt;Note that this generator:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function* getNumbers() {&lt;br&gt;
    // look! no star here!&lt;br&gt;
    yield [1, 2, 3];&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;simply emits one value - an array with 3 elements. Running the &lt;code&gt;for ... of&lt;/code&gt; loop on this example results in the following log:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
[ 1, 2, 3 ]&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Only after you use &lt;code&gt;yield*&lt;/code&gt;, the control will be actually &lt;em&gt;delegated&lt;/em&gt; to the array.&lt;/p&gt;

&lt;p&gt;Of course nothing stops us from using &lt;code&gt;yield*&lt;/code&gt; multiple times:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function* getNumbers() {&lt;br&gt;
    yield* [1, 2, 3];&lt;br&gt;
    yield* ['a', 'b', 'c'];&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;which results in:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;&lt;br&gt;
1&lt;br&gt;
2&lt;br&gt;
3&lt;br&gt;
a&lt;br&gt;
b&lt;br&gt;
c&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;We can also combine &lt;code&gt;yield&lt;/code&gt; and &lt;code&gt;yield*&lt;/code&gt; in any way we want:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;`js&lt;br&gt;
function* getNumbers() {&lt;br&gt;
    yield* [1, 2, 3];&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;yield '---';

yield* ['a', 'b', 'c'];
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;}&lt;br&gt;
`&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;which logs:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;`&lt;br&gt;
1&lt;br&gt;
2&lt;/p&gt;

&lt;h2&gt;
  
  
  3
&lt;/h2&gt;

&lt;p&gt;a&lt;br&gt;
b&lt;br&gt;
c&lt;br&gt;
`&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Since generators return iterators and since those iterators are iterables, this means we can use &lt;code&gt;yield*&lt;/code&gt; also on results coming from generators, basically allowing us to nest generators, just like we nest functions.&lt;/p&gt;

&lt;p&gt;Take two generators we already know:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;`js&lt;br&gt;
function* getNumbers() {&lt;br&gt;
    yield -3;&lt;br&gt;
    yield -2;&lt;br&gt;
    yield -1;&lt;br&gt;
}&lt;/p&gt;

&lt;p&gt;function* counterGenerator() {&lt;br&gt;
    let i = 0;&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;while(true) {
    yield i;
    i++;
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;}&lt;br&gt;
`&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;We can easily run them one after another by creating another generator:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function* getNumbersThenCount() {&lt;br&gt;
    yield* getNumbers();&lt;br&gt;
    yield* counterGenerator();&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Running:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
for (let element of getNumbersThenCount()) {&lt;br&gt;
    if (element &amp;gt; 4) {&lt;br&gt;
        break;&lt;br&gt;
    }&lt;br&gt;
    console.log(element);&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;logs a sequence:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
-3 // &amp;lt;- getNumbers()&lt;br&gt;
-2&lt;br&gt;
-1&lt;br&gt;
0  // &amp;lt;- counterGenerator()&lt;br&gt;
1&lt;br&gt;
2&lt;br&gt;
3&lt;br&gt;
4&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Of course in this example, since &lt;code&gt;counterGenerator&lt;/code&gt; is infinite, &lt;code&gt;getNumbersThenCount&lt;/code&gt; is infinite as well. If we wouldn't use &lt;code&gt;break&lt;/code&gt;, it would run forever.&lt;/p&gt;

&lt;h2&gt;
  
  
  Generators as methods &amp;amp; some other syntax issues
&lt;/h2&gt;

&lt;p&gt;I've left this section for the end because it's not really necessary to understand the &lt;em&gt;how&lt;/em&gt; and &lt;em&gt;why&lt;/em&gt; of generators.&lt;/p&gt;

&lt;p&gt;But leaving it out completely would be dishonest and it might lead you to confusion when reading generators written by someone else.&lt;/p&gt;

&lt;p&gt;Let's first start by noting, that you can easily turn object and class methods into generators, simply by prefixing the method name with a &lt;code&gt;*&lt;/code&gt; symbol:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
const object = {&lt;br&gt;
    *generatorMethod() {&lt;br&gt;
        yield 1;&lt;br&gt;
    }&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
class SomeClass {&lt;br&gt;
    *generatorMethod() {&lt;br&gt;
        yield 1;&lt;br&gt;
    }&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;It is also important to stress, that you can easily declare &lt;em&gt;anonymous&lt;/em&gt; generators. This might be handy when you are writing inline generators as arguments to some other functions. Remember our &lt;code&gt;runMaybe&lt;/code&gt; helper? With a little rewrite we could use it with an inline generator like this:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
runMaybe(function*() {&lt;br&gt;
    // do something&lt;br&gt;
})&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Going back to regular generator functions, it turns out, however, that the &lt;code&gt;*&lt;/code&gt; character can be positioned in few different places.&lt;/p&gt;

&lt;p&gt;Throughout this tutorial, we've written generators like this:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function* generator() {&lt;br&gt;
    yield 1;&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;But interestingly, this works as well:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function *generator() {&lt;br&gt;
    yield 1;&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Note how the &lt;code&gt;*&lt;/code&gt; character changed position.&lt;/p&gt;

&lt;p&gt;Oh, and this works as well...&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function * generator() {&lt;br&gt;
    yield 1;&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Uuuuuhm. And this also...&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function*generator() {&lt;br&gt;
    yield 1;&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;So this funny "looseness" of syntax means that you can see generators written in many ways. So don't get confused by it. In all of those cases, the behavior is exactly the same.&lt;/p&gt;

&lt;p&gt;A similar thing applies to anonymous generator functions.&lt;/p&gt;

&lt;p&gt;And in fact, &lt;code&gt;yield*&lt;/code&gt; expressions are equally "loose".&lt;/p&gt;

&lt;p&gt;So this works:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function* getNumbers() {&lt;br&gt;
    yield* [1, 2, 3];&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;But also this:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function* getNumbers() {&lt;br&gt;
    // * changed position here&lt;br&gt;
    yield *[1, 2, 3];&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;And this:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function* getNumbers() {&lt;br&gt;
    yield * [1, 2, 3];&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;And - you guessed it! - this:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function* getNumbers() {&lt;br&gt;
    yield*[1, 2, 3];&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;In his phenomenal &lt;a href="https://github.com/getify/You-Dont-Know-JS"&gt;You Don't Know JS&lt;/a&gt;, the author &lt;a href="https://twitter.com/getify"&gt;Kyle Simpson&lt;/a&gt; recommends using the following syntax:&lt;/p&gt;

&lt;p&gt;For declaring generators:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;`js&lt;br&gt;
function *someGenerator() {&lt;/p&gt;

&lt;p&gt;}&lt;br&gt;
`&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;For yield delegation:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function *someGenerator() {&lt;br&gt;
    yield *someIterable;&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;However, as you've seen in these tutorials, I prefer:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;`js&lt;br&gt;
function* someGenerator() {&lt;/p&gt;

&lt;p&gt;}&lt;br&gt;
`&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;And for yield delegation:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&lt;/code&gt;&lt;code&gt;js&lt;br&gt;
function* someGenerator() {&lt;br&gt;
    yield* someIterable;&lt;br&gt;
}&lt;br&gt;
&lt;/code&gt;&lt;code&gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;That's because I see the &lt;code&gt;function*&lt;/code&gt; string as a type declaration. So for me:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;function&lt;/code&gt; = a regular function,&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;function*&lt;/code&gt; = a generator function.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Similarly, I like to think of a &lt;code&gt;yield*&lt;/code&gt; as a single keyword (and hence written together), separate from &lt;code&gt;yield&lt;/code&gt;. That's because it is basically a completely different mechanism, so in my mind, it makes sense to have a separate keyword for it.&lt;/p&gt;

&lt;p&gt;But Kyle has some equally strong arguments, which you can read about &lt;a href="https://github.com/getify/You-Dont-Know-JS/blob/1st-ed/es6%20%26%20beyond/ch3.md#generators"&gt;here&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;So ultimately just choose what you prefer and stick with it. In the end, it doesn't really matter. What's important is that you actually understand deeply the mechanisms under that syntax.&lt;/p&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;Uhh... That was a lot!&lt;/p&gt;

&lt;p&gt;But I hope that at this point you feel that you understand generators very, very deeply.&lt;/p&gt;

&lt;p&gt;And I am beyond excited, because finally in the future article we will be able to put all this knowledge into practice, by combining generators with React!&lt;/p&gt;

&lt;p&gt;So if you don't want to miss those future articles, subscribe to me on &lt;a href="https://twitter.com/m_podlasin"&gt;Twitter&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Thanks for reading!&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>codenewbie</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>Generators in JavaScript, Part II - Simple use-case</title>
      <dc:creator>mpodlasin</dc:creator>
      <pubDate>Fri, 08 Jan 2021 13:56:18 +0000</pubDate>
      <link>https://forem.com/mpodlasin/generators-in-javascript-part-ii-simple-use-case-g6f</link>
      <guid>https://forem.com/mpodlasin/generators-in-javascript-part-ii-simple-use-case-g6f</guid>
      <description>&lt;p&gt;The behavior of generators that we've described in the &lt;a href="https://mpodlasin.com/articles/generators-i"&gt;previous article&lt;/a&gt; is not complicated, but it is certainly surprising and might be difficult to grasp at the very beginning.&lt;/p&gt;

&lt;p&gt;So in this article, instead of introducing more concepts, we will pause a bit and use only what we've learned to this point while discovering a cool use-case for generators.&lt;/p&gt;

&lt;p&gt;Let's say that we have a function like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;maybeAddNumbers&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberA&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberB&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Functions &lt;code&gt;maybeGetNumberA&lt;/code&gt; and &lt;code&gt;maybeGetNumberB&lt;/code&gt; return numbers, but sometimes they might also return &lt;code&gt;null&lt;/code&gt; or &lt;code&gt;undefined&lt;/code&gt;. That's what "maybe" in their names signalizes. &lt;/p&gt;

&lt;p&gt;When that's the case, we shouldn't try to add those values (for example a number and &lt;code&gt;null&lt;/code&gt;), but rather bail out immediately and just return, let's say, &lt;code&gt;null&lt;/code&gt; again. After all, it's better to return &lt;code&gt;null&lt;/code&gt; here, rather than some unpredictable value resulting from adding &lt;code&gt;null/undefined&lt;/code&gt; with a number or with another &lt;code&gt;null/undefined&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;So we have to add a check that makes sure those numbers are actually defined:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;maybeAddNumbers&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberA&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberB&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This works okay, but if &lt;code&gt;a&lt;/code&gt; is either a &lt;code&gt;null&lt;/code&gt; or an &lt;code&gt;undefined&lt;/code&gt;, there is really no point in calling the &lt;code&gt;maybeGetNumberB&lt;/code&gt; function at all. That's because we already know that we will return a &lt;code&gt;null&lt;/code&gt; anyways.&lt;/p&gt;

&lt;p&gt;So let's rewrite the function again:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;maybeAddNumbers&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberA&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberB&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;b&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Uuuh. From an easy to read 3-liner, this quickly grew to 10 lines of code (not counting the empty lines). This function is now filled with &lt;code&gt;if&lt;/code&gt; cases, which you have to get through in order to understand what it does.&lt;/p&gt;

&lt;p&gt;And this is just a toy example! You can imagine that in actual codebases, which contain much more complex logic, those checks would become even more complicated.&lt;/p&gt;

&lt;p&gt;So what if we could use generators here and bring back the code to its simpler form? &lt;/p&gt;

&lt;p&gt;Take a look at this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;maybeAddNumbers&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberA&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberB&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;What if we could give that &lt;code&gt;yield &amp;lt;something&amp;gt;&lt;/code&gt; expression the functionality of checking if &lt;code&gt;&amp;lt;something&amp;gt;&lt;/code&gt; is an actual value and not &lt;code&gt;null&lt;/code&gt; or &lt;code&gt;undefined&lt;/code&gt;?&lt;/p&gt;

&lt;p&gt;If it turned out that &lt;code&gt;&amp;lt;something&amp;gt;&lt;/code&gt; is &lt;code&gt;null&lt;/code&gt; or &lt;code&gt;undefined&lt;/code&gt;, we would just bail early and return &lt;code&gt;null&lt;/code&gt;, exactly like in the more verbose version of our code.&lt;/p&gt;

&lt;p&gt;This way we could write code that looks &lt;em&gt;almost&lt;/em&gt; as if it deals only with actual, defined values.&lt;br&gt;
It's the generator itself that would check for you if that's really the case and it would act accordingly! Sounds magical, doesn't it?&lt;/p&gt;

&lt;p&gt;And yet it's not only possible but also very easy to write!&lt;/p&gt;

&lt;p&gt;Of course, generators themselves don't possess this functionality. They just return iterators and optionally allow you to inject some values back into the generator.&lt;/p&gt;

&lt;p&gt;So we will have to write a wrapper - let's call it &lt;code&gt;runMaybe&lt;/code&gt; - which will give the generator this capability.&lt;/p&gt;

&lt;p&gt;So instead of calling the function directly:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;maybeAddNumbers&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We will be calling it as an argument to that wrapper:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;runMaybe&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;maybeAddNumbers&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is a pattern that you will see incredibly often with generators.&lt;/p&gt;

&lt;p&gt;Generators by themselves don't do much, but by writing custom wrappers like this one, you can grant generators custom behaviors! And that's precisely what we will do right now.&lt;/p&gt;

&lt;p&gt;So &lt;code&gt;runMaybe&lt;/code&gt; obviously is a function and it accepts one argument - an iterator produced by the generator:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;runMaybe&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;

&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We will run this iterator in a &lt;code&gt;while&lt;/code&gt; loop. In order to do that, we need to call the iterator for the first time and start checking its &lt;code&gt;done&lt;/code&gt; property:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;runMaybe&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

    &lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;

    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now inside a loop we have two options. If &lt;code&gt;result.value&lt;/code&gt; is &lt;code&gt;null&lt;/code&gt; or &lt;code&gt;undefined&lt;/code&gt; we want to break the iteration process immediately and return &lt;code&gt;null&lt;/code&gt;. Let's do that:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;runMaybe&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

    &lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You can see that we are immediately stopping the iteration with the &lt;code&gt;return&lt;/code&gt; and we are returning a &lt;code&gt;null&lt;/code&gt; from our wrapper.&lt;/p&gt;

&lt;p&gt;If however &lt;code&gt;result.value&lt;/code&gt; is an actual, defined value, we want to "give it back" to the generator. &lt;/p&gt;

&lt;p&gt;For example in &lt;code&gt;yield maybeGetNumberA()&lt;/code&gt;, if it turns out that &lt;code&gt;maybeGetNumberA()&lt;/code&gt; is actually a number, we just want to replace &lt;code&gt;yield maybeGetNumberA()&lt;/code&gt; with the value of the number itself.&lt;/p&gt;

&lt;p&gt;Even more specifically, if &lt;code&gt;maybeGetNumberA()&lt;/code&gt; evaluated to, say, number 5, we would like to change &lt;code&gt;const a = yield maybeGetNumberA();&lt;/code&gt; into &lt;code&gt;const a = 5;&lt;/code&gt;. As you can see, we don't want to change the yielded value in any way, but simply pass it &lt;em&gt;back&lt;/em&gt; to the generator.&lt;/p&gt;

&lt;p&gt;We remember that we can replace &lt;code&gt;yield &amp;lt;something&amp;gt;&lt;/code&gt; with some value by passing that value as an argument to the iterators &lt;code&gt;next&lt;/code&gt; method. So let's do that!&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;runMaybe&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

    &lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;

        &lt;span class="c1"&gt;// we are passing result.value back&lt;/span&gt;
        &lt;span class="c1"&gt;// to the generator&lt;/span&gt;
        &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And as you can see, the new result gets now stored in the &lt;code&gt;result&lt;/code&gt; variable again. We've specifically declared &lt;code&gt;result&lt;/code&gt; with &lt;code&gt;let&lt;/code&gt; so that it's possible.&lt;/p&gt;

&lt;p&gt;We are almost there - if at any point our generator encounters a &lt;code&gt;null/undefined&lt;/code&gt; when yielding a value, we just return a &lt;code&gt;null&lt;/code&gt; from our &lt;code&gt;runMaybe&lt;/code&gt; wrapper.&lt;/p&gt;

&lt;p&gt;But we need to return something also if the iteration process finishes without encountering any &lt;code&gt;null/undefined&lt;/code&gt; values. After all, if we receive two actual numbers in our generator, we want to return their sum from the wrapper!&lt;/p&gt;

&lt;p&gt;Our &lt;code&gt;maybeAddNumbers&lt;/code&gt; generator ends with a &lt;code&gt;return&lt;/code&gt; statement.&lt;/p&gt;

&lt;p&gt;We remember that &lt;code&gt;return &amp;lt;something&amp;gt;&lt;/code&gt; in a generator causes its iterator to return an object &lt;code&gt;{ value: &amp;lt;something&amp;gt;, done: true }&lt;/code&gt; from a &lt;code&gt;next&lt;/code&gt; call.&lt;/p&gt;

&lt;p&gt;When this happens, &lt;code&gt;while&lt;/code&gt; loop will stop running, because &lt;code&gt;done&lt;/code&gt; property will be set to &lt;code&gt;true&lt;/code&gt;. But that last returned value (in our specific case &lt;code&gt;a + b&lt;/code&gt; value) still will be stored in the &lt;code&gt;result.value&lt;/code&gt; property! So at the end we can simply return it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;runMaybe&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

    &lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;

        &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

    &lt;span class="c1"&gt;// just return the last value&lt;/span&gt;
    &lt;span class="c1"&gt;// after the iterator is done&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And... that's it!&lt;/p&gt;

&lt;p&gt;Let's create dummy &lt;code&gt;maybeGetNumberA&lt;/code&gt; and &lt;code&gt;maybeGetNumberB&lt;/code&gt; functions. Let's make them return actual numbers first:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberA&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberB&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If we run our code now and log the results:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;maybeAddNumbers&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberA&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberB&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;runMaybe&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;maybeAddNumbers&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We will see - as expected - number 15 in the console.&lt;/p&gt;

&lt;p&gt;Let's however change one of the added numbers to &lt;code&gt;null&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberA&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberB&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now running the code logs &lt;code&gt;null&lt;/code&gt;!&lt;/p&gt;

&lt;p&gt;It was however important to us to make sure that &lt;code&gt;maybeGetNumberB&lt;/code&gt; function doesn't called when the first function - &lt;code&gt;maybeGetNumberA&lt;/code&gt; - returns &lt;code&gt;null/undefined&lt;/code&gt;. So let's double-check if we really succeeded.&lt;/p&gt;

&lt;p&gt;We can do it simply by adding a &lt;code&gt;console.log&lt;/code&gt; to the second function:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberA&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberB&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;B&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If we wrote our &lt;code&gt;runMaybe&lt;/code&gt; helper correctly, the letter &lt;code&gt;B&lt;/code&gt; should &lt;em&gt;not&lt;/em&gt; appear in the console when running this example.&lt;/p&gt;

&lt;p&gt;And indeed, if you run the code now, you will simply see &lt;code&gt;null&lt;/code&gt; in the console, and nothing else. This means that our helper actually stops running the generator after it encounters a &lt;code&gt;null/undefined&lt;/code&gt; value.&lt;/p&gt;

&lt;p&gt;Our code also works as intended - by logging &lt;code&gt;null&lt;/code&gt; - in any of those combinations:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberA&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberB&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberA&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberB&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberA&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberB&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;etc.&lt;/p&gt;

&lt;p&gt;The power of this example doesn't lay however in running this particular code.&lt;/p&gt;

&lt;p&gt;It lays in the fact that we've created a &lt;em&gt;general&lt;/em&gt; helper, which can handle &lt;em&gt;any&lt;/em&gt; generator that potentially yields &lt;code&gt;null/undefined&lt;/code&gt; values.&lt;/p&gt;

&lt;p&gt;For example if we wrote a more complex function:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;maybeAddFiveNumbers&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberA&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberB&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;c&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberC&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;d&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberD&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;e&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;maybeGetNumberE&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;a&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;b&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;c&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;d&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="nx"&gt;e&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We can run it in our &lt;code&gt;runMaybe&lt;/code&gt; wrapper as well without any issue!&lt;/p&gt;

&lt;p&gt;In fact, our wrapper doesn't even rely on the fact that in our examples those functions are returning numbers. Note that in &lt;code&gt;runMaybe&lt;/code&gt; we don't mention the number type at all. So no matter what kind of values you are using in your generator - numbers, strings, objects, arrays, more complex data structures - it will still work with our helper!&lt;/p&gt;

&lt;p&gt;This is exactly what developers find exciting about generators. They allow you to introduce custom functionality to the code that looks very regular (apart from those &lt;code&gt;yield&lt;/code&gt; calls of course). You just need to create a wrapper that iterates over a generator in a particular way. This way, the wrapper basically "grants" the generator custom functionality!&lt;/p&gt;

&lt;p&gt;And that functionality could be literally anything you want. Generators introduce potentially endless possibilities and the only limitation are our imaginations! &lt;/p&gt;

&lt;p&gt;And in the following articles, we will keep exploring those possibilities, especially in combination with React. So if this sounds interesting to you, follow me on &lt;a href="https://twitter.com/m_podlasin"&gt;Twitter&lt;/a&gt; to not miss those future articles.&lt;/p&gt;

&lt;p&gt;Thanks for reading!&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>codenewbie</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>Generators in JavaScript, Part I - Basics</title>
      <dc:creator>mpodlasin</dc:creator>
      <pubDate>Mon, 21 Dec 2020 20:26:31 +0000</pubDate>
      <link>https://forem.com/mpodlasin/generators-in-javascript-part-i-basics-51kg</link>
      <guid>https://forem.com/mpodlasin/generators-in-javascript-part-i-basics-51kg</guid>
      <description>&lt;p&gt;In this series I will teach you basically everything there is to know about generators in JavaScript - what they are, how to use them, and - as usual - all the intricacies involved. And as always, we will begin with some basics, to give you an overview of what the generators are.&lt;/p&gt;

&lt;p&gt;This series doesn't assume &lt;em&gt;any&lt;/em&gt; previous knowledge about generators. However, it does assume a very solid knowledge of iterables and iterators in JavaScript. If you don't know iterables/iterators, or don't really feel confident using them, make sure to check out my &lt;a href="https://mpodlasin.com/articles/iterables-and-iterators"&gt;previous article&lt;/a&gt;, which covers them in-depth.&lt;/p&gt;

&lt;p&gt;Know the prerequisites? Awesome! You are ready to dive into the world of generators. It is a strange, strange world, where many things are completely different from what you are used to in a regular JavaScript code. &lt;/p&gt;

&lt;p&gt;But the actual mechanism is very simple, and even after reading this first article, you will feel confident in your capability to actually use generators by yourself.&lt;/p&gt;

&lt;p&gt;So let's get started!&lt;/p&gt;

&lt;h2&gt;
  
  
  Motivation
&lt;/h2&gt;

&lt;p&gt;"But why would I even want to learn about using generators?" - you might ask.&lt;/p&gt;

&lt;p&gt;And that's a very fair question. Indeed, generators are still a fairly exotic feature, not used very commonly in most of the codebases.&lt;/p&gt;

&lt;p&gt;But there &lt;em&gt;are&lt;/em&gt; problems which can be solved with generators surprisingly elegantly. And indeed, in the next article, I will show just such an example. And after we master the generators, we will actually try to combine them with React to create code that is highly superior to "hooks-only" code. This, hopefully, will inspire you to seek your own use-cases for generators.&lt;/p&gt;

&lt;p&gt;But don't think for a second that generators are still somehow "experimental". There are a lot of projects used in production codebases that lean on generators heavily. &lt;/p&gt;

&lt;p&gt;I guess the most popular in the React world is &lt;a href="https://redux-saga.js.org/"&gt;redux-saga&lt;/a&gt; package, which is a middleware for Redux, allowing you to write side effects code that is extremely readable and extremely testable at the same time (which doesn't happen that often!). &lt;/p&gt;

&lt;p&gt;I hope that this convinced you that it is absolutely worth learning generators. Are you now excited to study them? Let's do it then!&lt;/p&gt;

&lt;h2&gt;
  
  
  Introduction
&lt;/h2&gt;

&lt;p&gt;If I was tasked with explaining generators in only one sentence, I would probably write - "it is a syntax sugar for producing iterators". Of course, this doesn't even come close to covering everything that generators are and can do. But it is not very far from the truth.&lt;/p&gt;

&lt;p&gt;Let's take a basic, regular function, simply returning a number:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If we were to type it using TypeScript, we would say that it returns a &lt;code&gt;number&lt;/code&gt; type:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;():&lt;/span&gt; &lt;span class="kr"&gt;number&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In order to change a function into a generator function, we just need to add a &lt;code&gt;*&lt;/code&gt; sign after the &lt;code&gt;function&lt;/code&gt; keyword:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;():&lt;/span&gt; &lt;span class="nx"&gt;number&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;But if you really were to do that in TypeScript, the compiler would start to complain. Indeed, a generator function doesn't simply return a value that is being returned in its body. &lt;/p&gt;

&lt;p&gt;It instead returns an iterator!&lt;/p&gt;

&lt;p&gt;If you would change the typings this way:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;():&lt;/span&gt; &lt;span class="nx"&gt;Iterator&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="kr"&gt;number&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;TypeScript compiler would allow that without any issues.&lt;/p&gt;

&lt;p&gt;But that's TypeScript. Let's test if &lt;code&gt;function*&lt;/code&gt; really returns an iterator in pure JavaScript.&lt;/p&gt;

&lt;p&gt;We can check it for example by trying to call the &lt;code&gt;next&lt;/code&gt; method on the "thing" returned from the generator:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;probablyIterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;probablyIterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This not only works but it also logs &lt;code&gt;{ value: 5, done: true }&lt;/code&gt; to the console.&lt;/p&gt;

&lt;p&gt;It's actually very reasonable behavior. In a sense, a function is an iterable that just returns one value and then is finished.&lt;/p&gt;

&lt;p&gt;But would it be possible to return multiple values from a generator function? &lt;/p&gt;

&lt;p&gt;The first thing that might've come to your mind is to use multiple returns:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now, this looks like blasphemy for someone used to regular functions. But I told you, we are in a completely different world now! Everything is possible.&lt;/p&gt;

&lt;p&gt;However... this doesn't work. Let's run it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You will see the following result in the console:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So we only got our first value, and after that, the iterator is stuck in it's "done" state. Interestingly the returned value is accessible only one time for us - further &lt;code&gt;next&lt;/code&gt; calls just return &lt;code&gt;undefined&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;And this behavior is actually very reasonable. It obeys a basic rule true for &lt;em&gt;all&lt;/em&gt; functions - &lt;code&gt;return&lt;/code&gt; always stops executing the function body, even if there is some code after the &lt;code&gt;return&lt;/code&gt; statement. This is true also for generator functions.&lt;/p&gt;

&lt;p&gt;But &lt;em&gt;there is&lt;/em&gt; a way to "return" multiple values from our generator. Exactly for that purpose the keyword &lt;code&gt;yield&lt;/code&gt; was introduced. Let's try that:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now let's run our code again:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A success! Now we get the following result:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So yielding values in a generator allows you to create an iterator that will return multiple values.&lt;/p&gt;

&lt;p&gt;What happens if we call the &lt;code&gt;next&lt;/code&gt; method more times after that? It behaves like any typical iterator by always returning a &lt;code&gt;{ value: undefined, done: true }&lt;/code&gt; object.&lt;/p&gt;

&lt;p&gt;Note now that the last line in our generator is also a &lt;code&gt;yield&lt;/code&gt;. Would it make any difference if we changed it to a &lt;code&gt;return&lt;/code&gt;? Let's check&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="c1"&gt;// note that we used a `return` here!&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This code outputs:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;  &lt;span class="c1"&gt;// now done is true here!&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Hmm. Interesting. So it does basically the same thing, but the &lt;code&gt;done&lt;/code&gt; property gets set to &lt;code&gt;true&lt;/code&gt; one step earlier.&lt;/p&gt;

&lt;p&gt;You probably remember that the &lt;code&gt;done&lt;/code&gt; property in the returned object basically decides whether the &lt;code&gt;for ... of&lt;/code&gt; loop should continue running or not. &lt;/p&gt;

&lt;p&gt;So let's check how our two versions of the &lt;code&gt;getNumber&lt;/code&gt; generator behave with &lt;code&gt;for ... of&lt;/code&gt; loops.&lt;/p&gt;

&lt;p&gt;First let's run the version with 3 yields:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After running this code, we get:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="mi"&gt;1&lt;/span&gt;
&lt;span class="mi"&gt;2&lt;/span&gt;
&lt;span class="mi"&gt;3&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;No surprises really, that's how an iterator should behave.&lt;/p&gt;

&lt;p&gt;Now let's do the same but for a generator with 2 yields and 1 return:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="c1"&gt;// only this line changed&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;What we get:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="mi"&gt;1&lt;/span&gt;
&lt;span class="mi"&gt;2&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Huh. Very curious. But if you think about it, this is really just how iterators behave with the &lt;code&gt;for ... of&lt;/code&gt; loop. The &lt;code&gt;done&lt;/code&gt; property decides whether the next iteration step should be run or not.&lt;/p&gt;

&lt;p&gt;Take a look at how in the iterables article we simulated the &lt;code&gt;for ... of&lt;/code&gt; loop with a &lt;code&gt;while&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="k"&gt;while&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

    &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In that code, if you would get a &lt;code&gt;{ value: 3, done: true }&lt;/code&gt; object from the &lt;code&gt;iterator.next()&lt;/code&gt; call, the 3 would also never appear in the console. &lt;/p&gt;

&lt;p&gt;That's because before &lt;code&gt;console.log(element)&lt;/code&gt; gets called, we first have a &lt;code&gt;!result.done&lt;/code&gt; condition. Since this condition is false for the &lt;code&gt;{ value: 3, done: true }&lt;/code&gt; object, &lt;code&gt;while&lt;/code&gt; body would not be executed for the number 3.&lt;/p&gt;

&lt;p&gt;And &lt;code&gt;for ... of&lt;/code&gt; loops works in exactly the same way.&lt;/p&gt;

&lt;p&gt;So the rule is fairly simple - do you want a value to appear in a &lt;code&gt;for ... of&lt;/code&gt; loop? &lt;code&gt;yield&lt;/code&gt; it!&lt;/p&gt;

&lt;p&gt;Do you want to return it from a generator, but not include it in a &lt;code&gt;for ... of&lt;/code&gt; iteration? &lt;code&gt;return&lt;/code&gt; it!&lt;/p&gt;

&lt;h2&gt;
  
  
  Control flow in generators
&lt;/h2&gt;

&lt;p&gt;At this point, we must clarify that in a generator function you can use all the typical control flow constructions.&lt;/p&gt;

&lt;p&gt;For example, you might choose which number to yield based on an argument passed to the generator:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;beWeird&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

    &lt;span class="k"&gt;if&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;beWeird&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;100&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

    &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Calling &lt;code&gt;getNumber(false)&lt;/code&gt; will create an iterator that returns numbers: 1, 2, 3.&lt;/p&gt;

&lt;p&gt;Calling &lt;code&gt;getNumber(true)&lt;/code&gt; will create an iterator that returns numbers: 1, -100, 3.&lt;/p&gt;

&lt;p&gt;Not only that, you can even use loops in generators! And that's actually where their real power comes in.&lt;/p&gt;

&lt;p&gt;In our iterables article, we've created an infinite iterator, which was generating numbers 0, 1, 2, 3, ... - up to infinity. It wasn't too difficult, but it also wasn't the most readable code ever.&lt;/p&gt;

&lt;p&gt;Now we can do that with a generator in just few simple lines:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;counterGenerator&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

    &lt;span class="k"&gt;while&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
        &lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We simply start with an &lt;code&gt;index&lt;/code&gt; set to 0. We then run an infinite &lt;code&gt;while(true)&lt;/code&gt; loop. In that loop, we &lt;code&gt;yield&lt;/code&gt; current &lt;code&gt;index&lt;/code&gt; and then we simply bump that &lt;code&gt;index&lt;/code&gt; by one. This way, in the following step, &lt;code&gt;index&lt;/code&gt; will be yielded with a new value.&lt;/p&gt;

&lt;p&gt;Beautifully simple, right?&lt;/p&gt;

&lt;p&gt;This is the exact example that literally blew my mind when I was first learning generators. I hope that it blows your mind as well, at least a little bit.&lt;/p&gt;

&lt;p&gt;Just look how far we've come - we were used to functions that can only ever return a single value. And now we are writing a function that "returns" basically... forever!&lt;/p&gt;

&lt;h2&gt;
  
  
  Sending values to a generator
&lt;/h2&gt;

&lt;p&gt;On those first, simple examples we've seen that we can use generators to create typical iterators.&lt;/p&gt;

&lt;p&gt;But it turns out that an iterator returned from a generator is a bit strange. It allows you to... pass some values back to the generator as well!&lt;/p&gt;

&lt;p&gt;Let's enhance our previous generator example:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;first&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;second&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;third&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As you can see, we are still simply yielding numbers from the generator, but we also assign to variables whatever those &lt;code&gt;yield &amp;lt;number&amp;gt;&lt;/code&gt; expressions evaluate to.&lt;/p&gt;

&lt;p&gt;Obviously, at the moment those variables are not used in any way. For the tutorial purposes, we will be simply logging them, but you could of course do with them whatever you want. &lt;/p&gt;

&lt;p&gt;We will also put an additional log at the very beginning of the function.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;start&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;first&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;first&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;second&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;second&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;third&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;yield&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;third&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the rest of this section, we will be running that exact generator multiple times. I would therefore advise you to copy this code somewhere, or just open this article again in a second browser tab. &lt;/p&gt;

&lt;p&gt;It will be &lt;em&gt;much&lt;/em&gt; easier for you to understand what is happening if you look at this generator as often as possible while we run the examples!&lt;/p&gt;

&lt;p&gt;So let's run this new generator just as we did the previous one.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;What we get is:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start
1
undefined
2
undefined
3
undefined
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I hope it's clear which logs come from the generator itself and which come from the &lt;code&gt;for ... of&lt;/code&gt; loop. Just to make sure, here are the answers:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start          &amp;lt;- generator
1              &amp;lt;- loop
undefined      &amp;lt;- generator
2              &amp;lt;- loop
undefined      &amp;lt;- generator
3              &amp;lt;- loop
undefined      &amp;lt;- generator
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So apparently &lt;code&gt;yield &amp;lt;number&amp;gt;&lt;/code&gt; statements just evaluate to &lt;code&gt;undefined&lt;/code&gt;. But we can change that!&lt;/p&gt;

&lt;p&gt;To do that, we will have to abandon the &lt;code&gt;for ... of&lt;/code&gt; loop and consume the iterator by hand.&lt;/p&gt;

&lt;p&gt;Let's just call the &lt;code&gt;next&lt;/code&gt; method of the iterator 4 times, to get our 3 numbers and the last object with &lt;code&gt;done&lt;/code&gt; set to &lt;code&gt;true&lt;/code&gt;. We will log every result coming from the &lt;code&gt;next&lt;/code&gt; call.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After running that (with the generator unchanged), we get:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start
{ value: 1, done: false }
undefined
{ value: 2, done: false }
undefined
{ value: 3, done: false }
undefined
{ value: undefined, done: true }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So not much changed here - &lt;code&gt;undefined&lt;/code&gt; values are still here. We just swapped numbers from a &lt;code&gt;for ... of&lt;/code&gt; loop to logging whole objects coming from &lt;code&gt;next&lt;/code&gt; calls.&lt;/p&gt;

&lt;p&gt;Generators utilize in a smart way the flexibility of an iterator interface. After all, an iterator has to have a &lt;code&gt;next&lt;/code&gt; method, returning an object of shape &lt;code&gt;{ done, value }&lt;/code&gt;. But nobody said that this method can't accept some arguments! A &lt;code&gt;next&lt;/code&gt; method that accepts some argument still obeys the interface, as long as it returns an object of expected shape! &lt;/p&gt;

&lt;p&gt;So let's see what happens when we pass some strings to those &lt;code&gt;next&lt;/code&gt; calls:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;d&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After you run this, you'll finally see something else than &lt;code&gt;undefined&lt;/code&gt; in the console:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start
{ value: 1, done: false }
b                                &amp;lt;- no more undefined
{ value: 2, done: false }
c                                &amp;lt;- no more undefined
{ value: 3, done: false }
d                                &amp;lt;- no more undefined
{ value: undefined, done: true }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Perhaps this result is surprising to you. After all, the first letter we've passed to the &lt;code&gt;next&lt;/code&gt; was &lt;code&gt;a&lt;/code&gt;. And yet we only see &lt;code&gt;b&lt;/code&gt;, &lt;code&gt;c&lt;/code&gt; and &lt;code&gt;d&lt;/code&gt; here.&lt;/p&gt;

&lt;p&gt;But it's actually fairly straightforward to see what is happening here if we do it step by step.&lt;/p&gt;

&lt;p&gt;The rule is that a call to &lt;code&gt;next&lt;/code&gt; causes the generator function to run until it encounters a &lt;code&gt;yield &amp;lt;some value&amp;gt;&lt;/code&gt; call. When this call is encountered, the &lt;code&gt;&amp;lt;some value&amp;gt;&lt;/code&gt; part gets returned from the &lt;code&gt;next&lt;/code&gt; call (as a value in the &lt;code&gt;{ value, done }&lt;/code&gt; object). From this moment on, the generator simply waits for another &lt;code&gt;next&lt;/code&gt; call. The value passed to that &lt;em&gt;another&lt;/em&gt; &lt;code&gt;next&lt;/code&gt; call will become the value to which the whole &lt;code&gt;yield &amp;lt;something&amp;gt;&lt;/code&gt; expression gets evaluated.&lt;/p&gt;

&lt;p&gt;Let's see it step by step on our example generator.&lt;/p&gt;

&lt;p&gt;When you call &lt;code&gt;next&lt;/code&gt; the first time, it simply begins the execution of the generator function. In our case, this means that &lt;code&gt;console.log('start')&lt;/code&gt; will get executed.&lt;/p&gt;

&lt;p&gt;Indeed, running:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;results in the following:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the generator function, after &lt;code&gt;console.log('start')&lt;/code&gt;, we encounter the &lt;code&gt;yield 1&lt;/code&gt; expression. As we've explained, number 1 here will become the value returned from that first &lt;code&gt;next&lt;/code&gt; call that we have just made.&lt;/p&gt;

&lt;p&gt;Indeed, you can wrap the &lt;code&gt;next&lt;/code&gt; call in &lt;code&gt;console.log&lt;/code&gt; to make sure that's true:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This now logs:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start
{ value: 1, done: false }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The 1 there is precisely what we yielded in the generator. &lt;/p&gt;

&lt;p&gt;And this point, the generator is suspended. Even the statement where we encountered &lt;code&gt;yield&lt;/code&gt; - &lt;code&gt;const first = yield 1;&lt;/code&gt; - did &lt;em&gt;not&lt;/em&gt; get executed fully. After all, the generator doesn't know yet what the value of the &lt;code&gt;yield 1&lt;/code&gt; part should be.&lt;/p&gt;

&lt;p&gt;We will provide that value with our &lt;em&gt;next&lt;/em&gt; &lt;code&gt;next&lt;/code&gt; call:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This will print:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start
{ value: 1, done: false }
b
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So we see that the generator resumed execution and basically replaced &lt;code&gt;yield 1&lt;/code&gt; with a value that we passed to the &lt;code&gt;next&lt;/code&gt; call - &lt;code&gt;b&lt;/code&gt; string.&lt;/p&gt;

&lt;p&gt;To make sure you &lt;em&gt;really&lt;/em&gt; understand what is happening, you can try to pass some other values at this point:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;this is some other string, which we created for tutorial purposes&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This will (hopefully obviously to you now) print:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start
{ value: 1, done: false }
this is some other string, which we created for tutorial purposes
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;em&gt;You&lt;/em&gt; are the one who decides here what &lt;code&gt;yield 1&lt;/code&gt; will evaluate to.&lt;/p&gt;

&lt;p&gt;So at this point we see, that our &lt;em&gt;first&lt;/em&gt; &lt;code&gt;yield&lt;/code&gt; expression uses the value provided in the &lt;em&gt;second&lt;/em&gt; &lt;code&gt;next&lt;/code&gt; call. This is crucial to understand in generators. &lt;/p&gt;

&lt;p&gt;Basically, when encountering a &lt;code&gt;yield &amp;lt;some value&amp;gt;&lt;/code&gt;, the generator is saying: "in current &lt;code&gt;next&lt;/code&gt; call I will return you a &lt;code&gt;&amp;lt;some value&amp;gt;&lt;/code&gt;, but in the &lt;em&gt;next&lt;/em&gt; &lt;code&gt;next&lt;/code&gt; call please provide me as an argument what should I replace &lt;code&gt;yield &amp;lt;some value&amp;gt;&lt;/code&gt; with".&lt;/p&gt;

&lt;p&gt;And this actually means that the argument passed to the &lt;em&gt;first&lt;/em&gt; &lt;code&gt;next&lt;/code&gt; call will never be used by the generator. There is simply no point to provide it, so we will just remove it from our example:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt; &lt;span class="c1"&gt;// no need to pass anything on the first `next` call&lt;/span&gt;
&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After we've called &lt;code&gt;next&lt;/code&gt; a second time, the generator continued to execute the code, until it encountered &lt;em&gt;another&lt;/em&gt; &lt;code&gt;yield&lt;/code&gt; statement - &lt;code&gt;yield 2&lt;/code&gt;. Therefore number 2 gets returned from this &lt;code&gt;next&lt;/code&gt; call as a value.&lt;/p&gt;

&lt;p&gt;So this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;prints this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start
{ value: 1, done: false }
b
{ value: 2, done: false }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;What happens now? The generator does not know to what it should evaluate &lt;code&gt;yield 2&lt;/code&gt; in the &lt;code&gt;const second = yield 2;&lt;/code&gt; statement. So it just waits there, suspended, until you pass it another value in the &lt;code&gt;next&lt;/code&gt; call:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This now logs:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start
{ value: 1, done: false }
b
{ value: 2, done: false }
c
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So after that third &lt;code&gt;next&lt;/code&gt; call, code in the generator starts being executed again, until we encounter &lt;code&gt;yield 3&lt;/code&gt;. So 3 will be the value returned from that call:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt; &lt;span class="c1"&gt;// we've added console.log here&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This prints:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start
{ value: 1, done: false }
b
{ value: 2, done: false }
c
{ value: 3, done: false }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now the generator is suspended at the &lt;code&gt;const third = yield 3;&lt;/code&gt; statement. We know what to do to make it running again - another &lt;code&gt;next&lt;/code&gt; call with a value!&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;d&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="c1"&gt;// we've added another next call&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This prints:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start
{ value: 1, done: false }
b
{ value: 2, done: false }
c
{ value: 3, done: false }
d
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And - because our generator doesn't how more &lt;code&gt;yield&lt;/code&gt; statements in it - it doesn't have more values to return. It also runs till completion. &lt;/p&gt;

&lt;p&gt;That's why the last &lt;code&gt;{ done, value }&lt;/code&gt; object from the &lt;code&gt;next&lt;/code&gt; call, has no value in it and also notifies us that the iterator has finished.&lt;/p&gt;

&lt;p&gt;So this code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;getNumber&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;d&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt; &lt;span class="c1"&gt;// we've added console.log here&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Prints this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;start
{ value: 1, done: false }
b
{ value: 2, done: false }
c
{ value: 3, done: false }
d
{ value: undefined, done: true }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And that's it! If this still seems confusing, you need to run this example by yourself, perhaps even a few times. &lt;/p&gt;

&lt;p&gt;Help yourself by adding those successive &lt;code&gt;next&lt;/code&gt; and &lt;code&gt;console.log&lt;/code&gt; calls step by step just like I did. Try also to always control in which line of the generator you currently are. Remember! You have to look at the generator code at each step to really understand what is happening here!&lt;/p&gt;

&lt;p&gt;Don't just read the article - run this example by yourself, as many times as necessary, to make sure that you actually understand what is happening!&lt;/p&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;In this article, we've learned the basics of generators. How to create them, how to use the &lt;code&gt;yield&lt;/code&gt; keyword, and how to consume the generators.&lt;/p&gt;

&lt;p&gt;I hope that those first exercises and examples got you excited to learn more. We still have a lot to cover with regards to generators, so make sure to follow me on &lt;a href="https://twitter.com/m_podlasin"&gt;Twitter&lt;/a&gt; to not miss those future articles.&lt;/p&gt;

&lt;p&gt;Thanks for reading!&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>tutorial</category>
      <category>codenewbie</category>
    </item>
    <item>
      <title>Iterables &amp; Iterators - An In-Depth JavaScript Tutorial</title>
      <dc:creator>mpodlasin</dc:creator>
      <pubDate>Thu, 10 Dec 2020 07:51:39 +0000</pubDate>
      <link>https://forem.com/mpodlasin/iterables-iterators-an-in-depth-javascript-tutorial-5eh2</link>
      <guid>https://forem.com/mpodlasin/iterables-iterators-an-in-depth-javascript-tutorial-5eh2</guid>
      <description>&lt;p&gt;This article is an in-depth introduction to iterables and iterators in JavaScript. My main motivation for writing it was to prepare ourselves for learning generators next. In fact, later I plan to do some experimental stuff, like combining generators with React hooks.&lt;/p&gt;

&lt;p&gt;As a matter of fact, I planned to start with the generators article, but it quickly became obvious to me, that they are tough to explain without having a solid understanding of iterables &amp;amp; iterators first.&lt;/p&gt;

&lt;p&gt;That's why in this article we will focus on iterables &amp;amp; iterators only. We will assume no previous knowledge about them, but at the same time, we will go fairly in-depth. So if you know &lt;em&gt;something&lt;/em&gt; about iterables &amp;amp; iterators, but you still don't feel fully comfortable using them, this article should fix that.&lt;/p&gt;

&lt;h2&gt;
  
  
  Introduction
&lt;/h2&gt;

&lt;p&gt;As you've noticed, we are talking about iterables &lt;em&gt;and&lt;/em&gt; iterators. They are related, but distinct concepts, so while reading the article make sure to keep tabs on which one we are talking about at any given moment. &lt;/p&gt;

&lt;p&gt;Let's begin with iterables. What are they? An iterable is basically something that can be iterated over, like so:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;iterable&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// do something with an element&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Note that we are talking only about &lt;code&gt;for ... of&lt;/code&gt; loops here, which were introduced in ES6. &lt;code&gt;for ... in&lt;/code&gt; loops are an older construct and we will not use it at all in this article.&lt;/p&gt;

&lt;p&gt;You might now think, "okay, this &lt;code&gt;iterable&lt;/code&gt; variable is simply an array!". And indeed, arrays are iterables. But even currently in native JavaScript, there are other data structures that we could use in a &lt;code&gt;for ... of&lt;/code&gt; loop. In other words, there are more iterables in native JavaScript than just arrays.&lt;/p&gt;

&lt;p&gt;For example, we can iterate over ES6 Maps:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ourMap&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nb"&gt;Map&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;ourMap&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="kd"&gt;set&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="nx"&gt;ourMap&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="kd"&gt;set&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="nx"&gt;ourMap&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="kd"&gt;set&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;ourMap&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This code will print out:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So variable &lt;code&gt;element&lt;/code&gt; in the code above stores in each iteration step an array of two elements. The first element is a key, and the second element is a value.&lt;/p&gt;

&lt;p&gt;The fact that we could use &lt;code&gt;for ... of&lt;/code&gt; loop to iterate over Map, proves to us that Maps are iterables. Once again - &lt;em&gt;only&lt;/em&gt; iterables can be used in &lt;code&gt;for ... of&lt;/code&gt; loops. So if something works with that loop - it is an iterable.&lt;/p&gt;

&lt;p&gt;Funnily enough, &lt;code&gt;Map&lt;/code&gt; constructor itself optionally accepts an iterable of key-value pairs. So this is an alternative way to construct the same Map as before:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ourMap&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nb"&gt;Map&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;
    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="p"&gt;]);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And since - as we've just noted - Map itself is an iterable, we can create copies of Maps extremely easily:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;copyOfOurMap&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nb"&gt;Map&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;ourMap&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We have now two distinct maps, although they are storing the same values under the same keys.&lt;/p&gt;

&lt;p&gt;So we've seen two examples of iterables so far - an array and an ES6 Map.&lt;/p&gt;

&lt;p&gt;But we still didn't explain &lt;em&gt;how&lt;/em&gt; do they possess this magic power of being able to be iterated over.&lt;/p&gt;

&lt;p&gt;The answer is simple - they have &lt;em&gt;iterators&lt;/em&gt; associated with them. Read that carefully. Itera*&lt;em&gt;tors&lt;/em&gt;&lt;em&gt;, not itera&lt;/em&gt;&lt;em&gt;bles&lt;/em&gt;*.&lt;/p&gt;

&lt;p&gt;In what way an iterator is associated with it's iterable? An iterable object simply has to have a function under its &lt;code&gt;Symbol.iterator&lt;/code&gt; property. This function, when called, should return an iterator for that object.&lt;/p&gt;

&lt;p&gt;For example, we can retrieve an array's iterator like so:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This code will print &lt;code&gt;Object [Array Iterator] {}&lt;/code&gt; to the console.&lt;/p&gt;

&lt;p&gt;So we know that our array has an associated iterator and that this iterator is some kind of object.&lt;/p&gt;

&lt;p&gt;What is an iterator then?&lt;/p&gt;

&lt;p&gt;It's fairly simple. An iterator is just an object that has a &lt;code&gt;next&lt;/code&gt; method. This method, when called, should return:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;next value in a sequence of values,&lt;/li&gt;
&lt;li&gt;information whether the iterator has finished producing values or not.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Let's test it, by calling the &lt;code&gt;next&lt;/code&gt; method of the iterator of our array:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We will see an object &lt;code&gt;{ value: 1, done: false }&lt;/code&gt; printed in the console.&lt;/p&gt;

&lt;p&gt;The first element of the array we created was 1, so it appeared as the value here. We also got information that the iterator is not done yet, meaning we still can call the &lt;code&gt;next&lt;/code&gt; function and expect to see some values.&lt;/p&gt;

&lt;p&gt;Let's do it! In fact, let's call &lt;code&gt;next&lt;/code&gt; two more times:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Unsurprisingly, we get &lt;code&gt;{ value: 2, done: false }&lt;/code&gt; and &lt;code&gt;{ value: 3, done: false }&lt;/code&gt; printed, one after another.&lt;/p&gt;

&lt;p&gt;But our array had only 3 elements. So what happens, if we try to call &lt;code&gt;next&lt;/code&gt; yet again?&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This time we see &lt;code&gt;{ value: undefined, done: true }&lt;/code&gt; printed. This is information for us that the iterator has finished. There is no point calling &lt;code&gt;next&lt;/code&gt; again. In fact, if we do so, we will receive the same &lt;code&gt;{ value: undefined, done: true }&lt;/code&gt; object over and over again. &lt;code&gt;done: true&lt;/code&gt; is a sign for us to stop the iteration.&lt;/p&gt;

&lt;p&gt;Now we can understand what &lt;code&gt;for ... of&lt;/code&gt; loop does under the hood.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;First &lt;code&gt;[Symbol.iterator]()&lt;/code&gt; method is called to get an iterator,&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;next&lt;/code&gt; method is being called on that iterator in a loop until we get &lt;code&gt;done: true&lt;/code&gt;,&lt;/li&gt;
&lt;li&gt;after each call to &lt;code&gt;next&lt;/code&gt;, &lt;code&gt;value&lt;/code&gt; property is used in the loop's body.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Let's write all that in code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]();&lt;/span&gt;

&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

&lt;span class="k"&gt;while&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;done&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

    &lt;span class="c1"&gt;// do some something with element&lt;/span&gt;

    &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;All this code is directly equivalent to:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// do something with element&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You can make sure that's the case by, for example, placing &lt;code&gt;console.log(element)&lt;/code&gt; in place of &lt;code&gt;// do something with element&lt;/code&gt; comment.&lt;/p&gt;

&lt;h2&gt;
  
  
  Creating our own iterator
&lt;/h2&gt;

&lt;p&gt;So we know what the iterables and iterators are. The question then becomes - is it possible to write our own instances of them?&lt;/p&gt;

&lt;p&gt;Absolutely!&lt;/p&gt;

&lt;p&gt;There is nothing magical about iterators. They are just objects with a &lt;code&gt;next&lt;/code&gt; method, which behaves in a specified way.&lt;/p&gt;

&lt;p&gt;We've said which native JS values are iterables. We haven't mention objects there. Indeed, they are not iterables natively. Take an object like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ourObject&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;
&lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When we try to iterate over that object with &lt;code&gt;for (let element of ourObject)&lt;/code&gt;, we will get an error, stating that &lt;code&gt;object is not iterable&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;So let's practice writing custom iterators by making such an object an iterable!&lt;/p&gt;

&lt;p&gt;In order to do that, we would have to patch &lt;code&gt;Object&lt;/code&gt; prototype with our custom &lt;code&gt;[Symbol.iterator]()&lt;/code&gt; method. Since patching prototypes is a bad practice, let's just create a custom class, extending &lt;code&gt;Object&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;constructor&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;object&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;super&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
        &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;assign&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;object&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The constructor of our class simply takes a regular object and copies its properties onto an iterable one (although it's not really iterable yet!).&lt;/p&gt;

&lt;p&gt;So we will be creating an interable object like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterableObject&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
    &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;
&lt;span class="p"&gt;})&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In order to make the &lt;code&gt;IterableObject&lt;/code&gt; class &lt;em&gt;actually&lt;/em&gt; iterable, it needs to have a &lt;code&gt;[Symbol.iterator]()&lt;/code&gt; method. Let's add it then.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;constructor&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;object&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;super&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
        &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;assign&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;object&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;

    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now we can start writing an actual iterator!&lt;/p&gt;

&lt;p&gt;We already know that it has to be an object, which has a &lt;code&gt;next&lt;/code&gt; method on it. So let's start with that.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// same as before&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After every call to &lt;code&gt;next&lt;/code&gt;, we have to return an object of shape &lt;code&gt;{ value, done }&lt;/code&gt;. Let's do just that, with some dummy values.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// same as before&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                    &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;
                &lt;span class="p"&gt;}&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Given an iterable object:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterableObject&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
    &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;
&lt;span class="p"&gt;})&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;we would like to print it's key-value pairs, similarily to what iterating over ES6 Map did:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;1&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;2&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;3&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So in our custom iterator, under the &lt;code&gt;value&lt;/code&gt; property we want to place an array &lt;code&gt;[key, valueForThatKey]&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Note that this - compared to the previous steps of the example - is our own design decision. If we wanted to write an iterator that returned only keys or only property values - we might do that as well, and it would be perfectly fine. We simply ourselves decided to return key-value pairs.&lt;/p&gt;

&lt;p&gt;So we will need arrays of shape &lt;code&gt;[key, valueForThatKey]&lt;/code&gt;. The easiest way to obtain them is simply to use the &lt;code&gt;Object.entries&lt;/code&gt; method.&lt;/p&gt;

&lt;p&gt;We can use it just before creating an iterator object in the &lt;code&gt;[Symbol.iterator]()&lt;/code&gt; method:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// same as before&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="c1"&gt;// we made an addition here&lt;/span&gt;
        &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                    &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;
                &lt;span class="p"&gt;}&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The iterator returned in that method will have an access to the &lt;code&gt;entries&lt;/code&gt; variable thanks to a JavaScript closure.&lt;/p&gt;

&lt;p&gt;But we also need some kind of state variable. It will tell us which key-value pair should be returned in a current &lt;code&gt;next&lt;/code&gt; call. So let's add that as well.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// same as before&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
        &lt;span class="c1"&gt;// we made an addition here&lt;/span&gt;
        &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                    &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;
                &lt;span class="p"&gt;}&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Note how we declared &lt;code&gt;index&lt;/code&gt; variable with a &lt;code&gt;let&lt;/code&gt; because we know that we plan to update its value after each &lt;code&gt;next&lt;/code&gt; call.&lt;/p&gt;

&lt;p&gt;We are now ready to return an actual value in the &lt;code&gt;next&lt;/code&gt; method:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// same as before&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
        &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="c1"&gt;// we made a change here&lt;/span&gt;
                    &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
                    &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;
                &lt;span class="p"&gt;}&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This was easy. We just used both &lt;code&gt;entries&lt;/code&gt; and &lt;code&gt;index&lt;/code&gt; variables to access a proper key-value pair from the &lt;code&gt;entries&lt;/code&gt; array.&lt;/p&gt;

&lt;p&gt;Now we have to deal with that &lt;code&gt;done&lt;/code&gt; property because currently, it will be always set to &lt;code&gt;false&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;We could keep another variable - alongside &lt;code&gt;entries&lt;/code&gt; and &lt;code&gt;index&lt;/code&gt; - and update it after every &lt;code&gt;next&lt;/code&gt; call. But there is an even easier way. We can simply check if &lt;code&gt;index&lt;/code&gt; already went out of bounds of the &lt;code&gt;entries&lt;/code&gt; array:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// same as before&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
        &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
                    &lt;span class="c1"&gt;// we made a change here&lt;/span&gt;
                    &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;length&lt;/span&gt;
                &lt;span class="p"&gt;}&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Indeed, our iterator is done when the &lt;code&gt;index&lt;/code&gt; variable is equal to the length of &lt;code&gt;entries&lt;/code&gt; or is bigger.&lt;/p&gt;

&lt;p&gt;For example, if &lt;code&gt;entries&lt;/code&gt; has length 3, it has values under indexes 0, 1, and 2. So when the &lt;code&gt;index&lt;/code&gt; variable is 3 (equal to the length), or bigger, it means there are no more values to get. That's when we are done.&lt;/p&gt;

&lt;p&gt;This code &lt;em&gt;almost&lt;/em&gt; works. There is only one more thing we need to add. &lt;/p&gt;

&lt;p&gt;The &lt;code&gt;index&lt;/code&gt; variable starts with a value 0, but... we are never updating it!&lt;/p&gt;

&lt;p&gt;It's actually kind of tricky because we should update it &lt;em&gt;after&lt;/em&gt; we return &lt;code&gt;{ value, done }&lt;/code&gt;. But when we return it, the &lt;code&gt;next&lt;/code&gt; method stops running immediately, even if there is some code after the &lt;code&gt;return&lt;/code&gt; statement. &lt;/p&gt;

&lt;p&gt;We can however create the &lt;code&gt;{ value, done }&lt;/code&gt; object, store it in a variable, update the &lt;code&gt;index&lt;/code&gt; and &lt;em&gt;just then&lt;/em&gt; return the object:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// same as before&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
        &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
                    &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;length&lt;/span&gt;
                &lt;span class="p"&gt;};&lt;/span&gt;

                &lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

                &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After all these changes, this is how our &lt;code&gt;IterableObject&lt;/code&gt; class looks so far:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;constructor&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;object&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;super&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
        &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;assign&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;object&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
        &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
                    &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;length&lt;/span&gt;
                &lt;span class="p"&gt;};&lt;/span&gt;

                &lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

                &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;result&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This code works perfectly fine, but it became a bit convoluted. There is actually a smarter (but less obvious) way to deal with having to update &lt;code&gt;index&lt;/code&gt; &lt;em&gt;after&lt;/em&gt; creating the &lt;code&gt;result&lt;/code&gt; object. We can simply initialize &lt;code&gt;index&lt;/code&gt; with -1!&lt;/p&gt;

&lt;p&gt;Then, even though the &lt;code&gt;index&lt;/code&gt; update happens before returning the object from &lt;code&gt;next&lt;/code&gt;, everything will work just fine, because the first update will bump -1 to 0.&lt;/p&gt;

&lt;p&gt;So let's do just that:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// same as before&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
        &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

                &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
                    &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;length&lt;/span&gt;
                &lt;span class="p"&gt;}&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As you can see, now we don't have to juggle the order of creating the result object and updating &lt;code&gt;index&lt;/code&gt;. That's because we are starting with -1. During the first &lt;code&gt;next&lt;/code&gt; call, &lt;code&gt;index&lt;/code&gt; will be updated to 0 and then we will return the result. &lt;/p&gt;

&lt;p&gt;During the second call, &lt;code&gt;index&lt;/code&gt; will be updated to 1 and we will return another result, etc...&lt;/p&gt;

&lt;p&gt;So everything will work just as we wanted, and the code looks now much simpler than the previous version.&lt;/p&gt;

&lt;p&gt;How we can test if it really works properly? We could manually run &lt;code&gt;[Symbol.iterator]()&lt;/code&gt; method to create an iterator instance, then directly test the results of &lt;code&gt;next&lt;/code&gt; calls, etc.&lt;/p&gt;

&lt;p&gt;But there is a much simpler way!  We've said that every iterable can be plugged into &lt;code&gt;for ... of&lt;/code&gt; loop! So let's do just that and log the values returned by our custom iterable:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterableObject&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
    &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;
&lt;span class="p"&gt;});&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;iterableObject&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;It works! You will see the following result printed in the console:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="p"&gt;[&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;1&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;a&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="p"&gt;[&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;2&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;b&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="p"&gt;[&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;3&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;c&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="p"&gt;]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's exactly what we wanted!&lt;/p&gt;

&lt;p&gt;Isn't this cool? We've started with objects not being able to be used in &lt;code&gt;for ... of&lt;/code&gt; loops because natively they don't have built-in iterators. But we created a custom &lt;code&gt;IterableObject&lt;/code&gt;, which &lt;em&gt;does&lt;/em&gt; have an associated iterator, which we have written by hand.&lt;/p&gt;

&lt;p&gt;I hope that by now you can see and appreciate the power of iterables and iterators. It's a mechanism that allows your own data structures to cooperate with JS features like &lt;code&gt;for ... of&lt;/code&gt; loops, in a way indistinguishable from the native data structures! That's very powerful and in certain situations, it can vastly simplify the code, especially if you plan to do iterations on your data structures often.&lt;/p&gt;

&lt;p&gt;On top of that, we can customize what exactly such iteration will return. We've settled on returning key-value pairs from our iterator. But what if we cared only about the values themselves? No problem! We can just rewrite our iterator:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// same as before&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="c1"&gt;// changed `entries` to `values`&lt;/span&gt;
        &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;values&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;values&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
        &lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

                &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="c1"&gt;// changed `entries` to `values`&lt;/span&gt;
                    &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;values&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;index&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
                    &lt;span class="c1"&gt;// changed `entries` to `values`&lt;/span&gt;
                    &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="nx"&gt;values&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;length&lt;/span&gt;
                &lt;span class="p"&gt;}&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And that's it!&lt;/p&gt;

&lt;p&gt;If we run &lt;code&gt;for ... of&lt;/code&gt; loop after this change, we will see the following output in the console:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;a
b
c
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So we really returned only the objects values, just as we wanted.&lt;/p&gt;

&lt;p&gt;This proves how flexible your custom iterators can be. You can really make them return whatever you wish.&lt;/p&gt;

&lt;h2&gt;
  
  
  Iterators as... iterables
&lt;/h2&gt;

&lt;p&gt;You will see people very often confusing iterators and iterables.&lt;/p&gt;

&lt;p&gt;That's a mistake and I was trying to carefully differentiate between the two in this article, but I think I know one of the main reasons why people confuse them so often.&lt;/p&gt;

&lt;p&gt;It turns out that iterators... are sometimes iterables as well!&lt;/p&gt;

&lt;p&gt;What does it mean? We said that an iterable is an object that has an iterator associated with it.&lt;/p&gt;

&lt;p&gt;It turns out that every native JavaScript iterator also has a &lt;code&gt;[Symbol.iterator]()&lt;/code&gt; method, returning yet another iterator! This - according to our previous definition - makes that first iterator an iterable.&lt;/p&gt;

&lt;p&gt;We can check that it is true, by taking an iterator returned from an array and calling &lt;code&gt;[Symbol.iterator]()&lt;/code&gt; on it once more:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]();&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;secondIterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]();&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;secondIterator&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After running this code, you will see &lt;code&gt;Object [Array Iterator] {}&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;So not only our iterator has another iterator associated with it, but we also see that it is again an array iterator.&lt;/p&gt;

&lt;p&gt;In fact, if we compare those two iterators with &lt;code&gt;===&lt;/code&gt;, it turns out that this is simply exactly the same iterator:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]();&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;secondIterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]();&lt;/span&gt;

&lt;span class="c1"&gt;// logs `true`&lt;/span&gt;
&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="nx"&gt;secondIterator&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This behavior of an iterator being its own iterator might seem strange at the beginning.&lt;/p&gt;

&lt;p&gt;But it's actually fairly useful.&lt;/p&gt;

&lt;p&gt;You cannot plug a bare iterator into the &lt;code&gt;for ... of&lt;/code&gt; loop. &lt;code&gt;for ... of&lt;/code&gt; accepts only an iterable - that is an object with a &lt;code&gt;[Symbol.iterator]()&lt;/code&gt; method.&lt;/p&gt;

&lt;p&gt;However, an iterator being its own iterator (and hence an iterable) mitigates that problem. Since native JavaScript iterators &lt;em&gt;do&lt;/em&gt; have &lt;code&gt;[Symbol.iterator]()&lt;/code&gt; methods on them, you can pass them to &lt;code&gt;for ... of&lt;/code&gt; loops directly without thinking twice.&lt;/p&gt;

&lt;p&gt;So because of that feature, both:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;and:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]();&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;work without any problems and do exactly the same thing.&lt;/p&gt;

&lt;p&gt;But why would you even want to use an iterator directly in a &lt;code&gt;for ... of&lt;/code&gt; loop like that? The answer is simple - it turns out that sometimes it is simply unavoidable.&lt;/p&gt;

&lt;p&gt;First of all, you might want to create an iterator without any iterable to which it belongs. We will see such example later, and it's actually not &lt;em&gt;that&lt;/em&gt; rare to create such "bare" iterators. Sometimes an iterable itself just isn't needed.&lt;/p&gt;

&lt;p&gt;And it would be very akward if having a bare iterator meant you couldn't just consume it via &lt;code&gt;for ... of&lt;/code&gt;. It's of course always possible to do it manually with a &lt;code&gt;next&lt;/code&gt; method and, for example, a &lt;code&gt;while&lt;/code&gt; loop, but we've seen that it requires quite a lot of typing and boilerplate. &lt;/p&gt;

&lt;p&gt;It's simple - if you want to avoid that boilerplate and use your iterator in a &lt;code&gt;for ... of&lt;/code&gt; loop, you have to make it an iterable as well.&lt;/p&gt;

&lt;p&gt;On the other hand, you will also quite often receive iterators from methods other than &lt;code&gt;[Symbol.iterator]()&lt;/code&gt;. For example, ES6 Map has &lt;code&gt;entries&lt;/code&gt;, &lt;code&gt;values&lt;/code&gt; and &lt;code&gt;keys&lt;/code&gt; methods. All of them return iterators.&lt;/p&gt;

&lt;p&gt;If native JavaScript iterators weren't iterables as well, you couldn't just use those methods directly in &lt;code&gt;for ... of&lt;/code&gt; loops like that:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;map&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;map&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;values&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;map&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;keys&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The code above works, because iterators returned by the methods are also iterables.&lt;/p&gt;

&lt;p&gt;If they weren't, we would have to, for example, awkardly wrap a result from &lt;code&gt;map.entries()&lt;/code&gt; call in some kind of a dummy iterable. Luckily we don't have to, and we can just use those methods directly, without worrying too much about it.&lt;/p&gt;

&lt;p&gt;For those reasons, it is a good practice to make your custom iterators iterables as well. &lt;em&gt;Especially&lt;/em&gt; if they will be returned from some methods other than &lt;code&gt;[Symbol.iterator]()&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;And it's actually very simple to make an iterator an iterable. Let's do that with our &lt;code&gt;IterableObject&lt;/code&gt; iterator.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nx"&gt;IterableObject&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// same as before&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="c1"&gt;// same as before&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="c1"&gt;// same as before&lt;/span&gt;
            &lt;span class="p"&gt;},&lt;/span&gt;

            &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As you can see, we just created a &lt;code&gt;[Symbol.iterator]()&lt;/code&gt; method under the &lt;code&gt;next&lt;/code&gt; method.&lt;/p&gt;

&lt;p&gt;We've made this iterator it's own iterator by simply returning &lt;code&gt;this&lt;/code&gt; - so it just returned itself. We've seen that that's exactly how the array iterator behaved.&lt;/p&gt;

&lt;p&gt;That's enough to make sure that our iterator works with &lt;code&gt;for ... of&lt;/code&gt; loops, even when used in them directly.&lt;/p&gt;

&lt;h2&gt;
  
  
  State of an iterator
&lt;/h2&gt;

&lt;p&gt;It should be fairly clear by now that each iterator has a state associated with it.&lt;/p&gt;

&lt;p&gt;For example in our &lt;code&gt;IterableObject&lt;/code&gt; iterator, we kept the state - an &lt;code&gt;index&lt;/code&gt; variable - as a closure.&lt;/p&gt;

&lt;p&gt;After each iteration step, that &lt;code&gt;index&lt;/code&gt; was updated.&lt;/p&gt;

&lt;p&gt;So what happens after the iteration process ends? It's simple - the iterator becomes useless and we can (and should!) discard it.&lt;/p&gt;

&lt;p&gt;We can doublecheck that this happens even with iterators of native JavaScript objects.&lt;/p&gt;

&lt;p&gt;We will take an iterator of an array and try to run it in a &lt;code&gt;for ... of&lt;/code&gt; loop twice.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]();&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You might expect to see numbers &lt;code&gt;1, 2, 3&lt;/code&gt; appearing in the console twice. But this is not what happens. The result is still just:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;1
2
3
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;But why?&lt;/p&gt;

&lt;p&gt;We can discover that, by trying to call &lt;code&gt;next&lt;/code&gt; manually, after the loop finishes:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]();&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;());&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The last log prints &lt;code&gt;{ value: undefined, done: true }&lt;/code&gt; to the console.&lt;/p&gt;

&lt;p&gt;Aaah. So after the loop finishes, the iterator is now in its "done" state. From now on it always return a &lt;code&gt;{ value: undefined, done: true }&lt;/code&gt; object.&lt;/p&gt;

&lt;p&gt;Is there a way to "reset" the state of this iterator, in order to use it in a &lt;code&gt;for ... of&lt;/code&gt; loop second time?&lt;/p&gt;

&lt;p&gt;In some cases perhaps, but there is really no point. This is exactly why &lt;code&gt;[Symbol.iterator]&lt;/code&gt; is a method and not just a property. We can simply call that method again to obtain &lt;em&gt;another&lt;/em&gt; iterator:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]();&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;secondIterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]();&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;secondIterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now it works as we would expect.&lt;/p&gt;

&lt;p&gt;Right now you should be able to understand why looping over an array directly multiple times works:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;ourArray&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's because each of those &lt;code&gt;for ... of&lt;/code&gt; loops uses a &lt;em&gt;different&lt;/em&gt; iterator! After an iterator is done and a loop ends, that iterator is never used again.&lt;/p&gt;

&lt;h2&gt;
  
  
  Iterators vs arrays
&lt;/h2&gt;

&lt;p&gt;Because we use iterators (although indirectly) in &lt;code&gt;for ... of&lt;/code&gt; loops, they might look to you deceivingly similar to arrays.&lt;/p&gt;

&lt;p&gt;But there are two important distinctions to be made between the iterators and the arrays.&lt;/p&gt;

&lt;p&gt;Both of them have to do with the concept of eager and lazy values.&lt;/p&gt;

&lt;p&gt;When you create an array, at any given moment it has a specific length and its values are already initialized. &lt;/p&gt;

&lt;p&gt;I mean, sure, you can create an array wihout any values inside, but that's not what we mean here. &lt;/p&gt;

&lt;p&gt;We mean that it is impossible to create an array that initializes its value only &lt;em&gt;after&lt;/em&gt; you attempt to access that value by writing &lt;code&gt;array[someIndex]&lt;/code&gt;. I mean, perhaps it is &lt;em&gt;possible&lt;/em&gt; with some Proxy or other JS trickery, but by default JavaScript arrays don't behave in that way. You just create an array with values initialized beforehand and that's it.&lt;/p&gt;

&lt;p&gt;And when saying that an array has a length, we in fact mean that the array is of a finite length. There are no infinite arrays in JavaScript.&lt;/p&gt;

&lt;p&gt;Those two qualities point to the &lt;em&gt;eagerness&lt;/em&gt; of arrays.&lt;/p&gt;

&lt;p&gt;On the other hand, iterators are &lt;em&gt;lazy&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;To show that, we will create two custom iterators - the first one will be an infinite iterator, in contrast to finite arrays, and the second will initialize its values only when they are actually needed/requested by whoever is using the iterator.&lt;/p&gt;

&lt;p&gt;Let's start with the infinite iterator. This might sound scary, but we will create something very simple - an iterator that starts at 0 and at each step returns the next integer in a sequence. Forever.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;counterIterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;integer&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;

    &lt;span class="nx"&gt;next&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;integer&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;integer&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;done&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="p"&gt;};&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;

    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Symbol&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;iterator&lt;/span&gt;&lt;span class="p"&gt;]()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's it! We start with the &lt;code&gt;integer&lt;/code&gt; property equal to -1. At each &lt;code&gt;next&lt;/code&gt; call we bump it by one and return it as a &lt;code&gt;value&lt;/code&gt; in the result object.&lt;/p&gt;

&lt;p&gt;Note that we used here the same trick as before - starting at -1 in order to return 0 as the first result.&lt;/p&gt;

&lt;p&gt;Look also at the &lt;code&gt;done&lt;/code&gt; property. It will be &lt;em&gt;always&lt;/em&gt; false. This iterator never ends!&lt;/p&gt;

&lt;p&gt;Third thing, which you've probably noticed yourself - we have made this iterator an iterable, by giving it a simple &lt;code&gt;[Symbol.iterator]()&lt;/code&gt; implementation.&lt;/p&gt;

&lt;p&gt;And one last note. This is the case that we've been mentioning earlier - we've created an iterator, but there is no iterable in sight! This is an iterator which doesn't need an iterable "parent" for anything.&lt;/p&gt;

&lt;p&gt;We can now try out this iterator in a &lt;code&gt;for ... of&lt;/code&gt; loop. We just need to remember to break out of the loop at some point. Otherwise, the code would run forever!&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;let&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;counterIterator&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;break&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;

    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After running this code we will see the following in the console:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;0
1
2
3
4
5
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So we really created an infinite iterator, which can return you as many integers as you wish. And it was actually very easy do achieve!&lt;/p&gt;

&lt;p&gt;Now, let's make an iterator, which doesn't create its values until they are requested.&lt;/p&gt;

&lt;p&gt;Well... we already did it!&lt;/p&gt;

&lt;p&gt;Have you noticed that at any given moment, our &lt;code&gt;counterIterator&lt;/code&gt; stores only one number on the &lt;code&gt;integer&lt;/code&gt; property? It stores only the last number that it has returned in a &lt;code&gt;next&lt;/code&gt; call.&lt;/p&gt;

&lt;p&gt;This is indeed the laziness we were talking about. This iterator can &lt;em&gt;potentially&lt;/em&gt; return any number (non-negative integer, to be specific). But it only creates a number when it is actually needed - when someone is calling the &lt;code&gt;next&lt;/code&gt; method.&lt;/p&gt;

&lt;p&gt;This might not seem like a big benefit. After all, numbers are created fast and they don't occupy a lot of memory.&lt;/p&gt;

&lt;p&gt;But if you are dealing with very big, memory-heavy objects in your code, sometimes swapping arrays for iterators can be extremely valuable, making your program faster more memory efficient.&lt;/p&gt;

&lt;p&gt;The heavier the object (or the longer it takes to create it), the bigger the benefit.&lt;/p&gt;

&lt;h2&gt;
  
  
  Some other ways to consume iterables
&lt;/h2&gt;

&lt;p&gt;So far we've been playing only with a &lt;code&gt;for ... of&lt;/code&gt; loop, or we've been consuming our iterators manually, using the &lt;code&gt;next&lt;/code&gt; method.&lt;/p&gt;

&lt;p&gt;But those are not your only options!&lt;/p&gt;

&lt;p&gt;We've already seen that &lt;code&gt;Map&lt;/code&gt; constructor accepts an iterable as an argument.&lt;/p&gt;

&lt;p&gt;You can also easily transform an iterable into an actual array by using &lt;code&gt;Array.from&lt;/code&gt; method. Be careful though! As we've said, laziness is sometimes a big benefit of an iterator. Converting it to an array gets rid of all the laziness. All the values returned by an iterator get initialized immediately and then they get put into an array.&lt;/p&gt;

&lt;p&gt;In particular, this means that trying to convert our infinite &lt;code&gt;counterIterator&lt;/code&gt; into an array would result in a catastrophe. &lt;code&gt;Array.from&lt;/code&gt; would just run forever and never return any result! So before converting an iterable/iterator to an array, make sure it's a safe operation.&lt;/p&gt;

&lt;p&gt;Interestingly, iterables also play nicely with a spread operator (&lt;code&gt;...&lt;/code&gt;). Just keep in mind that this works similarly to an &lt;code&gt;Array.from&lt;/code&gt;, where all the values of an iterator get initialized at once.&lt;/p&gt;

&lt;p&gt;For example, we can use the spread operator to create our own version of &lt;code&gt;Array.from&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;We just apply the operator on an iterable and then put the values into an array:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;arrayFromIterator&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[...&lt;/span&gt;&lt;span class="nx"&gt;iterable&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We can also get all the values from an iterable and apply them to a function:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;
&lt;span class="nx"&gt;someFunction&lt;/span&gt;&lt;span class="p"&gt;(...&lt;/span&gt;&lt;span class="nx"&gt;iterable&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;I hope that at this point you understand why the title of this article was "Iterables &lt;em&gt;and&lt;/em&gt; Iterators".&lt;/p&gt;

&lt;p&gt;We've learned what are they, how do they differ, how to use them, and how to create your own instances of them.&lt;/p&gt;

&lt;p&gt;This makes us more than ready to deal with generators. In fact, if you understand iterators well, then jumping into generators should be no problem at all!&lt;/p&gt;

&lt;p&gt;If you've enjoyed this article and want more, remember to subscribe to me on &lt;a href="https://twitter.com/m_podlasin"&gt;Twitter&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Thanks for reading!&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>codenewbie</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>Iterables &amp; Iterators in JS, Part III - "Advanced" concepts (YouTube tutorial)</title>
      <dc:creator>mpodlasin</dc:creator>
      <pubDate>Wed, 09 Dec 2020 21:38:34 +0000</pubDate>
      <link>https://forem.com/mpodlasin/iterables-iterators-in-js-part-iii-advanced-concepts-youtube-tutorial-180i</link>
      <guid>https://forem.com/mpodlasin/iterables-iterators-in-js-part-iii-advanced-concepts-youtube-tutorial-180i</guid>
      <description>&lt;p&gt;This is the last video of my 3 part Iterables &amp;amp; Iterators series!&lt;/p&gt;

&lt;p&gt;This time we cover some "advanced" concepts, which are actually not &lt;em&gt;that&lt;/em&gt; advanced - I just needed some name for this episode. ;)&lt;/p&gt;

&lt;p&gt;And in the next video we will finally move on to long-awaited &lt;strong&gt;generators&lt;/strong&gt;, so stay tuned!&lt;/p&gt;

&lt;p&gt;Enjoy!&lt;/p&gt;

&lt;p&gt;&lt;iframe width="710" height="399" src="https://www.youtube.com/embed/vJLRRuVzTCQ"&gt;
&lt;/iframe&gt;
&lt;/p&gt;

</description>
    </item>
  </channel>
</rss>
