<?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: Michael Taggart</title>
    <description>The latest articles on Forem by Michael Taggart (@mttaggart).</description>
    <link>https://forem.com/mttaggart</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%2F37245%2F614baea3-83a9-4cd5-9a54-36b7787deb14.jpg</url>
      <title>Forem: Michael Taggart</title>
      <link>https://forem.com/mttaggart</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://forem.com/feed/mttaggart"/>
    <language>en</language>
    <item>
      <title>Programming and Bloom's Taxonomy</title>
      <dc:creator>Michael Taggart</dc:creator>
      <pubDate>Thu, 07 Dec 2017 18:00:26 +0000</pubDate>
      <link>https://forem.com/mttaggart/programming-and-blooms-taxonomy-85g</link>
      <guid>https://forem.com/mttaggart/programming-and-blooms-taxonomy-85g</guid>
      <description>&lt;p&gt;&lt;em&gt;Originally appeared &lt;a href="https://theforeverstudent.com/cs-ed-week-part-3-programming-and-blooms-taxonomy-151cfc0d550f"&gt;on my blog&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;You can't get near education theory in the 21st century without Benjamin Bloom's &lt;a href="https://en.wikipedia.org/wiki/Bloom%27s_taxonomy"&gt;categorization of cognitive activities&lt;/a&gt;. Yes, there are accompanying taxonomies for affective and psychomotor activities, but for now, I'm focusing on the cognitive set. Let's all recite them together:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Remembering&lt;/li&gt;
&lt;li&gt;Comprehending&lt;/li&gt;
&lt;li&gt;Applying&lt;/li&gt;
&lt;li&gt;Analyzing&lt;/li&gt;
&lt;li&gt;Synthesizing&lt;/li&gt;
&lt;li&gt;Evaluating&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Amen. These are ordered by cognitive complexity, and as it so happens, map extremely well onto the process of learning the skills of computer programming. Perhaps that's obvious: a framework for describing learning describes how you learn something. Still, I'd argue that the congruence is remarkable. Some subjects engage with many of these levels at once, asking students to analyze, synthesize, and evaluate all at once. In programming, it is difficult to approach a higher echelon before mastering the ones beneath.&lt;/p&gt;

&lt;p&gt;Let me explain with my own experience learning these skills.&lt;/p&gt;

&lt;h2&gt;
  
  
  Remembering
&lt;/h2&gt;

&lt;p&gt;There are ways in which learning to program is like learning a language—the symbols and syntax of each programming language is unique, and it takes time to memorize these sufficiently to produce code that is not riddled with errors.&lt;/p&gt;

&lt;p&gt;Here's a bit of code in Python—my first language—that checks whether a number is even or odd:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;is_even&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="o"&gt;%&lt;/span&gt; &lt;span class="mi"&gt;2&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="bp"&gt;True&lt;/span&gt;
    &lt;span class="k"&gt;elif&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="o"&gt;%&lt;/span&gt; &lt;span class="mi"&gt;2&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="bp"&gt;False&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I am willing to bet that even if you've never read a line of Python before, you can make some sense of that. The modulus (&lt;code&gt;%&lt;/code&gt;) returns the remainder of integer division, so essentially I'm saying:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;If, when dividing &lt;code&gt;n&lt;/code&gt; by 2, I get zero, &lt;code&gt;n&lt;/code&gt; really &lt;em&gt;is&lt;/em&gt; even. &lt;/p&gt;

&lt;p&gt;Otherwise, if I get anything that &lt;em&gt;isn't&lt;/em&gt; zero, &lt;code&gt;n&lt;/code&gt; is a phony, a fake. A flim-flammer.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;This bit of Python is syntactically perfect. Of course, it took me days to be able to rattle off something like this without constantly checking the &lt;a href="//https//docs.python.org"&gt;reference documentation&lt;/a&gt;. But the syntax, the symbols, were the first thing I had to learn. I had to &lt;em&gt;remember&lt;/em&gt; what Python was even supposed to look like.&lt;/p&gt;

