Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/sorting/2.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

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/haskell/9.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
Sorting Haskell简单初学者排序程序_Sorting_Haskell - Fatal编程技术网

Sorting Haskell简单初学者排序程序

Sorting Haskell简单初学者排序程序,sorting,haskell,Sorting,Haskell,哈斯克尔还是个新手。我正在尝试使用递归编写排序函数,到目前为止,我已经做到了: sort' :: [Int] -> [Int] sort' [] = [] sort' [x] = [x] sort' (x:y:xs) = if x > y then y:sort' (x:xs) else x:sort' (y:xs) 据我所知,当要排序的元素少于2个时,它可以正常工作。但是如果我输入[3,2,1],我得到[2,1,3]。我已经尝试手动跟踪输入的路径,但我不知道

哈斯克尔还是个新手。我正在尝试使用递归编写排序函数,到目前为止,我已经做到了:

sort' :: [Int] -> [Int]
sort' [] = []
sort' [x] = [x]
sort' (x:y:xs) = 
  if x > y
    then y:sort' (x:xs)
    else x:sort' (y:xs)

据我所知,当要排序的元素少于2个时,它可以正常工作。但是如果我输入[3,2,1],我得到[2,1,3]。我已经尝试手动跟踪输入的路径,但我不知道如何对2个以上的初始元素进行排序。我读了一些书,并且考虑了一些涉及到迭代和使用列表长度(
length
)的事情,但是我不确定如果它真的起作用,如何实现它。

你的
排序'
实现了冒泡排序的迭代,因此,反复应用它将得到一个完全排序的列表。有,一个是使用
迭代
重复应用它,然后使用
选择第N个应用程序

completeSort list = iterate sort' list !! length list

您的
sort'
实现了冒泡排序的迭代,因此反复应用它将产生一个完全排序的列表。有,一个是使用
迭代
重复应用它,然后使用
选择第N个应用程序

completeSort list = iterate sort' list !! length list

正如@另一个家伙指出的,您可以使用
iterate
sort'
应用于列表
n
次,这是在Haskell中使用高级组合符的一个很好的例子(与原始递归相反)。另一个对这类事情有用的很好的组合词是
until
until
将接受谓词
::a->Bool
、函数
::a->a
、值
::a
,并将函数应用于该值,直到谓词保持为真。因此,当您遇到类似的情况,但不知道要对输入进行多少次传递时,可以执行类似于
的操作,直到IsOrted sort'xs
,这非常好

Haskell中还有很多其他单次排序算法,包括自顶向下和(尤其是)自底向上的合并排序

冒着让你陷入理论深渊的风险,我想提到另一种非常好的高级组合思维方式,即迭代
n次。这是基于“递归模式”的思想,其基本思想是递归数据类型的结构通知处理/转换它的有用模式。恰巧,哈斯克尔的能力足以表达这些想法。递归方案的最简单示例之一是基于自然数:

data Nat = Zero | Succ Nat
这是一种递归数据类型,因为第二个数据构造函数引用回
Nat
本身。有一种处理
Nat
s的非常自然的方法,也就是说:当我有
Zero
时,我应该返回一些值;否则,我应该递归地处理
Nat
,然后使用这些值生成一个新值。事实上,我们可以用不同的方式编写
Nat
,这使得一般来说非常容易做到:

data NatF a = Zero | Succ a
type Nat = Mu NatF
现在,
NatF
数据类型可以在其“递归”组件中保存任何类型的值,而不仅仅是另一个
Nat
。第二行中的
Mu
类型构造函数基本上类似于
fix
函数,但对于类型:它实例化
NatF(NatF(NatF(NatF…))
,因此
Nat=NatF-Nat
,这与我们之前的定义相同

但是,由于泛型的增加,我们现在可以写下描述处理
Nat
s的函数的类型:
natfa->a
。当给定一个
0
时,这种类型的函数只返回一些
a
;当给定一个
Succ
时,它可以访问它在“内部”
Nat
上递归调用时返回的
a
。事实证明,可以对实现这一点所需的基础设施进行泛化,这样它就可以处理以上述样式编写的任何类型(即,作为递归组件上泛化的类型的固定点)。这意味着您可以在给定递归调用结果的情况下,为函数写下方程式,然后在此数据结构上调用
cata
,而不必费心写下重复的无聊递归调用

这还意味着将“应用排序”(长度xs)时间写入xs`的另一种方法是:

sort xs = cata phi (toNat $ length xs)
  where phi Zero = xs
        phi (Succ xs) = sort' xs

正如@另一个家伙指出的,您可以使用
iterate
sort'
应用于列表
n
次,这是在Haskell中使用高级组合符的一个很好的例子(与原始递归相反)另一个对这类事情有用的很好的组合词是
直到
直到
将接受一个谓词
::a->Bool
,一个函数
::a->a
,一个值
::a
,并将函数应用于该值,直到谓词保持为真。因此,当您遇到类似情况但不知道e时确切地说,您希望对输入进行多少次传递,您可以执行类似于
的操作,直到isSorted sort'xs
,这非常好

Haskell中还有很多其他单次排序算法,包括自顶向下和(尤其是)自底向上的合并排序

冒着让你陷入理论深渊的风险,我想提到另一种关于迭代
n
次的非常好的高级组合思维方式。这是基于“递归方案”的思想,其基本思想是递归数据类型的结构通知处理/转换它的有用模式。恰巧,哈斯克尔的能力足以表达这些想法。递归方案的最简单示例之一是基于自然数:

data Nat = Zero | Succ Nat
这是一种递归数据类型,因为第二个数据构造函数引用回
Nat
本身。有一种非常自然的方式