在SML中反转字符串的想法

在SML中反转字符串的想法,sml,smlnj,Sml,Smlnj,我是SML的新手,对C/C++有一定的背景。我一直在尝试编写一个名为reverseString的函数,它接收要反转的字符串。很简单。通过使用一个辅助函数,我可以编写一个函数来反转任何给定的字符串,并在结果中添加一个额外的字符。例如: - reverseString("hello"); val it = "ollehh" : string 任何关于如何克服这一障碍的帮助都将非常有用。请记住,我正在尝试在没有任何附加功能的情况下实现该功能,即在我的中断实现中未使用的功能: fun reverseA

我是SML的新手,对C/C++有一定的背景。我一直在尝试编写一个名为reverseString的函数,它接收要反转的字符串。很简单。通过使用一个辅助函数,我可以编写一个函数来反转任何给定的字符串,并在结果中添加一个额外的字符。例如:

- reverseString("hello");
val it = "ollehh" : string
任何关于如何克服这一障碍的帮助都将非常有用。请记住,我正在尝试在没有任何附加功能的情况下实现该功能,即在我的中断实现中未使用的功能:

fun reverseAux(s:string, i:int) : string = 
    if i = 0 then str(String.sub(s, 0)) 
    else str(String.sub(s, i-1)) ^ reverseAux(s, i-1);

fun reverseString(s:string) : string = 
    reverseAux(s, size(s));

除了我的评论之外,一旦您了解了模式匹配,这是一个更简单的解决方案:

fun helper [] = []
| helper [x] = [x]
| helper (l::ls) = (helper ls) @ [l];

fun reverse s = implode (helper (explode s));

分解和内爆是分别将字符串转换为字符列表的函数,反之亦然。列表比字符串更容易遍历。

除了我的注释之外,一旦您了解了模式匹配,这是一个更容易的解决方案:

fun helper [] = []
| helper [x] = [x]
| helper (l::ls) = (helper ls) @ [l];

fun reverse s = implode (helper (explode s));
分解和内爆是分别将字符串转换为字符列表的函数,反之亦然。列表比字符串更容易遍历。

您可以先分解,然后折叠,然后内爆:

你可以先爆炸,然后折叠,然后内爆:


值得接受的公认答案解释了你如何从头开始做这件事——这在你刚开始的时候是一个很好的想法,但它涉及到@这是一个有点昂贵的操作。请参阅关于看似线性的算法如何在引擎盖下是二次的极好讨论。有一种方法可以避免它,不过如果你感兴趣的话,解释它有点复杂。相反,内置函数rev已经实现了有效的列表反转。使用它,再加上内置合成运算符o,可以在一行中创建反向限制:

val reverseString = implode o rev o explode;

请注意,我使用val而不是fun。Composition是一个返回其他函数的高阶函数,我使用Composition直接创建我想要的函数,而不是从头定义它。函数式编程的主要优点之一是能够将大量代码打包到一行代码中。在这种情况下,它使用的构图是一个链式操作符,从右向左读取。它说,要反转一根弦,你应该首先将它分解成一个列表,然后反转升力,然后再将它内爆成一根弦。

值得接受的公认答案解释了你如何从头开始做这件事,这是一个很好的想法,但是它涉及到@,这是一个有点昂贵的操作,请参阅关于看似线性的算法如何在引擎盖下是二次的极好讨论。有一种方法可以避免它,不过如果你感兴趣的话,解释它有点复杂。相反,内置函数rev已经实现了有效的列表反转。使用它,再加上内置合成运算符o,可以在一行中创建反向限制:

val reverseString = implode o rev o explode;

请注意,我使用val而不是fun。Composition是一个返回其他函数的高阶函数,我使用Composition直接创建我想要的函数,而不是从头定义它。函数式编程的主要优点之一是能够将大量代码打包到一行代码中。在这种情况下,它使用的构图是一个链式操作符,从右向左读取。它说,要反转字符串,首先应将其分解为列表,然后反转升力,然后将其内爆回字符串。

实现所需功能的最简单修改是将i=0更改为i=1,或将大小更改为size-1String.subs,结果中出现两次0,虽然有一次它伪装成了String.subs,但当我1岁的时候,我是1岁。谢谢,凯文和莫尔布尼洛。这就是我要找的。使用递归反转字符串让我非常困惑…实现您所寻求的功能的最简单修改是将i=0更改为i=1,或者将大小更改为size-1String.subs,结果中出现两次0,尽管其中一次在我为1时伪装为string.subs,i-1。谢谢,Kevin和molbdnilo。这就是我要找的。使用递归反转字符串让我很困惑。。。