&lt;p&gt;But you know what? This code is partially nonsense. It's a little like a &lt;a href="https://en.wikipedia.org/wiki/Colorless_green_ideas_sleep_furiously"&gt;Chomsky sentence&lt;/a&gt;: structurally sound, but functionally useless. To fix it, I had to &lt;em&gt;comprehend&lt;/em&gt; something more about the task. In this case, something about the nature of functions, and the nature of if/else statements.&lt;/p&gt;

&lt;h2&gt;
  
  
  Comprehending
&lt;/h2&gt;

&lt;p&gt;"If it's sunny, then I'll go to the beach. Otherwise, I'll go to the movies."&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;sunny&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="bp"&gt;True&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
    &lt;span class="n"&gt;go_to_beach&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="n"&gt;go_to_movies&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A contrived example perhaps, but that's how &lt;em&gt;conditionals&lt;/em&gt; work. We perform tests on our information, and then we execute different commands accordingly. You can see how the same structure exists in English, and maps well onto Python's syntax. But you'll also notice that the second part of the code is an &lt;code&gt;else&lt;/code&gt;, not an &lt;code&gt;elif&lt;/code&gt; like above. Conditionals, if they have more than one option, &lt;em&gt;must&lt;/em&gt; end with &lt;code&gt;else&lt;/code&gt;; it's the default behavior. And I didn't comprehend why when I wrote the syntactically-correct version above, it was yelling at me.&lt;/p&gt;

&lt;p&gt;Once I &lt;em&gt;comprehended&lt;/em&gt; the rule that conditionals must end in &lt;code&gt;else&lt;/code&gt;, I rewrote it as:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;is_even&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="o"&gt;%&lt;/span&gt; &lt;span class="mi"&gt;2&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="bp"&gt;True&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;return&lt;/span&gt; &lt;span class="bp"&gt;False&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;But I still had more to comprehend. This time, about functions.&lt;/p&gt;

&lt;p&gt;That &lt;code&gt;def is_even(n):&lt;/code&gt; line above is the start of a function. Like in math, functions take information in and spit something back out. That's what the &lt;code&gt;return&lt;/code&gt; symbol is all about: spitting back either &lt;code&gt;True&lt;/code&gt; or &lt;code&gt;False&lt;/code&gt; based on whether the number is even. Functions can only return one thing—after they do a return, they stop until they're "called again." So if I have &lt;code&gt;4&lt;/code&gt; to my &lt;code&gt;is_even&lt;/code&gt; function, it would test to see if &lt;code&gt;4&lt;/code&gt; is evenly divided by &lt;code&gt;2&lt;/code&gt;, and if so, return &lt;code&gt;True&lt;/code&gt;. The &lt;code&gt;elif&lt;/code&gt; ("else if") part of the code isn't even touched in that case.&lt;/p&gt;

&lt;p&gt;Turns out, I don't even &lt;em&gt;need&lt;/em&gt; the &lt;code&gt;else&lt;/code&gt;! Just a single &lt;code&gt;if&lt;/code&gt; will do, because if that test passes, &lt;code&gt;return&lt;/code&gt; ensures the rest of the function isn't run. So my final form looks like:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;is_even&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="o"&gt;%&lt;/span&gt; &lt;span class="mi"&gt;2&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="bp"&gt;True&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="bp"&gt;False&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A tad more elegant, no? Concision isn't necessarily a goal for programmers (readability is), but it tends to result from a deep understanding of the tools at one's disposal.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;UPDATE:&lt;/strong&gt; &lt;a href="https://dev.to/courier10pt"&gt;Bob&lt;/a&gt; accurately points out that the following:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;is_even&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="o"&gt;%&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;...is even more elegant. I often, when writing teaching code, leave the last step of elegance to preserve clarity. Still, the above is worth understanding as an improvement.&lt;/p&gt;

&lt;h2&gt;
  
  
  Applying
&lt;/h2&gt;

&lt;p&gt;Certainly writing a function to tell even numbers from odd is a bit contrived. Nevertheless, the patterns I learned in this exercise would become invaluable in the countless functions I went on to write.&lt;/p&gt;

