<?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>DEV Community: Elodie Lander</title>
    <description>The latest articles on DEV Community by Elodie Lander (@elodielander).</description>
    <link>https://dev.to/elodielander</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%2F1777843%2F39b403da-d939-46cb-b8e4-c800a86b3904.png</url>
      <title>DEV Community: Elodie Lander</title>
      <link>https://dev.to/elodielander</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/elodielander"/>
    <language>en</language>
    <item>
      <title>Doing Horrible Things in Haskell</title>
      <dc:creator>Elodie Lander</dc:creator>
      <pubDate>Sun, 04 Aug 2024 02:54:08 +0000</pubDate>
      <link>https://dev.to/elodielander/doing-horrible-things-in-haskell-13fh</link>
      <guid>https://dev.to/elodielander/doing-horrible-things-in-haskell-13fh</guid>
      <description>&lt;p&gt;A while back I encountered a conversation on a platform that shall remain unnamed, where people were recommending must-read books on software engineering and programming. One of the recommendations was &lt;a href="https://moys.gov.iq/upload/common/Programming_in_Lua,_4th_ed._(2017)_.pdf" rel="noopener noreferrer"&gt;Programming in Lua&lt;/a&gt; by &lt;a href="https://en.wikipedia.org/wiki/Roberto_Ierusalimschy" rel="noopener noreferrer"&gt;Roberto Ierusalimschy&lt;/a&gt;, the creator of the Lua programming language. Wishing to brush up on my admittedly rusty imperative programming skills, I decided to take a look at Programming in Lua.&lt;/p&gt;

&lt;p&gt;To my surprise and dismay, the first large exercise gave me real trouble! How could it be so difficult to understand code in an introductory text, given that I have been coding for years? The answer of course is that when I do functional programming, there are fundamental differences in how I approach problem solving. For me, the approach taken by the exercise's starting code was very difficult to reason about.&lt;/p&gt;

&lt;p&gt;As I was struggling through the exercise, eventually coming to understand how the code worked, a truly cursed idea occurred to me. What if I were to attempt to clone this tiny Lua program in Haskell? I don't mean simply writing a Haskell program that exhibits the same behavior as the Lua code, but imitating the style of the Lua code. This would involve using the parts of Haskell that we are taught to avoid whenever possible, in favor of the easier-to-reason-about functional idioms. It would be an absolutely horrible thing to do. So I decided to do it and write this post about the experience.&lt;/p&gt;

&lt;p&gt;The exercise in question is Chapter 2 of the book. The exercise begins with a complete program and then asks the reader to make some modifications to the behavior of the program. This post will cover the Haskell translation of the starting code. If I feel so inclined, I may cover the exercises themselves in future posts. All of the code in this post can be found in &lt;a href="https://github.com/nlander/horrible_things" rel="noopener noreferrer"&gt;this repository&lt;/a&gt;. I have doctored the commit history so that you should be able to follow along by stepping through the commits.&lt;/p&gt;

&lt;p&gt;The problem presented in this exercise is called the Eight Queen Puzzle. Ierusalimschy describes the puzzle: "its goal is to position eight queens in a chessboard in such a way that no queen can&lt;br&gt;
attack another one" The book further details the problem as follows:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;A first step to solving the eight-queen puzzle is to note that any valid solution must have exactly one queen in each row. Therefore, we can represent potential solutions with a simple array of eight numbers, one for each row; each number tells at which column is the queen at that row. For instance, the array {3, 7, 2, 1, 8, 6, 5, 4} means that the queens are in the squares (1,3), (2,7), (3,2), (4,1), (5,8), (6,6), (7,5), and (8,4). (By the way, this is not a valid solution; for instance, the queen in square (3,2) can attack the one in square (4,1).) Note that any valid solution must be a permutation of the integers 1 to 8, as a valid solution also must have exactly one queen in each column.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Here is the initial solution program in Lua, as it is presented in the book:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight lua"&gt;&lt;code&gt;&lt;span class="n"&gt;N&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;8&lt;/span&gt; &lt;span class="c1"&gt;-- board size&lt;/span&gt;
&lt;span class="c1"&gt;-- check whether position (n,c) is free from attacks&lt;/span&gt;
&lt;span class="k"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;isplaceok&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&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="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;i&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="n"&gt;n&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt; &lt;span class="c1"&gt;-- for each queen already placed&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="ow"&gt;or&lt;/span&gt; &lt;span class="c1"&gt;-- same column?&lt;/span&gt;
      &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&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="ow"&gt;or&lt;/span&gt; &lt;span class="c1"&gt;-- same diagonal?&lt;/span&gt;
      &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&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="k"&gt;then&lt;/span&gt; &lt;span class="c1"&gt;-- same diagonal?&lt;/span&gt;
      &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="c1"&gt;-- place can be attacked&lt;/span&gt;
    &lt;span class="k"&gt;end&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;-- no attacks; place is OK&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;

&lt;span class="c1"&gt;-- print a board&lt;/span&gt;
&lt;span class="k"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;printsolution&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;i&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="n"&gt;N&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt; &lt;span class="c1"&gt;-- for each row&lt;/span&gt;
    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;j&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="n"&gt;N&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt; &lt;span class="c1"&gt;-- and for each column&lt;/span&gt;
      &lt;span class="c1"&gt;-- write "X" or "-" plus a space&lt;/span&gt;
      &lt;span class="nb"&gt;io.write&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;j&lt;/span&gt; &lt;span class="ow"&gt;and&lt;/span&gt; &lt;span class="s2"&gt;"X"&lt;/span&gt; &lt;span class="ow"&gt;or&lt;/span&gt; &lt;span class="s2"&gt;"-"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;" "&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;end&lt;/span&gt;
    &lt;span class="nb"&gt;io.write&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
  &lt;span class="nb"&gt;io.write&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;

&lt;span class="c1"&gt;-- add to board 'a' all queens from 'n' to 'N'&lt;/span&gt;
&lt;span class="k"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;addqueen&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&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;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;N&lt;/span&gt; &lt;span class="k"&gt;then&lt;/span&gt; &lt;span class="c1"&gt;-- all queens have been placed?&lt;/span&gt;
    &lt;span class="n"&gt;printsolution&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="c1"&gt;-- try to place n-th queen&lt;/span&gt;
    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;c&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="n"&gt;N&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;isplaceok&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&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="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;then&lt;/span&gt;
        &lt;span class="n"&gt;a&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="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="c1"&gt;-- place n-th queen at column 'c'&lt;/span&gt;
        &lt;span class="n"&gt;addqueen&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&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;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="k"&gt;end&lt;/span&gt;
    &lt;span class="k"&gt;end&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;

&lt;span class="c1"&gt;-- run the program&lt;/span&gt;
&lt;span class="n"&gt;addqueen&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;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Ierusalimschy explains the Lua solution:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;The first function is isplaceok, which checks whether a given position on a board is free from attacks from previously placed queens. More specifically, it checks whether putting the n-th queen in column c will conflict with any of the previous n-1 queens already set in the array a. Remember that, by represen- tation, two queens cannot be in the same row, so isplaceok checks whether there are no queens in the same column or in the same diagonals of the new position. Next we have the function printsolution, which prints a board. It simply traverses the entire board, printing an X at positions with a queen and a - at other positions, without any fancy graphics. (Note its use of the and–or idiom to select the character to print at each position.) Each result will look like this:&lt;br&gt;
&lt;/p&gt;
&lt;/blockquote&gt;

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

&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;The last function, addqueen, is the core of the program. It tries to place all queens larger than or equal to n in the board. It uses backtracking to search for valid solutions. First, it checks whether the solution is complete and, if so, prints that solution. Otherwise, it loops through all columns for the n-th queen; for each column that is free from attacks, the program places the queen there and recursively tries to place the following queens. Finally, the main body simply calls addqueen on an empty solution.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;After reading this explanation, I copied the lua code into my text editor and ran it. I was surprised to see that the program prints not just one, but all of the solutions to the Eight Queen Puzzle! Why did I find it difficult to understand about this program's behavior? At a first glance, I thought that it would print only the first solution it encountered. After all, when the board is full, it hits the recursive "base case" and ends execution after printing the solution. What I failed to notice is that the recursive call in &lt;code&gt;addqueen&lt;/code&gt; happens &lt;em&gt;inside a for loop&lt;/em&gt;. So while the execution of that particular recursive tree may have terminated, the for loop in which that recursive function call was made is still running! This is not at all idiomatic in functional programming, even though it is technically possible to put a recursive call inside of a fold.&lt;/p&gt;

