Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/364.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
JavaScript中的函数式编程风格模式匹配_Javascript_Algorithm_Functional Programming_Compiler Construction_Pattern Matching - Fatal编程技术网

JavaScript中的函数式编程风格模式匹配

JavaScript中的函数式编程风格模式匹配,javascript,algorithm,functional-programming,compiler-construction,pattern-matching,Javascript,Algorithm,Functional Programming,Compiler Construction,Pattern Matching,我正在编写从函数式语言到JS的编译器。编译器将在浏览器中运行。我需要在JS中实现模式匹配机制,因为原始语言有一个。我已经找到并找到了。据我所知,Sparkler不能在浏览器中执行,Z也没有我需要的所有可能性 所以我的语言有如下语义: count x [] <- 0 count x [ x : xs ] <- 1 + count x xs count x [ y : xs ] <- count x xs const count = (x, list) =>

我正在编写从函数式语言到JS的编译器。编译器将在浏览器中运行。我需要在JS中实现模式匹配机制,因为原始语言有一个。我已经找到并找到了。据我所知,Sparkler不能在浏览器中执行,Z也没有我需要的所有可能性

所以我的语言有如下语义:

count x []         <- 0
count x [ x : xs ] <- 1 + count x xs
count x [ y : xs ] <- count x xs
const count = (x, list) => {
    match(x, list) => (
        (x, []) => {...}
        (x, [ x : xs ]) => {...}
        (x, [ y : xs ]) => {...}
    )
} 
如何正确地将这种模式匹配展开为
ifs
ors

一般情况 这是一个很好的例子,但截至2018年,它还处于非常早期的阶段

目前,“实施”部分仅列出:

  • (注意:这不是基于提案,本提案部分基于提案!)
列表案例 使用,例如:


使用
ex模式
,您可以编写如下示例。您需要使用软件包随附的占位符名称(
\uuu
A
B
C
,…
Z
),但您可以在回调函数中通过解构重命名匹配的变量(包含所有命名匹配项的对象作为回调函数的第一个参数传入)

import{when,then,Y,u,tail,end}来自'ex patterns';
常数计数=列表=>(
时间(列表)
([],然后(()=>0))//匹配空数组
([\uz],然后(()=>1))//将数组与(任意)1个元素匹配
([\ux,tail(Y)],然后({Y:xs})=>1+计数(xs))//匹配数组并捕获tail
(完);
);
这也涵盖了
list=[undefined,'foo','bar']
的情况,我认为公认的答案不会涵盖这一点

为了提高代码的效率,您可以使用Immutable.js
列表而不是数组调用
count
(无需更改)。在这种情况下,数组的
尾部
部分不需要在每个循环上被切片并复制到新数组中

正如您提到的软件包一样,这并不是在浏览器中本机运行的,但我想这并不是现代捆绑工具的主要障碍

以下是文件:


免责声明:我是
ex patterns
:)

的作者,我需要进行模式匹配,并制作了一些适合我的东西

下面是数组上的
toPairs([…])
函数匹配

const{patron,}=require('patron');
const-toPairs=patron(
[u,[u],([a,b,[c],p=[])=>toPairs(c,[…p,[a,b]]),
_,(,p=[])=>p,
)


poc;考虑在npm上发布。

您只支持某些内置类型或通用代数数据类型上的模式匹配吗?您支持什么类型的模式?例如,您是否支持用户定义的模式(如Scala中的提取器或F#中的活动模式)?
[x:xs]
是链表(可以表示为ADT)还是数组(可能表示为JavaScript数组)?如果您支持ADT,您是否已经知道如何表示它们?链表表示为JS数组。对于内置类型和列表分解,我只需要支持单个值。也不支持代数数据类型。如何将链表表示为数组?你是说一个两元素的数组,其中一个元素是头,另一个元素是尾?还是一个对象数组,其中每个对象都包含一个值及其尾部在数组中的索引?或者你的意思是“列表就是数组”是打字错误?无论如何,若只是常量、变量、元组、数组和/或列表,元组模式可以转换为元素的赋值,常量模式切换为
,列表/数组模式切换为
es,列表/数组模式切换为
if
s,检查列表的大小,然后分配元素。您提到的repo尝试在Javascript中实现模式匹配,这是不可能的,因为真正的模式匹配不依赖于相等,而是依赖于结构。您也不能利用分解分配,因为它具有不同的语义。例如,当出现不匹配时,它会抛出一个错误。@sepp2k是否有关于您提出的方法的文章或内容?我想了解更多细节
const count = list => {
  const [x, ...xs] = list;
  if (x === undefined) {
    return 0;
  } else if (xs === undefined) {
    return 1;
  } else {
    return 1 + count(xs);
  }
}