&lt;p&gt;If we zoom out from the specifics of evenness/oddness, what is this function doing? It's determining the nature of an object, sorting it into one of two categories. Of course in human life, binary states are rare; life is shades of gray. But in pure reason, it is often the case that we must determine whether something &lt;em&gt;is&lt;/em&gt; or &lt;em&gt;is not&lt;/em&gt;. Every time we do, this pattern emerges. With a firm comprehension of the form of this reasoning, of its pattern, I was able to apply it to other problems.&lt;/p&gt;

&lt;h2&gt;
  
  
  Analyzing
&lt;/h2&gt;

&lt;p&gt;As a writer and English teacher, I took pride in my proofreading abilities. I'd find that missing Oxford comma, that malapropistic "its." Reflecting on this ability, I'm certain it derives from sufficient practice, yes, but also sufficient reading such that my comprehension of the "rules" of language made violations of the rules readily apparent. &lt;/p&gt;

&lt;p&gt;A typo or grammatical error can be irritating. A program that doesn't run because of a logical flaw &lt;em&gt;or&lt;/em&gt; a typo (it can be difficult to tell one from the other) is infuriating.&lt;/p&gt;

&lt;p&gt;Here's a line I feed to all my students: programming is a uniquely frustrating discipline, because most of the time you spend working on a problem, it feels like you're failing. Once it works, you stop and move on to the next. And when you get it wrong, you know right away. No craft so ruthlessly exposes your own logical flaws.&lt;/p&gt;

&lt;p&gt;Enticed yet?&lt;/p&gt;

&lt;p&gt;Okay so to properly analyze one's own code or someone else's, the first two tiers of the Taxonomy must be well in-hand.&lt;/p&gt;

&lt;p&gt;Ah, but analysis in the realm of programming also refers to the problem domain. A programmer has to understand the operating parameters and solve within them. To build a bridge, one must first read the terrain, measure the gorge, and plan carefully. It is in analysis where programming begins to resemble engineering in its thought processes. &lt;/p&gt;

&lt;h2&gt;
  
  
  Synthesizing
&lt;/h2&gt;

&lt;p&gt;The examples so far have been rather simplistic, in part because they can afford to be. And even in most programming curricula, the tasks set students will be one- or two-dimensional up to the level of synthesis: write a function that takes X and returns Y; implement function A to integrate with output from function B. You'll find significant amounts of scaffolding in the early chapters of a programming curriculum. In order to give beginners anything like an authentic experience, the tasks set to them have to be contextualized in ways that resemble what they'll encounter later in their journey. Real software applications have a lot of moving parts. It's a Rube Goldberg machine up in there.&lt;/p&gt;

&lt;p&gt;So by the time students reach the synthesis phase, they can code a multidimensional project. A real application.&lt;/p&gt;

&lt;p&gt;Or, y'know, direct an &lt;a href="https://www.youtube.com/watch?v=qybUFnY7Y8w"&gt;OK Go&lt;/a&gt; video.&lt;/p&gt;

&lt;h2&gt;
  
  
  Evaluating
&lt;/h2&gt;

&lt;p&gt;Up here in the thin air of Bloom's, we have evaluation. In programming—and perhaps in writing—this is where style emerges. The programmer has a strong enough foundation in their craft to begin making choices about how to approach a given problem. Shall we use object-oriented or functional patterns? Would a stack or queue data structure make more sense? Should I attempt a recursive algorithm?&lt;/p&gt;

&lt;p&gt;Choice may even extend into the programming language for a given problem domain. With broad experience comes a broad array of options, and programming languages are just tools. &lt;/p&gt;

&lt;p&gt;But how could a programmer make such choices without experiencing extending to fully completed projects. Put another way, programmers must have completed a synthesis before ascending to evaluation.&lt;/p&gt;

&lt;h2&gt;
  
  
  Beyond Bloom
&lt;/h2&gt;

&lt;p&gt;Bloom's Taxonomy fits the programmer's journey well enough, as far as it goes. However, one criticism of the Taxonomy is its hyper-individualism. It's a curious model, given the social nature of, well, humanity in general, but certainly of learning. Any Harkness teacher will tell you that deep learning is a social enterprise, yet Bloom functionally elides discourse and dialectic in the Taxonomy. One might argue that the emotive component of the Taxonomy speaks to it, but emotional activities are specifically distinct from the cognitive, yet intellectual discussions are definitionally cognitive. &lt;/p&gt;