&lt;p&gt;With a hard-won understanding of how the Lua code works, I started to think about how I could do similarly tough-to-understand things in Haskell. Let's start with the first function, &lt;code&gt;isplaceok&lt;/code&gt;. It checks if the current position we are looking at is a viable location for the next queen, by looking at the queens that have already been placed. The way this is accomplished in this Lua program is, again, entirely unidiomatic in Haskell. In Haskell I would be inclined to use something like &lt;code&gt;not $ any (\i -&amp;gt; alreadyPlacedQueenCanAttackCurrentPosition i n c) a&lt;/code&gt;. But here I want to imitate the style of the Lua code, which in this case is using a &lt;code&gt;for&lt;/code&gt; loop with &lt;code&gt;return&lt;/code&gt; to short circuit the loop. In Haskell, we don't have loops as language primitives, but we do have the function &lt;a href="https://hackage.haskell.org/package/base-4.20.0.1/docs/Data-Foldable.html#v:for_" rel="noopener noreferrer"&gt;&lt;code&gt;for_&lt;/code&gt;&lt;/a&gt;. I decided to use this function to imitate the &lt;code&gt;for&lt;/code&gt; loop, and the blocking behavior of an &lt;code&gt;MVar&lt;/code&gt; for the short-circuiting. This seemed like a sufficiently cursed solution to me, so I went with 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;isplaceok&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&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;Int&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;MVar&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;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
  &lt;span class="n"&gt;isplaceok&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
    &lt;span class="n"&gt;for_&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;..&lt;/span&gt;&lt;span class="p"&gt;(&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;1&lt;/span&gt;&lt;span class="p"&gt;)]&lt;/span&gt;
      &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;\&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&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;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;-&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&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;||&lt;/span&gt;
                &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt;
             &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="n"&gt;putMVar&lt;/span&gt; &lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt; &lt;span class="c1"&gt;-- set the (assumed to be empty) MVar to False&lt;/span&gt;
             &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
      &lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="kr"&gt;_&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;tryPutMVar&lt;/span&gt; &lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt; &lt;span class="c1"&gt;-- If the MVar wasn't set to False anywhere in the forM_ loop, we set it to True here.&lt;/span&gt;
    &lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Compare this with the original Lua:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight lua"&gt;&lt;code&gt;&lt;span class="k"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;isplaceok&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&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="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;i&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="n"&gt;n&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt; &lt;span class="c1"&gt;-- for each queen already placed&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="ow"&gt;or&lt;/span&gt; &lt;span class="c1"&gt;-- same column?&lt;/span&gt;
      &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&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="ow"&gt;or&lt;/span&gt; &lt;span class="c1"&gt;-- same diagonal?&lt;/span&gt;
      &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&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="k"&gt;then&lt;/span&gt; &lt;span class="c1"&gt;-- same diagonal?&lt;/span&gt;
      &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="c1"&gt;-- place can be attacked&lt;/span&gt;
    &lt;span class="k"&gt;end&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;-- no attacks; place is OK&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Note that I must subtract 1 from &lt;code&gt;i&lt;/code&gt; when indexing because Lua arrays are indexed starting from 1 while Haskell lists are indexed starting from 0.&lt;/p&gt;

&lt;p&gt;Next up is the &lt;code&gt;printsolution&lt;/code&gt; function. This one is pretty straightforward, using for_ in a similar way to how I used it in &lt;code&gt;isplaceok&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;printsolution&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
  &lt;span class="n"&gt;printsolution&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
    &lt;span class="n"&gt;for_&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;..&lt;/span&gt;&lt;span class="n"&gt;boardSize&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;\&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
        &lt;span class="n"&gt;for_&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;..&lt;/span&gt;&lt;span class="n"&gt;boardSize&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;\&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
            &lt;span class="kr"&gt;let&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;bool&lt;/span&gt; &lt;span class="s"&gt;"-"&lt;/span&gt; &lt;span class="s"&gt;"X"&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;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;j&lt;/span&gt;
            &lt;span class="n"&gt;putStr&lt;/span&gt; &lt;span class="o"&gt;$&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="s"&gt;" "&lt;/span&gt;
          &lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="n"&gt;putStr&lt;/span&gt; &lt;span class="s"&gt;"&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt;
      &lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="n"&gt;putStr&lt;/span&gt; &lt;span class="s"&gt;"&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And here's the Lua:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight lua"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- print a board&lt;/span&gt;
