在Haskell中构建无功计算器

2020-06-18 17:47:22

在本实践教程中,我们将在Haskell中构建一个反应式计算器应用程序。我们将要编写的代码将使用GHCJS在您的浏览器上运行,但是如果您愿意,您可以很容易地将其更改为在桌面上运行:所有GUI代码将恰好位于一个模块中,只有50多行代码。

在构建应用程序时,一个常见的问题是使用哪个框架。对于几乎没有动画的反应型应用,我们推荐Keera Hails:它非常简单,本机跨平台,易于扩展,并且已经在许多项目中使用,包括商业项目和开源项目(图1)。

Keera Hailes背后的关键思想是反应性价值和关系。反应值只是一个可以在应用程序执行过程中更改的值。该术语与FRP中的分段信号或事件流的术语没有太大不同,但反应值是基于推送的、离散的、异步的,并且可以连接到多个其他房车。您可以在本文和我们的公共GitHub回购中找到更多详细信息。

Keera Hail应用程序通常由三个部分构成:视图、模型和一组反应性规则。视图和模型将发布反应值。反应性规则将反应性值连接起来,确保当其他部分更改时,每个部分都会更新。

Hails的语法和API被选择为非常易于使用。如果x是包含文本框中的字符串的反应值,而y是表示应用程序模型中的用户名的反应值,则规则x=:=y将在程序的其余执行过程中使两者保持同步。

我们发布这篇文章的目的是让入门变得非常简单,所以我们要直截了当地寻找解决方案。如果您遵循本教程中的步骤,最后您将在浏览器中运行一个运行计算器的Web应用程序(图2)。

您首先需要的是一个有效的设置。您需要GHCJS的工作版本,在Linux上,您可以使用HVR的PPA安装一个。您还需要一个最新版本的阴谋(至少2.4)。通过将GHCJS添加到PATH环境变量(调整它以引用您拥有的GHCJS版本),确保GHCJS位于您的PATH中:

为了保持所有内容的隔离,我们将把所有内容安装在沙箱中。使用哪种CACAL/堆栈变体以及使用哪种安装方法的问题超出了本文的范围。您可以自由调整该示例以使用v2或新的CABAL接口、堆栈或任何其他工具。

接下来,我们将为我们的示例创建一个简单的阴谋文件。这只会使跟踪我们所需的选项和依赖项变得容易得多。将以下文本复制到文件keera-hails-example.Cabal中:

您当然可以使用不同的许可证。请确保为许可证创建一个名称为License的文件,该文件在安装过程中是必需的。

最后,为代码创建一个目录src/(命令为mkdir src/),并在文件src/Main.hs中编写以下代码:

如果一切顺利,您应该能够在浏览器中编译并查看此应用程序(图3):

xdg-open是一个Linux工具,它将使用默认应用程序打开文件,但是您可以使用任何浏览器并导航到该路径。不要关闭显示我们创建的新页面的浏览器选项卡:我们将重新安装我们的应用程序并刷新页面以查看更改。

在我们继续创建实际的应用程序之前,让我们先构建一个基本的示例,以了解如何使用反应性值和关系来与Web元素交互。为此,我们将创建一个Web,其中包含两个相互连接的反应性输入文本框。将Main.hs文件修改为如下所示:

此代码创建两个HTML输入文本框,将它们添加到HTML页面的正文中,并在第一个传递的文本发生更改时将其传递给第二个传递。函数Hails.MVC.View.HTML.inputTextReactive创建投影输入文本框文本的反应值。

如果您编译这个新版本的Main.hs(使用Cabal install-ghcjs)并在浏览器中刷新页面,您现在应该会看到两个并排的文本框。在第一个框中写入文本会自动将其传播到第二个框(图4)。

还有一个替代的关系构建函数(=:=),它可以双向连接两个房车。请尝试改用它,并查看它对文本框行为的影响。

创建并添加第三个文本框input3,并使用另一个规则input2=:>;input3将其连接到input2。现在看看效果如何。

在刚才介绍的最后一个规则中,使用组合符(<;^>;)将字符串->;字符串函数(例如,Reverse)应用到input2。

不能将函数REVERSE应用于(=:>;)右侧的input3,或应用于使用(=:=)的双向规则中的RV。你能想出为什么吗?看看Hails库中的liftW和liftRW,看看是否可以使其工作。

在本系列的下一篇文章中,我们将了解如何为计算器应用程序构建一个漂亮的视图,如何使视图元素具有反应性,以及如何将它们连接到线程安全的反应性模型来实现反应性应用程序。您可以在这里继续阅读本系列的下一篇文章。

多年来,我们公司一直在哈斯克尔开发移动应用和游戏方面处于领先地位。为了帮助支持我们的使命,请购买我们的iOS或Android Haskell游戏,并尽可能多地向人们介绍我们。它们的价格还不到一杯咖啡,所以我们每个月需要数千次销售,才能维持灯火通明。如果您不能这样做,请考虑帮助维护我们的一些开源代码,以及其他Haskell项目的代码。人们帮助我们推广、改进和维护我们的应用程序和代码的次数越多,我们就越有能力以开源的方式发布和回馈。