&lt;p&gt;So I have beef with Bloom here, especially when it comes to programming, since programmers no longer work in solitude. To fully master the craft, a programmer must join a community of others, sharing experiences and code in an open marketplace of ideas.&lt;/p&gt;

&lt;h3&gt;
  
  
  Sharing
&lt;/h3&gt;

&lt;p&gt;It takes courage to publish one's code to the internet, open to the scrutiny of others. &lt;a href="https://github.com/explore"&gt;Yet millions do this every day&lt;/a&gt;. We'll talk more about open source tomorrow, but joining the community of programmers is an integral part of mastery. Learning how to discuss issues, contribute helpfully on projects, and hold oneself accountable for assigned work as part of a team transforms programming from craft to profession.&lt;/p&gt;

&lt;h3&gt;
  
  
  Community-Building
&lt;/h3&gt;

&lt;p&gt;Lastly, the young programmer will hopefully start their own open source project that develops a community of contributors around it. Here, the programmer is now also a connector of people, responsible for the communal bonds that develop around the common goal of the project. Success here is no longer situated in the craft of programmer, but the more holistic human skills we hope to impart to all students.&lt;/p&gt;

&lt;p&gt;In short, the full path of the programmer is not so different from other skills or disciplines: mastery makes one, through the hard work along the way, a good person.&lt;/p&gt;

</description>
      <category>learning</category>
    </item>
    <item>
      <title>Things I learned writing my first Elm app</title>
      <dc:creator>Michael Taggart</dc:creator>
      <pubDate>Sun, 26 Nov 2017 15:40:24 +0000</pubDate>
      <link>https://forem.com/mttaggart/things-i-learned-writing-my-first-elm-app-27b</link>
      <guid>https://forem.com/mttaggart/things-i-learned-writing-my-first-elm-app-27b</guid>
      <description>&lt;p&gt;Some disclaimers up front. I am not a professional developer; I'm a self-taught programmer who's found himself in the unlikely position to be the Director of Technology for a school. Possessed of these skills, it's often the case that I see value in building a solution to our problems rather than purchasing one. To do this means successfully passing a rigorous cost-benefit analysis in which "build" beats "buy." It also means I have to build in such a way that I am not the only person who can maintain applications that become mission-critical. &lt;/p&gt;

&lt;p&gt;I'd like to tell you that I therefore follow every best practice: thorough documentation, writing tests for everything. I'm not there yet. I'm still learning.&lt;/p&gt;

&lt;p&gt;About a year ago I learned about &lt;a href="https://elm-lang.org"&gt;Elm&lt;/a&gt;. Having dabbled in Haskell and written a React Redux app, I was completely enamored with functional programming and &lt;a href="https://guide.elm-lang.org/architecture/"&gt;The Elm Architecture&lt;/a&gt;, in particular. So when the opportunity to rewrite an in-house scheduling app came about, I knew I wanted to use Elm. It wasn't a particularly complex application, just a way to create recurring events on a six-day rotation rather than daily, weekly, or monthly. The perfect size for a foray into a new language.&lt;/p&gt;

&lt;p&gt;But hang on, what about that maintainability thing? Wouldn't introducing a &lt;em&gt;completely alien&lt;/em&gt; language be a nightmare for anyone besides me who had to look at the code?&lt;/p&gt;

&lt;p&gt;That brings me to the first thing I learned.&lt;/p&gt;

&lt;h2&gt;
  
  
  Elm makes some clean code
&lt;/h2&gt;