&lt;span class="k"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;printsolution&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;i&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="n"&gt;N&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt; &lt;span class="c1"&gt;-- for each row&lt;/span&gt;
    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;j&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="n"&gt;N&lt;/span&gt; &lt;span class="k"&gt;do&lt;/span&gt; &lt;span class="c1"&gt;-- and for each column&lt;/span&gt;
      &lt;span class="c1"&gt;-- write "X" or "-" plus a space&lt;/span&gt;
      &lt;span class="nb"&gt;io.write&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;j&lt;/span&gt; &lt;span class="ow"&gt;and&lt;/span&gt; &lt;span class="s2"&gt;"X"&lt;/span&gt; &lt;span class="ow"&gt;or&lt;/span&gt; &lt;span class="s2"&gt;"-"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s2"&gt;" "&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;end&lt;/span&gt;
    &lt;span class="nb"&gt;io.write&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;end&lt;/span&gt;
  &lt;span class="nb"&gt;io.write&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Finally, we have the &lt;code&gt;addqueen&lt;/code&gt; function, the core of this program. This function is recursive, so it shouldn't create the mutable variables, but instead take them as arguments. This function takes an MVar that it expects to be empty. The &lt;code&gt;placeok&lt;/code&gt; function will fill it, and this function will empty it and check the result to determine whether or not to continue. If the result was True, we have found a valid position to place a queen in this row, and we can make the recursive call to move to the next row. If the result was False, we know that the current position is not valid for the queens we have placed so far, so we need to move to the next column. To do this, we don't make a recursive call and allow the &lt;code&gt;for&lt;/code&gt; loop to continue checking the index for the next column. Also of note is that I needed to define a &lt;code&gt;set&lt;/code&gt; function to update a value in a list, even if it is out of the current bounds of the list. I wrote this &lt;code&gt;set&lt;/code&gt; to take an index starting from 1, like in Lua.&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;addqueen&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;MVar&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;IORef&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&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;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;addqueen&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="n"&gt;n&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;n&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;boardSize&lt;/span&gt;
  &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="n"&gt;readIORef&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&amp;gt;=&lt;/span&gt; &lt;span class="n"&gt;printsolution&lt;/span&gt;
  &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;for_&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;..&lt;/span&gt;&lt;span class="n"&gt;boardSize&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;\&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
           &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;readIORef&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt;
           &lt;span class="n"&gt;isplaceok&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt;
           &lt;span class="n"&gt;placeok&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;takeMVar&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt;
           &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;placeok&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
             &lt;span class="n"&gt;modifyIORef&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="o"&gt;$&lt;/span&gt; &lt;span class="n"&gt;set&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;
             &lt;span class="n"&gt;addqueen&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="p"&gt;(&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;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
           &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
         &lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="kr"&gt;where&lt;/span&gt;
    &lt;span class="n"&gt;set&lt;/span&gt; &lt;span class="o"&gt;::&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;Int&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;Int&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="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
    &lt;span class="n"&gt;set&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;v&lt;/span&gt; &lt;span class="n"&gt;l&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;take&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="n"&gt;l&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="n"&gt;drop&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;l&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Finally, I just needed to define a main function! This is where I initialize the mutable variables, before passing them to the &lt;code&gt;addqueen&lt;/code&gt; 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;main&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;main&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
  &lt;span class="n"&gt;placeokVar&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;newEmptyMVar&lt;/span&gt;
  &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;newIORef&lt;/span&gt; &lt;span class="kt"&gt;[]&lt;/span&gt;
  &lt;span class="n"&gt;addqueen&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With that code in place, I crossed my fingers and ran the code&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;gt; runhaskell haskell/eight-queen-from-text-clone.hs
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;To my dismay, it hung, and then printed out this error:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;eight-queen-from-text-clone.hs: thread blocked indefinitely in an MVar operation
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Nooooo! There was something wrong in my reasoning about my use of MVars. If you already spotted the flaw in my logic, give yourself a pat on the back! I, on the other hand, was a bit puzzled, so I decided to put in some logging to debug the issue.&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;addqueen&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;MVar&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;IORef&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&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;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;addqueen&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="n"&gt;n&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;n&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;boardSize&lt;/span&gt;
  &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="n"&gt;readIORef&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&amp;gt;=&lt;/span&gt; &lt;span class="n"&gt;printsolution&lt;/span&gt;
  &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;for_&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;..&lt;/span&gt;&lt;span class="n"&gt;boardSize&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;\&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
           &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;readIORef&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt;
           &lt;span class="n"&gt;log&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;
           &lt;span class="n"&gt;isplaceok&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt;
           &lt;span class="n"&gt;log&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;
           &lt;span class="n"&gt;placeok&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;takeMVar&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt;
           &lt;span class="n"&gt;log&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;
           &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;placeok&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
             &lt;span class="n"&gt;modifyIORef&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="o"&gt;$&lt;/span&gt; &lt;span class="n"&gt;set&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;
             &lt;span class="n"&gt;log&lt;/span&gt; &lt;span class="mi"&gt;4&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;
             &lt;span class="n"&gt;addqueen&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="p"&gt;(&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;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
           &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
         &lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="kr"&gt;where&lt;/span&gt;
     &lt;span class="n"&gt;set&lt;/span&gt; &lt;span class="o"&gt;::&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;Int&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;Int&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="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
     &lt;span class="n"&gt;set&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;v&lt;/span&gt; &lt;span class="n"&gt;l&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;take&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="n"&gt;l&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="n"&gt;drop&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;l&lt;/span&gt;
     &lt;span class="n"&gt;log&lt;/span&gt; &lt;span class="o"&gt;::&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="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&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;Int&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
     &lt;span class="n"&gt;log&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt;
       &lt;span class="kr"&gt;let&lt;/span&gt; &lt;span class="n"&gt;message&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt;
             &lt;span class="n"&gt;show&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="s"&gt;": a = "&lt;/span&gt;
             &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="n"&gt;show&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="s"&gt;", n = "&lt;/span&gt;
             &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="n"&gt;show&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="s"&gt;", c = "&lt;/span&gt;
             &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="n"&gt;show&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;
       &lt;span class="kr"&gt;in&lt;/span&gt; &lt;span class="n"&gt;putStrLn&lt;/span&gt; &lt;span class="n"&gt;message&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This resulted 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;&amp;gt; runhaskell haskell/eight-queen-from-text-clone.hs
1: a = [], n = 1, c = 1
2: a = [], n = 1, c = 1
3: a = [], n = 1, c = 1
4: a = [], n = 1, c = 1
1: a = [1], n = 2, c = 1
2: a = [1], n = 2, c = 1
3: a = [1], n = 2, c = 1
1: a = [1], n = 2, c = 2
2: a = [1], n = 2, c = 2
3: a = [1], n = 2, c = 2
1: a = [1], n = 2, c = 3
2: a = [1], n = 2, c = 3
3: a = [1], n = 2, c = 3
4: a = [1], n = 2, c = 3
1: a = [1,3], n = 3, c = 1
2: a = [1,3], n = 3, c = 1
3: a = [1,3], n = 3, c = 1
1: a = [1,3], n = 3, c = 2
2: a = [1,3], n = 3, c = 2
3: a = [1,3], n = 3, c = 2
1: a = [1,3], n = 3, c = 3
eight-queen-from-text-clone.hs: thread blocked indefinitely in an MVar operation
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I stared at these log results and didn't quite know what to make of it. I ran it a few times more to ensure that I had it right, and the output was consistently the same. There was no flakiness to be found. After a bit of puzzling over it I was able to make a couple of conclusions. First, my MVar logic, at least with regard to the interaction between &lt;code&gt;addqueen&lt;/code&gt; and &lt;code&gt;isplaceok&lt;/code&gt;, was not fundamentally flawed, as the MVar was being successfully filled and emptied for six calls to &lt;code&gt;addqueen&lt;/code&gt;. We can tell that there are six successful passes of the MVar from &lt;code&gt;addqueen&lt;/code&gt; to &lt;code&gt;isplaceok&lt;/code&gt; and back, because that is how many times we see log 1 followed by log 2, and the call to &lt;code&gt;isplaceok&lt;/code&gt; happens between those two logging statements. Second, the blocking of the MVar must be happening in the seventh call to &lt;code&gt;isplaceok&lt;/code&gt;, as it is the seventh time that log 1 is printed that the program hangs and crashes. I still couldn't see how &lt;code&gt;isplaceok&lt;/code&gt; could be blocking the MVar, so I decided to add some logging to that function as well:&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;isplaceok&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&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;Int&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;MVar&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;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;isplaceok&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
  &lt;span class="n"&gt;for_&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;..&lt;/span&gt;&lt;span class="p"&gt;(&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;1&lt;/span&gt;&lt;span class="p"&gt;)]&lt;/span&gt;
    &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;\&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
           &lt;span class="n"&gt;log&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;
           &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&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;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;-&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&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;||&lt;/span&gt;
              &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt;
           &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="n"&gt;putMVar&lt;/span&gt; &lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt;
           &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
    &lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="kr"&gt;_&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;tryPutMVar&lt;/span&gt; &lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
  &lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
  &lt;span class="kr"&gt;where&lt;/span&gt;
    &lt;span class="n"&gt;log&lt;/span&gt; &lt;span class="o"&gt;::&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;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
    &lt;span class="n"&gt;log&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt;
      &lt;span class="kr"&gt;let&lt;/span&gt; &lt;span class="n"&gt;message&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"i = "&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="n"&gt;show&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;
      &lt;span class="kr"&gt;in&lt;/span&gt; &lt;span class="n"&gt;putStrLn&lt;/span&gt; &lt;span class="n"&gt;message&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With this new logging in place, I ran the program again and saw this output:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;gt; runhaskell haskell/eight-queen-from-text-clone.hs
1: a = [], n = 1, c = 1
2: a = [], n = 1, c = 1
3: a = [], n = 1, c = 1
4: a = [], n = 1, c = 1
1: a = [1], n = 2, c = 1
i = 1
2: a = [1], n = 2, c = 1
3: a = [1], n = 2, c = 1
1: a = [1], n = 2, c = 2
i = 1
2: a = [1], n = 2, c = 2
3: a = [1], n = 2, c = 2
1: a = [1], n = 2, c = 3
i = 1
2: a = [1], n = 2, c = 3
3: a = [1], n = 2, c = 3
4: a = [1], n = 2, c = 3
1: a = [1,3], n = 3, c = 1
i = 1
i = 2
2: a = [1,3], n = 3, c = 1
3: a = [1,3], n = 3, c = 1
1: a = [1,3], n = 3, c = 2
i = 1
i = 2
2: a = [1,3], n = 3, c = 2
3: a = [1,3], n = 3, c = 2
1: a = [1,3], n = 3, c = 3
i = 1
i = 2
eight-queen-from-text-clone.hs: thread blocked indefinitely in an MVar operation
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Seeing the different indices in the &lt;code&gt;isplaceok&lt;/code&gt; function printed out, finally helped me see the flaw in my logic. The blocking functionality of the MVar does nothing to actually make the &lt;code&gt;for_&lt;/code&gt; "loop" short circuit! The MVar turned out to be a good choice for the style, as it forced me to make sure that I was making a loop that would short circuit, but it in itself was not causing the short circuit. Rather, it was blocking execution when the loop failed to short circuit and there were more than one already-placed queen threatening the spot we are checking.&lt;/p&gt;

&lt;p&gt;Let's break this down a little further so there's no confusion. To re-clarify, the logic of &lt;code&gt;isplaceok&lt;/code&gt; determines if a candidate position in row &lt;code&gt;n&lt;/code&gt;, column &lt;code&gt;c&lt;/code&gt;, is threatened by any of the already placed queens. It does this by checking each of the already placed queens in the array &lt;code&gt;a&lt;/code&gt;. For each of the placed queens, it makes three checks. First it checks if the candidate position is in the same column: &lt;code&gt;a !! (i - 1) == c&lt;/code&gt;. This is checking the queen placed in the &lt;code&gt;i&lt;/code&gt;th position of &lt;code&gt;a&lt;/code&gt; (&lt;code&gt;i&lt;/code&gt; denoting the row). Remember that &lt;code&gt;i&lt;/code&gt; is a base-1-index as in Lua, but &lt;code&gt;a&lt;/code&gt; is a base-0-indexed Haskell list. (Please note that I'm using the word base here to denote where we start counting from, not the number system of the indices). Next it checks if the candidate position is in the same diagonal running top-left to bottom-right: &lt;code&gt;a !! (i - 1) - i == c - n&lt;/code&gt;. Finally, it checks if the candidate position is in the same diagonal running top-right to bottom-left: &lt;code&gt;a !! (i - 1) + i == c + n&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;The problematic case, as we can see from the logs, has &lt;code&gt;a = [1,3]&lt;/code&gt;, &lt;code&gt;n = 3&lt;/code&gt;, and &lt;code&gt;c = 3&lt;/code&gt;. The value of &lt;code&gt;a&lt;/code&gt; means that we have already placed a queen at row 1 column 1, and also at row 2 column 3. The values of &lt;code&gt;n&lt;/code&gt; and &lt;code&gt;c&lt;/code&gt; mean that the candidate position is at row 3 column 3. The candidate position is threatened on the diagonal by the first queen, so the second condition resolves to True:&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;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;-&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt;
&lt;span class="cd"&gt;-- | - substitute 1 in for i, 3 for c and 3 for n&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;a&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="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="o"&gt;-&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;
&lt;span class="cd"&gt;-- | - evaluate within the parenthesis&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;
&lt;span class="cd"&gt;-- | - get the value in `a` at Haskell list index 0&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;`&lt;/span&gt;
&lt;span class="cd"&gt;-- | - perform the subtractions&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="mi"&gt;0&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;
&lt;span class="cd"&gt;-- | - evaluate the equality&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As a result, we fill the MVar with the value False: &lt;code&gt;putMVar result False&lt;/code&gt;. The MVar &lt;code&gt;result&lt;/code&gt; is now blocked on further puts until &lt;code&gt;takeMVar&lt;/code&gt; gets called, but &lt;code&gt;for_&lt;/code&gt; is not done processing the list &lt;code&gt;a&lt;/code&gt;! It continues for the second value of &lt;code&gt;i&lt;/code&gt;. As it turns out, the second queen, at row 2 column 3, also threatens the candidate position. It is in the same column, so the first condition resolves to True:&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;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;
&lt;span class="cd"&gt;-- | - substitute 1 in for i and 3 for c&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="p"&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;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;
&lt;span class="cd"&gt;-- | - evaluate within the parenthesis&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;
&lt;span class="cd"&gt;-- | - get the value in `a` at Haskell list index 1&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="mi"&gt;3&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;
&lt;span class="cd"&gt;-- | - evaluate the equality&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="kt"&gt;True&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Once again, we try to put a False value in the &lt;code&gt;result&lt;/code&gt; MVar: &lt;code&gt;putMVar result False&lt;/code&gt;. This time though, the computation is blocked, because the MVar is already full. There is no asynchronous computation to empty the &lt;code&gt;result&lt;/code&gt;, so the program blocks here, and crashes.&lt;/p&gt;

&lt;p&gt;Now I finally understood the error of my logic and I was faced with a new problem. How can I make a for loop that short circuits like a Lua for loop does? First I took a look at the definition of &lt;a href="https://hackage.haskell.org/package/base-4.20.0.1/docs/Data-Foldable.html#v:for_" rel="noopener noreferrer"&gt;&lt;code&gt;for_&lt;/code&gt;&lt;/a&gt; to see if I could use it any differently.&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;for_&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;Int&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="kt"&gt;Int&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&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="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;for_&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;flip&lt;/span&gt; &lt;span class="n"&gt;traverse_&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Okay, that doesn't tell me much. So what is the definition of &lt;a href="https://hackage.haskell.org/package/base-4.20.0.1/docs/Data-Foldable.html#v:traverse_" rel="noopener noreferrer"&gt;&lt;code&gt;traverse_&lt;/code&gt;&lt;/a&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;traverse_&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="p"&gt;(&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;IO&lt;/span&gt; &lt;span class="nb"&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="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;traverse_&lt;/span&gt; &lt;span class="n"&gt;f&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;foldr&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="kr"&gt;where&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="n"&gt;k&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;f&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;*&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;k&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I know that &lt;code&gt;foldr&lt;/code&gt; will short-circuit when the function passed to it doesn't evaluate its second argument. However, the function passed to &lt;code&gt;foldr&lt;/code&gt; here, &lt;code&gt;c&lt;/code&gt;, always evaluates its second argument, &lt;code&gt;k&lt;/code&gt;. This means I won't be able to use &lt;code&gt;for_&lt;/code&gt; to imitate lua for loops. However, I might be able write a similar combinator that &lt;em&gt;does&lt;/em&gt; short-circuit using &lt;code&gt;foldr&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;For those who are unfamiliar with this behavior of &lt;code&gt;foldr&lt;/code&gt;, let's go over a relatively simple example. We can implement the &lt;a href="https://hackage.haskell.org/package/base-4.20.0.1/docs/Prelude.html#v:take" rel="noopener noreferrer"&gt;&lt;code&gt;take&lt;/code&gt;&lt;/a&gt; function, that takes the first n elements of a list, in terms of &lt;code&gt;foldr&lt;/code&gt; 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;take&lt;/span&gt; &lt;span class="o"&gt;::&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="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;a&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="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="n"&gt;take&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;map&lt;/span&gt; &lt;span class="n"&gt;fst&lt;/span&gt; &lt;span class="o"&gt;$&lt;/span&gt; &lt;span class="n"&gt;foldr&lt;/span&gt; &lt;span class="n"&gt;f&lt;/span&gt;  &lt;span class="kt"&gt;[]&lt;/span&gt; &lt;span class="o"&gt;$&lt;/span&gt; &lt;span class="n"&gt;zip&lt;/span&gt; &lt;span class="n"&gt;l&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="o"&gt;..&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
  &lt;span class="kr"&gt;where&lt;/span&gt;
    &lt;span class="n"&gt;f&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="kt"&gt;Int&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="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="kt"&gt;Int&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="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;)]&lt;/span&gt;
    &lt;span class="n"&gt;f&lt;/span&gt; &lt;span class="n"&gt;tuple&lt;/span&gt;&lt;span class="o"&gt;@&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&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="n"&gt;l&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;n'&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="n"&gt;tuple&lt;/span&gt; &lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;l&lt;/span&gt; &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="kt"&gt;[]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This implementation will stop as soon as the condition in &lt;code&gt;f&lt;/code&gt; is false, which means it can be called on an infinite Haskell list. To see how this happens let's see how &lt;code&gt;take 2 [1,2,3,4]&lt;/code&gt; gets calculated for the following definition of &lt;a href="https://hackage.haskell.org/package/base-4.20.0.1/docs/Prelude.html#v:foldr" rel="noopener noreferrer"&gt;&lt;code&gt;foldr&lt;/code&gt;&lt;/a&gt; (there are many ways to define &lt;code&gt;foldr&lt;/code&gt;, but this one is relatively easy to reason about):&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;foldr&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="p"&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;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;b&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;a&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;
&lt;span class="n"&gt;foldr&lt;/span&gt; &lt;span class="n"&gt;f&lt;/span&gt; &lt;span class="n"&gt;z&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;go&lt;/span&gt;
  &lt;span class="kr"&gt;where&lt;/span&gt;
    &lt;span class="n"&gt;go&lt;/span&gt; &lt;span class="kt"&gt;[]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;z&lt;/span&gt;
    &lt;span class="n"&gt;go&lt;/span&gt; &lt;span class="p"&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;xs&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="p"&gt;`&lt;/span&gt;&lt;span class="n"&gt;f&lt;/span&gt;&lt;span class="p"&gt;`&lt;/span&gt; &lt;span class="n"&gt;go&lt;/span&gt; &lt;span class="n"&gt;xs&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The expression evaluates 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;take&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;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="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="cd"&gt;-- | - apply definition of `take` and `zip`&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;map&lt;/span&gt; &lt;span class="n"&gt;fst&lt;/span&gt; &lt;span class="o"&gt;$&lt;/span&gt; &lt;span class="n"&gt;foldr&lt;/span&gt; &lt;span class="n"&gt;f&lt;/span&gt; &lt;span class="kt"&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;0&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="mi"&gt;1&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="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="mi"&gt;4&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="kr"&gt;where&lt;/span&gt;
    &lt;span class="n"&gt;f&lt;/span&gt; &lt;span class="n"&gt;tuple&lt;/span&gt;&lt;span class="o"&gt;@&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&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="n"&gt;l&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;n'&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="n"&gt;tuple&lt;/span&gt; &lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;l&lt;/span&gt; &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="kt"&gt;[]&lt;/span&gt;
&lt;span class="cd"&gt;-- | - apply definition of `foldr`&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;map&lt;/span&gt; &lt;span class="n"&gt;fst&lt;/span&gt; &lt;span class="o"&gt;$&lt;/span&gt; &lt;span class="n"&gt;go&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;0&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="mi"&gt;1&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="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="mi"&gt;4&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="kr"&gt;where&lt;/span&gt;
    &lt;span class="n"&gt;go&lt;/span&gt; &lt;span class="kt"&gt;[]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kt"&gt;[]&lt;/span&gt;
    &lt;span class="n"&gt;go&lt;/span&gt; &lt;span class="p"&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;xs&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="p"&gt;`&lt;/span&gt;&lt;span class="n"&gt;f&lt;/span&gt;&lt;span class="p"&gt;`&lt;/span&gt; &lt;span class="n"&gt;go&lt;/span&gt; &lt;span class="n"&gt;xs&lt;/span&gt;
    &lt;span class="n"&gt;f&lt;/span&gt; &lt;span class="n"&gt;tuple&lt;/span&gt;&lt;span class="o"&gt;@&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&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="n"&gt;l&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;n'&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="n"&gt;tuple&lt;/span&gt; &lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;l&lt;/span&gt; &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="kt"&gt;[]&lt;/span&gt;
&lt;span class="cd"&gt;-- | - (From this point on I will elide the definitions&lt;/span&gt;
&lt;span class="cd"&gt;-- | - of `f` and `go`, as they don't change).&lt;/span&gt;
&lt;span class="cd"&gt;-- | - first application of `go` to the tuple list&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;map&lt;/span&gt; &lt;span class="n"&gt;fst&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;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;`&lt;/span&gt;&lt;span class="n"&gt;f&lt;/span&gt;&lt;span class="p"&gt;`&lt;/span&gt; &lt;span class="n"&gt;go&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;1&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="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="mi"&gt;4&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="cd"&gt;-- | - apply `f`&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;map&lt;/span&gt; &lt;span class="n"&gt;fst&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;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;go&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;1&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="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="mi"&gt;4&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="cd"&gt;-- | - apply `go`&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;map&lt;/span&gt; &lt;span class="n"&gt;fst&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;0&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="mi"&gt;2&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="p"&gt;`&lt;/span&gt;&lt;span class="n"&gt;f&lt;/span&gt;&lt;span class="p"&gt;`&lt;/span&gt; &lt;span class="n"&gt;go&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="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="mi"&gt;4&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="cd"&gt;-- | - apply `f`&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;map&lt;/span&gt; &lt;span class="n"&gt;fst&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;0&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="mi"&gt;2&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="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;go&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="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="mi"&gt;4&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="cd"&gt;-- | - apply `go`&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;map&lt;/span&gt; &lt;span class="n"&gt;fst&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;0&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="mi"&gt;2&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="o"&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="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="n"&gt;f&lt;/span&gt;&lt;span class="p"&gt;`&lt;/span&gt; &lt;span class="n"&gt;go&lt;/span&gt; &lt;span class="p"&gt;[(&lt;/span&gt;&lt;span class="mi"&gt;4&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="cd"&gt;-- | - apply `f`&lt;/span&gt;
&lt;span class="cd"&gt;-- | - `2 &amp;lt; 2` is false, so `f` returns an empty list&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;map&lt;/span&gt; &lt;span class="n"&gt;fst&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;0&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="mi"&gt;2&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="o"&gt;:&lt;/span&gt; &lt;span class="kt"&gt;[]&lt;/span&gt;
&lt;span class="cd"&gt;-- | - list syntactic sugar&lt;/span&gt;
&lt;span class="c1"&gt;-- v&lt;/span&gt;
&lt;span class="n"&gt;map&lt;/span&gt; &lt;span class="n"&gt;fst&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;0&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="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)]&lt;/span&gt;
&lt;span class="cd"&gt;-- | - apply `map fst`&lt;/span&gt;
&lt;span class="c1"&gt;-- v&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;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As we see in this example, &lt;code&gt;foldr&lt;/code&gt; will only continue computation if the function &lt;code&gt;f&lt;/code&gt; passed to it evaluates its second argument. When we reached the index (the second tuple element) that was not smaller than the argument &lt;code&gt;n&lt;/code&gt;, the function &lt;code&gt;f&lt;/code&gt; did not evaluate its second argument, and instead returned an empty list. This halted computation, because there were no more calls to &lt;code&gt;go&lt;/code&gt; in the expression.&lt;/p&gt;

&lt;p&gt;We can use this property of &lt;code&gt;foldr&lt;/code&gt; to make a &lt;code&gt;for&lt;/code&gt; function that behaves much more like a for loop in Lua. Since we are making our own function, we can take two numbers instead of a list, to be a little closer to the syntax of a Lua &lt;code&gt;for&lt;/code&gt; loop.&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;for&lt;/span&gt; &lt;span class="o"&gt;::&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;Int&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;Int&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&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="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;for&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;action&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;foldr&lt;/span&gt; &lt;span class="n"&gt;action&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&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;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Notice that the action this combinator takes has two arguments, not one as with for_. We can think of this second argument as the rest of the computation that will be computed if we continue processing the list. When I use this new &lt;code&gt;for&lt;/code&gt; combinator, I name this argument &lt;code&gt;continue&lt;/code&gt;. With this naming convention, we can see one interesting difference between the Lua &lt;code&gt;for&lt;/code&gt; loop and my Haskell &lt;code&gt;for&lt;/code&gt; function. In a Lua &lt;code&gt;for&lt;/code&gt; loop we must explicitly &lt;em&gt;end&lt;/em&gt; the loop computation, with the &lt;code&gt;return&lt;/code&gt; or &lt;code&gt;break&lt;/code&gt; keywords, while with my &lt;code&gt;for&lt;/code&gt; function, we must explicitly &lt;em&gt;remain in&lt;/em&gt; the loop by calling the &lt;code&gt;continue&lt;/code&gt; argument in the definition of the &lt;code&gt;action&lt;/code&gt;. With this in mind, here is the new and improved &lt;code&gt;isplaceok&lt;/code&gt; 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;isplaceok&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&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;Int&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;MVar&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;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;isplaceok&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
  &lt;span class="n"&gt;for&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="p"&gt;(&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;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;\&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;continue&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;
      &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&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;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;-&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&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;||&lt;/span&gt;
         &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt;
      &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="n"&gt;putMVar&lt;/span&gt; &lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt;
      &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;continue&lt;/span&gt;
    &lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="kr"&gt;_&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;tryPutMVar&lt;/span&gt; &lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
  &lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Notice that now, in the case that we put &lt;code&gt;False&lt;/code&gt; in the &lt;code&gt;result&lt;/code&gt; MVar, we do not call &lt;code&gt;continue&lt;/code&gt;, meaning the loop computation will end. I decided to use my new &lt;code&gt;for&lt;/code&gt; combinator in &lt;code&gt;addqueen&lt;/code&gt; as well:&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;addqueen&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;MVar&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;IORef&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&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;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;addqueen&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="n"&gt;n&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;n&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;boardSize&lt;/span&gt;
  &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="n"&gt;readIORef&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&amp;gt;=&lt;/span&gt; &lt;span class="n"&gt;printsolution&lt;/span&gt;
  &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;for&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="n"&gt;boardSize&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;\&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="n"&gt;continue&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
           &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;readIORef&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt;
           &lt;span class="n"&gt;isplaceok&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt;
           &lt;span class="n"&gt;placeok&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;takeMVar&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt;
           &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;placeok&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
             &lt;span class="n"&gt;modifyIORef&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="o"&gt;$&lt;/span&gt; &lt;span class="n"&gt;set&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;
             &lt;span class="n"&gt;addqueen&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="p"&gt;(&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;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
           &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
           &lt;span class="n"&gt;continue&lt;/span&gt;
         &lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="kr"&gt;where&lt;/span&gt;
    &lt;span class="n"&gt;set&lt;/span&gt; &lt;span class="o"&gt;::&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;Int&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;Int&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="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
    &lt;span class="n"&gt;set&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;v&lt;/span&gt; &lt;span class="n"&gt;l&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;take&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="n"&gt;l&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="n"&gt;drop&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;l&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This didn't change the behavior of &lt;code&gt;addqueen&lt;/code&gt;, but it felt nice. I left the definition of &lt;code&gt;printsolution&lt;/code&gt; as it was for no particular reason. Here is the final program:&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;module&lt;/span&gt; &lt;span class="nn"&gt;Main&lt;/span&gt; &lt;span class="kr"&gt;where&lt;/span&gt;

&lt;span class="kr"&gt;import&lt;/span&gt; &lt;span class="nn"&gt;Control.Concurrent.MVar&lt;/span&gt;
&lt;span class="kr"&gt;import&lt;/span&gt; &lt;span class="nn"&gt;Data.Bool&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;bool&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="kr"&gt;import&lt;/span&gt; &lt;span class="nn"&gt;Data.Foldable&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;for_&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="kr"&gt;import&lt;/span&gt; &lt;span class="nn"&gt;Data.IORef&lt;/span&gt;

&lt;span class="n"&gt;boardSize&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;Int&lt;/span&gt;
&lt;span class="n"&gt;boardSize&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;8&lt;/span&gt;

&lt;span class="n"&gt;for&lt;/span&gt; &lt;span class="o"&gt;::&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;Int&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;Int&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&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="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;for&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;action&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;foldr&lt;/span&gt; &lt;span class="n"&gt;action&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;i&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;isplaceok&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&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;Int&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;MVar&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;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;isplaceok&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
  &lt;span class="n"&gt;for&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="p"&gt;(&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;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;\&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;continue&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;
      &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&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;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;-&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&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;||&lt;/span&gt;
         &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt;
      &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="n"&gt;putMVar&lt;/span&gt; &lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="kt"&gt;False&lt;/span&gt;
      &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;continue&lt;/span&gt;
    &lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="kr"&gt;_&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;tryPutMVar&lt;/span&gt; &lt;span class="n"&gt;result&lt;/span&gt; &lt;span class="kt"&gt;True&lt;/span&gt;
  &lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;

&lt;span class="n"&gt;printsolution&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;printsolution&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
  &lt;span class="n"&gt;for_&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;..&lt;/span&gt;&lt;span class="n"&gt;boardSize&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;\&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
      &lt;span class="n"&gt;for_&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="o"&gt;..&lt;/span&gt;&lt;span class="n"&gt;boardSize&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;\&lt;/span&gt;&lt;span class="n"&gt;j&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
          &lt;span class="kr"&gt;let&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;bool&lt;/span&gt; &lt;span class="s"&gt;"-"&lt;/span&gt; &lt;span class="s"&gt;"X"&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;!!&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;j&lt;/span&gt;
          &lt;span class="n"&gt;putStr&lt;/span&gt; &lt;span class="o"&gt;$&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="s"&gt;" "&lt;/span&gt;
        &lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="n"&gt;putStr&lt;/span&gt; &lt;span class="s"&gt;"&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt;
    &lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="n"&gt;putStr&lt;/span&gt; &lt;span class="s"&gt;"&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt;

&lt;span class="n"&gt;addqueen&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;MVar&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;IORef&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&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;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;addqueen&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="n"&gt;n&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;n&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;boardSize&lt;/span&gt;
  &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="n"&gt;readIORef&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&amp;gt;=&lt;/span&gt; &lt;span class="n"&gt;printsolution&lt;/span&gt;
  &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;for&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="n"&gt;boardSize&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;\&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="n"&gt;continue&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
           &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;readIORef&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt;
           &lt;span class="n"&gt;isplaceok&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt;
           &lt;span class="n"&gt;placeok&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;takeMVar&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt;
           &lt;span class="kr"&gt;if&lt;/span&gt; &lt;span class="n"&gt;placeok&lt;/span&gt; &lt;span class="kr"&gt;then&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
             &lt;span class="n"&gt;modifyIORef&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="o"&gt;$&lt;/span&gt; &lt;span class="n"&gt;set&lt;/span&gt; &lt;span class="n"&gt;n&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;
             &lt;span class="n"&gt;addqueen&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="p"&gt;(&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;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
           &lt;span class="kr"&gt;else&lt;/span&gt; &lt;span class="n"&gt;pure&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
           &lt;span class="n"&gt;continue&lt;/span&gt;
         &lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="kr"&gt;where&lt;/span&gt;
    &lt;span class="n"&gt;set&lt;/span&gt; &lt;span class="o"&gt;::&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;Int&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;Int&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="kt"&gt;Int&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
    &lt;span class="n"&gt;set&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;v&lt;/span&gt; &lt;span class="n"&gt;l&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;take&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&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="n"&gt;l&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="n"&gt;drop&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="n"&gt;l&lt;/span&gt;

&lt;span class="n"&gt;main&lt;/span&gt; &lt;span class="o"&gt;::&lt;/span&gt; &lt;span class="kt"&gt;IO&lt;/span&gt; &lt;span class="nb"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;main&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="kr"&gt;do&lt;/span&gt;
  &lt;span class="n"&gt;placeokVar&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;newEmptyMVar&lt;/span&gt;
  &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;newIORef&lt;/span&gt; &lt;span class="kt"&gt;[]&lt;/span&gt;
  &lt;span class="n"&gt;addqueen&lt;/span&gt; &lt;span class="n"&gt;placeokVar&lt;/span&gt; &lt;span class="n"&gt;aRef&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With the critical modification in &lt;code&gt;isplaceok&lt;/code&gt; implemented, my Haskell translation finally gave the same output as the Lua program from the book:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;gt; runhaskell haskell/eight-queen-from-text-clone.hs
X - - - - - - -
- - - - X - - -
- - - - - - - X
- - - - - X - -
- - X - - - - -
- - - - - - X -
- X - - - - - -
- - - X - - - -

X - - - - - - -
- - - - - X - -
- - - - - - - X
- - X - - - - -
- - - - - - X -
- - - X - - - -
- X - - - - - -
- - - - X - - -

X - - - - - - -
- - - - - - X -
- - - X - - - -
- - - - - X - -
- - - - - - - X
- X - - - - - -
- - - - X - - -
- - X - - - - -

X - - - - - - -
- - - - - - X -
- - - - X - - -
- - - - - - - X
- X - - - - - -
- - - X - - - -
- - - - - X - -
- - X - - - - -

- X - - - - - -
- - - X - - - -
- - - - - X - -
- - - - - - - X
- - X - - - - -
X - - - - - - -
- - - - - - X -
- - - - X - - -

- X - - - - - -
- - - - X - - -
- - - - - - X -
X - - - - - - -
- - X - - - - -
- - - - - - - X
- - - - - X - -
- - - X - - - -

- X - - - - - -
- - - - X - - -
- - - - - - X -
- - - X - - - -
X - - - - - - -
- - - - - - - X
- - - - - X - -
- - X - - - - -

- X - - - - - -
- - - - - X - -
X - - - - - - -
- - - - - - X -
- - - X - - - -
- - - - - - - X
- - X - - - - -
- - - - X - - -

- X - - - - - -
- - - - - X - -
- - - - - - - X
- - X - - - - -
X - - - - - - -
- - - X - - - -
- - - - - - X -
- - - - X - - -

- X - - - - - -
- - - - - - X -
- - X - - - - -
- - - - - X - -
- - - - - - - X
- - - - X - - -
X - - - - - - -
- - - X - - - -

- X - - - - - -
- - - - - - X -
- - - - X - - -
- - - - - - - X
X - - - - - - -
- - - X - - - -
- - - - - X - -
- - X - - - - -

- X - - - - - -
- - - - - - - X
- - - - - X - -
X - - - - - - -
- - X - - - - -
- - - - X - - -
- - - - - - X -
- - - X - - - -

- - X - - - - -
X - - - - - - -
- - - - - - X -
- - - - X - - -
- - - - - - - X
- X - - - - - -
- - - X - - - -
- - - - - X - -

- - X - - - - -
- - - - X - - -
- X - - - - - -
- - - - - - - X
X - - - - - - -
- - - - - - X -
- - - X - - - -
- - - - - X - -

- - X - - - - -
- - - - X - - -
- X - - - - - -
- - - - - - - X
- - - - - X - -
- - - X - - - -
- - - - - - X -
X - - - - - - -

- - X - - - - -
- - - - X - - -
- - - - - - X -
X - - - - - - -
- - - X - - - -
- X - - - - - -
- - - - - - - X
- - - - - X - -

- - X - - - - -
- - - - X - - -
- - - - - - - X
- - - X - - - -
X - - - - - - -
- - - - - - X -
- X - - - - - -
- - - - - X - -

- - X - - - - -
- - - - - X - -
- X - - - - - -
- - - - X - - -
- - - - - - - X
X - - - - - - -
- - - - - - X -
- - - X - - - -

- - X - - - - -
- - - - - X - -
- X - - - - - -
- - - - - - X -
X - - - - - - -
- - - X - - - -
- - - - - - - X
- - - - X - - -

- - X - - - - -
- - - - - X - -
- X - - - - - -
- - - - - - X -
- - - - X - - -
X - - - - - - -
- - - - - - - X
- - - X - - - -

- - X - - - - -
- - - - - X - -
- - - X - - - -
X - - - - - - -
- - - - - - - X
- - - - X - - -
- - - - - - X -
- X - - - - - -

- - X - - - - -
- - - - - X - -
- - - X - - - -
- X - - - - - -
- - - - - - - X
- - - - X - - -
- - - - - - X -
X - - - - - - -

- - X - - - - -
- - - - - X - -
- - - - - - - X
X - - - - - - -
- - - X - - - -
- - - - - - X -
- - - - X - - -
- X - - - - - -

- - X - - - - -
- - - - - X - -
- - - - - - - X
X - - - - - - -
- - - - X - - -
- - - - - - X -
- X - - - - - -
- - - X - - - -

- - X - - - - -
- - - - - X - -
- - - - - - - X
- X - - - - - -
- - - X - - - -
X - - - - - - -
- - - - - - X -
- - - - X - - -

- - X - - - - -
- - - - - - X -
- X - - - - - -
- - - - - - - X
- - - - X - - -
X - - - - - - -
- - - X - - - -
- - - - - X - -

- - X - - - - -
- - - - - - X -
- X - - - - - -
- - - - - - - X
- - - - - X - -
- - - X - - - -
X - - - - - - -
- - - - X - - -

- - X - - - - -
- - - - - - - X
- - - X - - - -
- - - - - - X -
X - - - - - - -
- - - - - X - -
- X - - - - - -
- - - - X - - -

- - - X - - - -
X - - - - - - -
- - - - X - - -
- - - - - - - X
- X - - - - - -
- - - - - - X -
- - X - - - - -
- - - - - X - -

- - - X - - - -
X - - - - - - -
- - - - X - - -
- - - - - - - X
- - - - - X - -
- - X - - - - -
- - - - - - X -
- X - - - - - -

- - - X - - - -
- X - - - - - -
- - - - X - - -
- - - - - - - X
- - - - - X - -
X - - - - - - -
- - X - - - - -
- - - - - - X -

- - - X - - - -
- X - - - - - -
- - - - - - X -
- - X - - - - -
- - - - - X - -
- - - - - - - X
X - - - - - - -
- - - - X - - -

- - - X - - - -
- X - - - - - -
- - - - - - X -
- - X - - - - -
- - - - - X - -
- - - - - - - X
- - - - X - - -
X - - - - - - -

- - - X - - - -
- X - - - - - -
- - - - - - X -
- - - - X - - -
X - - - - - - -
- - - - - - - X
- - - - - X - -
- - X - - - - -

- - - X - - - -
- X - - - - - -
- - - - - - - X
- - - - X - - -
- - - - - - X -
X - - - - - - -
- - X - - - - -
- - - - - X - -

- - - X - - - -
- X - - - - - -
- - - - - - - X
- - - - - X - -
X - - - - - - -
- - X - - - - -
- - - - X - - -
- - - - - - X -

- - - X - - - -
- - - - - X - -
X - - - - - - -
- - - - X - - -
- X - - - - - -
- - - - - - - X
- - X - - - - -
- - - - - - X -

- - - X - - - -
- - - - - X - -
- - - - - - - X
- X - - - - - -
- - - - - - X -
X - - - - - - -
- - X - - - - -
- - - - X - - -

- - - X - - - -
- - - - - X - -
- - - - - - - X
- - X - - - - -
X - - - - - - -
- - - - - - X -
- - - - X - - -
- X - - - - - -

- - - X - - - -
- - - - - - X -
X - - - - - - -
- - - - - - - X
- - - - X - - -
- X - - - - - -
- - - - - X - -
- - X - - - - -

- - - X - - - -
- - - - - - X -
- - X - - - - -
- - - - - - - X
- X - - - - - -
- - - - X - - -
X - - - - - - -
- - - - - X - -

- - - X - - - -
- - - - - - X -
- - - - X - - -
- X - - - - - -
- - - - - X - -
X - - - - - - -
- - X - - - - -
- - - - - - - X

- - - X - - - -
- - - - - - X -
- - - - X - - -
- - X - - - - -
X - - - - - - -
- - - - - X - -
- - - - - - - X
- X - - - - - -

- - - X - - - -
- - - - - - - X
X - - - - - - -
- - X - - - - -
- - - - - X - -
- X - - - - - -
- - - - - - X -
- - - - X - - -

- - - X - - - -
- - - - - - - X
X - - - - - - -
- - - - X - - -
- - - - - - X -
- X - - - - - -
- - - - - X - -
- - X - - - - -

- - - X - - - -
- - - - - - - X
- - - - X - - -
- - X - - - - -
X - - - - - - -
- - - - - - X -
- X - - - - - -
- - - - - X - -

- - - - X - - -
X - - - - - - -
- - - X - - - -
- - - - - X - -
- - - - - - - X
- X - - - - - -
- - - - - - X -
- - X - - - - -

- - - - X - - -
X - - - - - - -
- - - - - - - X
- - - X - - - -
- X - - - - - -
- - - - - - X -
- - X - - - - -
- - - - - X - -

- - - - X - - -
X - - - - - - -
- - - - - - - X
- - - - - X - -
- - X - - - - -
- - - - - - X -
- X - - - - - -
- - - X - - - -

- - - - X - - -
- X - - - - - -
- - - X - - - -
- - - - - X - -
- - - - - - - X
- - X - - - - -
X - - - - - - -
- - - - - - X -

- - - - X - - -
- X - - - - - -
- - - X - - - -
- - - - - - X -
- - X - - - - -
- - - - - - - X
- - - - - X - -
X - - - - - - -

- - - - X - - -
- X - - - - - -
- - - - - X - -
X - - - - - - -
- - - - - - X -
- - - X - - - -
- - - - - - - X
- - X - - - - -

- - - - X - - -
- X - - - - - -
- - - - - - - X
X - - - - - - -
- - - X - - - -
- - - - - - X -
- - X - - - - -
- - - - - X - -

- - - - X - - -
- - X - - - - -
X - - - - - - -
- - - - - X - -
- - - - - - - X
- X - - - - - -
- - - X - - - -
- - - - - - X -

- - - - X - - -
- - X - - - - -
X - - - - - - -
- - - - - - X -
- X - - - - - -
- - - - - - - X
- - - - - X - -
- - - X - - - -

- - - - X - - -
- - X - - - - -
- - - - - - - X
- - - X - - - -
- - - - - - X -
X - - - - - - -
- - - - - X - -
- X - - - - - -

- - - - X - - -
- - - - - - X -
X - - - - - - -
- - X - - - - -
- - - - - - - X
- - - - - X - -
- - - X - - - -
- X - - - - - -

- - - - X - - -
- - - - - - X -
X - - - - - - -
- - - X - - - -
- X - - - - - -
- - - - - - - X
- - - - - X - -
- - X - - - - -

- - - - X - - -
- - - - - - X -
- X - - - - - -
- - - X - - - -
- - - - - - - X
X - - - - - - -
- - X - - - - -
- - - - - X - -

- - - - X - - -
- - - - - - X -
- X - - - - - -
- - - - - X - -
- - X - - - - -
X - - - - - - -
- - - X - - - -
- - - - - - - X

- - - - X - - -
- - - - - - X -
- X - - - - - -
- - - - - X - -
- - X - - - - -
X - - - - - - -
- - - - - - - X
- - - X - - - -

- - - - X - - -
- - - - - - X -
- - - X - - - -
X - - - - - - -
- - X - - - - -
- - - - - - - X
- - - - - X - -
- X - - - - - -

- - - - X - - -
- - - - - - - X
- - - X - - - -
X - - - - - - -
- - X - - - - -
- - - - - X - -
- X - - - - - -
- - - - - - X -

- - - - X - - -
- - - - - - - X
- - - X - - - -
X - - - - - - -
- - - - - - X -
- X - - - - - -
- - - - - X - -
- - X - - - - -

- - - - - X - -
X - - - - - - -
- - - - X - - -
- X - - - - - -
- - - - - - - X
- - X - - - - -
- - - - - - X -
- - - X - - - -

- - - - - X - -
- X - - - - - -
- - - - - - X -
X - - - - - - -
- - X - - - - -
- - - - X - - -
- - - - - - - X
- - - X - - - -

- - - - - X - -
- X - - - - - -
- - - - - - X -
X - - - - - - -
- - - X - - - -
- - - - - - - X
- - - - X - - -
- - X - - - - -

- - - - - X - -
- - X - - - - -
X - - - - - - -
- - - - - - X -
- - - - X - - -
- - - - - - - X
- X - - - - - -
- - - X - - - -

- - - - - X - -
- - X - - - - -
X - - - - - - -
- - - - - - - X
- - - X - - - -
- X - - - - - -
- - - - - - X -
- - - - X - - -

- - - - - X - -
- - X - - - - -
X - - - - - - -
- - - - - - - X
- - - - X - - -
- X - - - - - -
- - - X - - - -
- - - - - - X -

- - - - - X - -
- - X - - - - -
- - - - X - - -
- - - - - - X -
X - - - - - - -
- - - X - - - -
- X - - - - - -
- - - - - - - X

- - - - - X - -
- - X - - - - -
- - - - X - - -
- - - - - - - X
X - - - - - - -
- - - X - - - -
- X - - - - - -
- - - - - - X -

- - - - - X - -
- - X - - - - -
- - - - - - X -
- X - - - - - -
- - - X - - - -
- - - - - - - X
X - - - - - - -
- - - - X - - -

- - - - - X - -
- - X - - - - -
- - - - - - X -
- X - - - - - -
- - - - - - - X
- - - - X - - -
X - - - - - - -
- - - X - - - -

- - - - - X - -
- - X - - - - -
- - - - - - X -
- - - X - - - -
X - - - - - - -
- - - - - - - X
- X - - - - - -
- - - - X - - -

- - - - - X - -
- - - X - - - -
X - - - - - - -
- - - - X - - -
- - - - - - - X
- X - - - - - -
- - - - - - X -
- - X - - - - -

- - - - - X - -
- - - X - - - -
- X - - - - - -
- - - - - - - X
- - - - X - - -
- - - - - - X -
X - - - - - - -
- - X - - - - -

- - - - - X - -
- - - X - - - -
- - - - - - X -
X - - - - - - -
- - X - - - - -
- - - - X - - -
- X - - - - - -
- - - - - - - X

- - - - - X - -
- - - X - - - -
- - - - - - X -
X - - - - - - -
- - - - - - - X
- X - - - - - -
- - - - X - - -
- - X - - - - -

- - - - - X - -
- - - - - - - X
- X - - - - - -
- - - X - - - -
X - - - - - - -
- - - - - - X -
- - - - X - - -
- - X - - - - -

- - - - - - X -
X - - - - - - -
- - X - - - - -
- - - - - - - X
- - - - - X - -
- - - X - - - -
- X - - - - - -
- - - - X - - -

- - - - - - X -
- X - - - - - -
- - - X - - - -
X - - - - - - -
- - - - - - - X
- - - - X - - -
- - X - - - - -
- - - - - X - -

- - - - - - X -
- X - - - - - -
- - - - - X - -
- - X - - - - -
X - - - - - - -
- - - X - - - -
- - - - - - - X
- - - - X - - -

- - - - - - X -
- - X - - - - -
X - - - - - - -
- - - - - X - -
- - - - - - - X
- - - - X - - -
- X - - - - - -
- - - X - - - -

- - - - - - X -
- - X - - - - -
- - - - - - - X
- X - - - - - -
- - - - X - - -
X - - - - - - -
- - - - - X - -
- - - X - - - -

- - - - - - X -
- - - X - - - -
- X - - - - - -
- - - - X - - -
- - - - - - - X
X - - - - - - -
- - X - - - - -
- - - - - X - -

- - - - - - X -
- - - X - - - -
- X - - - - - -
- - - - - - - X
- - - - - X - -
X - - - - - - -
- - X - - - - -
- - - - X - - -

- - - - - - X -
- - - - X - - -
- - X - - - - -
X - - - - - - -
- - - - - X - -
- - - - - - - X
- X - - - - - -
- - - X - - - -

- - - - - - - X
- X - - - - - -
- - - X - - - -
X - - - - - - -
- - - - - - X -
- - - - X - - -
- - X - - - - -
- - - - - X - -

- - - - - - - X
- X - - - - - -
- - - - X - - -
- - X - - - - -
X - - - - - - -
- - - - - - X -
- - - X - - - -
- - - - - X - -

- - - - - - - X
- - X - - - - -
X - - - - - - -
- - - - - X - -
- X - - - - - -
- - - - X - - -
- - - - - - X -
- - - X - - - -

- - - - - - - X
- - - X - - - -
X - - - - - - -
- - X - - - - -
- - - - - X - -
- X - - - - - -
- - - - - - X -
- - - - X - - -
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;What have I learned from this experience? That with a few terrible decisions and using the parts of Haskell we usually try to avoid at all cost, it is possible to get pretty close to the style of a basic Lua program. Maybe a little too close for comfort.&lt;/p&gt;

</description>
      <category>haskell</category>
      <category>lua</category>
    </item>
  </channel>
</rss>