&lt;p&gt;I am in love with the way Elm code reads. The &lt;code&gt;update&lt;/code&gt; function takes a set of messages sent by the &lt;code&gt;view&lt;/code&gt; and updates the &lt;code&gt;model&lt;/code&gt; (state of the app/module). It looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight elm"&gt;&lt;code&gt;&lt;span class="n"&gt;update&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kt"&gt;Action&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;Model&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;Model&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="kt"&gt;Cmd&lt;/span&gt; &lt;span class="kt"&gt;Action&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;update&lt;/span&gt; &lt;span class="n"&gt;action&lt;/span&gt; &lt;span class="n"&gt;model&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt;
    &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="n"&gt;action&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt;
        &lt;span class="kt"&gt;NoOp&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;
            &lt;span class="n"&gt;model&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt; &lt;span class="p"&gt;[]&lt;/span&gt;

        &lt;span class="kt"&gt;RequestCalendars&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;
            &lt;span class="n"&gt;model&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt; &lt;span class="n"&gt;getCalendarList&lt;/span&gt; &lt;span class="n"&gt;clientId&lt;/span&gt; &lt;span class="p"&gt;]&lt;/span&gt;

        &lt;span class="kt"&gt;ReceiveCalendars&lt;/span&gt; &lt;span class="n"&gt;calendars&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;
            &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="n"&gt;model&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;calendars&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;calendars&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;span class="n"&gt;getLetterDays&lt;/span&gt; &lt;span class="n"&gt;letterDayCalendar&lt;/span&gt; &lt;span class="p"&gt;]&lt;/span&gt; 

        &lt;span class="kt"&gt;RequestLetterDayEvents&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;
            &lt;span class="n"&gt;model&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt; &lt;span class="n"&gt;getLetterDays&lt;/span&gt; &lt;span class="n"&gt;letterDayCalendar&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've never read a functional language, that might look completely bananas. The first thing to know is that the top line is the function definition. It tells us what types come in to the function, and what type comes out. Then we name the arguments in the second line, which is equivalent to &lt;code&gt;function update(action, model){&lt;/code&gt;. &lt;/p&gt;

&lt;p&gt;The &lt;code&gt;action&lt;/code&gt; argument is of a special type that I've described myself. It describes the kinds of messages the view (what users see/interact with) can send to &lt;code&gt;update&lt;/code&gt;. Beneath that, you see a &lt;code&gt;case/of&lt;/code&gt; statement, which is similar to a &lt;code&gt;switch&lt;/code&gt; statement in JS. Each line after an &lt;code&gt;-&amp;gt;&lt;/code&gt; indicates what &lt;code&gt;update&lt;/code&gt; should return in the case of that given &lt;code&gt;action&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;Action&lt;/code&gt;, in fact, is part of the second thing I learned.&lt;/p&gt;

&lt;h2&gt;
  
  
  I love strict typing
&lt;/h2&gt;

&lt;p&gt;My programming journey began in Python, then moved to PHP, then JavaScript. So for a long time I had a bit of apprehension about static typing, to say nothing of strict typing. Then I learned Haskell, and discovered a new way to think about programming. Procedural languages treat programs as sets of instructions to execute in order—the classic "recipe" example. And that's all fine, and is often the absolutely correct way to conceive of a problem space. By contrast, functional languages like Haskell and Elm ask the programmer to consider the "shape" of information coming into a function and the shape that should emerge from a function. Applying the right operations to the information between input and output produces the desired result. Rather than thinking of steps in order, you begin thinking of enclosed transformations. In doing so, you &lt;em&gt;must&lt;/em&gt; be completely clear on your data types between input and output. That's where strict typing comes in. By defining functions first in terms of what comes in and goes out, there's never any ambiguity about what's happening or what's being passed around your code.&lt;/p&gt;

&lt;p&gt;Consider the following mega-contrived example:&lt;/p&gt;

&lt;p&gt;Suppose I wanted to write a function that takes in an array of numbers and returns them squared. Easy enough, right? Here is such a function in JS:&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;squareEach&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;nums&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;res&lt;/span&gt; &lt;span class="o"&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;const&lt;/span&gt; &lt;span class="nx"&gt;n&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;nums&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="nx"&gt;res&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;push&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;n&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;n&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;res&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;Okay, I know there's a cleaner way. Here you go:&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;squareEach&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;nums&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;nums&lt;/span&gt;&lt;span class="p"&gt;.&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;n&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="nx"&gt;n&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;n&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;Problem is, I could only know &lt;code&gt;nums&lt;/code&gt;'s type through comments. And while comments are good, nothing in comments will stop me from writing a really bad bit of code that ends up sending &lt;code&gt;undefined&lt;/code&gt; or something worse to &lt;code&gt;squareEach()&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Now, here's the same function in Elm:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight elm"&gt;&lt;code&gt;&lt;span class="n"&gt;squareEach&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kt"&gt;List&lt;/span&gt; &lt;span class="kt"&gt;Int&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;List&lt;/span&gt; &lt;span class="kt"&gt;Int&lt;/span&gt;
&lt;span class="n"&gt;squareEach&lt;/span&gt; &lt;span class="n"&gt;nums&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt;
    &lt;span class="kt"&gt;List&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;map&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;\&lt;/span&gt;&lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;nums&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;First I define &lt;code&gt;squareEach&lt;/code&gt;, telling Elm (and anyone reading my code) that it will take a list of integers and return the same kind of thing. Then I implement it, using a lambda (anonymous function) and &lt;code&gt;List.map&lt;/code&gt; to emulate the same behavior as &lt;code&gt;Array.map()&lt;/code&gt; in the second JavaScript example.&lt;/p&gt;

&lt;p&gt;Now suppose I write some function elsewhere that tries to pass, say, a &lt;code&gt;String&lt;/code&gt; to &lt;code&gt;squareEach&lt;/code&gt;. The Elm compiler will catch it and provide an error for me. I can't even &lt;em&gt;compile&lt;/em&gt; stupid type mistakes.&lt;/p&gt;

&lt;p&gt;And that's thing #3 I learned.&lt;/p&gt;

&lt;h2&gt;
  
  
  Love recompiling
&lt;/h2&gt;

&lt;p&gt;I fought with the Elm compiler a lot. Some mornings, I just had to stand up and walk away from the computer, since I could not get the compiler to agree to build my code. Invariably, my thinking was in error and taking the time to correct my mistakes the proper way resulted in cleaner, more elegant code. Spending copious amounts of time reading documentation helped. It isn't a great feeling, constant screens of red text in my terminal as Elm code fails. But you know what's an &lt;em&gt;incredible&lt;/em&gt; feeling?&lt;/p&gt;

&lt;p&gt;No runtime errors. &lt;/p&gt;

&lt;p&gt;That's the tradeoff: rather than finding a ton of errors in production because an unexpected value slipped passed me, even with tests, hammering away against compiler errors results in a fairly stable application. No surprise &lt;code&gt;undefined&lt;/code&gt;s to wreck your runtime. This isn't to say that Elm makes failproof apps—any language is only as good as its user. However, the number of issues caught by the compiler vastly reduces live debugging. Adding good tests to this mix is an even greater guarantee of stability. &lt;/p&gt;

&lt;p&gt;Well, I say "stable," but...&lt;/p&gt;

&lt;h2&gt;
  
  
  Elm ain't done yet
&lt;/h2&gt;

&lt;p&gt;There's no question this language is going places, and I've never had more fun putting together a frontend. Nevertheless, there are a few pieces still missing from the &lt;code&gt;core&lt;/code&gt; library, like reasonable &lt;code&gt;Date/Time&lt;/code&gt; tools. I used Justin Mimb's excellent &lt;a href="http://package.elm-lang.org/packages/justinmimbs/elm-date-extra/"&gt;date-extra&lt;/a&gt; package to handle date/time parsing. But I shouldn't have to install a third-party dependency for ISO Strings, or to compare (&lt;code&gt;&amp;lt;&lt;/code&gt;, &lt;code&gt;&amp;gt;&lt;/code&gt;) &lt;code&gt;Date&lt;/code&gt;s.&lt;/p&gt;

&lt;p&gt;On the flip-side, the community packages are of a high quality. Just know that if you're making a non-trivial app with Elm, you'll end up installing a couple of third-party dependencies, or writing a bunch of your own helper code.&lt;/p&gt;

&lt;p&gt;So if you want to change the way you think about programming, I highly recommend checking out a functional language. And if you want to fall in love with frontend again, I highly recommend Elm.&lt;/p&gt;

</description>
      <category>elm</category>
      <category>functional</category>
      <category>frontend</category>
    </item>
  </channel>
</rss>
