将单词列表与Racket中的para结合起来

时间:2016-09-02 07:34:22

标签: scheme racket

我必须结合一个单词列表来产生一个段落。我管理了以下内容:

(define (wordlist2para wl)
  (define str " ")
  (for ((w wl))
    (set! str (string-append str w " ")))
  (string-trim str))

(wordlist2para '("this" "is" "a" "test"))

输出:

"this is a test"

它有效,但不起作用。如何为此编写功能代码?

4 个答案:

答案 0 :(得分:3)

如果我想明确地做而不使用string-join,我会递归并使用三种情况:

  • 空列表生成空字符串
  • 单元素列表生成其唯一元素(这避免了具有尾随分隔符)
  • 否则,将car和空格附加到cdr上的递归。

像这样:

(define (wordlist2para ws)
  (cond ((null? ws) "")
        ((null? (cdr ws)) (car ws))
        (else (string-append (car ws) " " (wordlist2para (cdr ws))))))

答案 1 :(得分:2)

不需要递归或循环,有原始函数string-join(参见manual):

(define (wordlist2para wl)
  (string-join wl " "))

(wordlist2para '("this" "is" "a" "test"))

;; -> "this is a test"

答案 2 :(得分:2)

我们有标准程序来执行此操作:

;; racket library or srfi/13
(string-join '("this" "is" "it"))   ; ==> "this is it"

有一种方法可以始终重写这些非常简单的方法。我想远离球拍的强大功能集,只关注简单的方案和递归程序。请注意,在您的循环中,您正在更改2件事wl变小,str变得更长,所以让我们这样做:

; all things that change as arguments
(define (wordlist2para-loop wl str) 
  (if (null? wl)
      str
      (wordlist2para-loop (cdr wl)
                          (string-append str (car wl) " "))))

现在我们只需更换循环:

(define (wordlist2para wl)
  (wordlist2para-loop wl ""))

从这里开始,您可以将帮助程序移动到本地或者使其成为命名的let或任何其他重构,但它实际上并没有真正改变实现的编译结果,只是如何它看起来。

注意我还没有修复只有一个单词的错误。 (wordlist2para '("this")) ; ==> "this "结果实际上与您的结果完全相同,只是它的尾部递归且功能正常。

答案 3 :(得分:1)

我不确定是否可以调用以下函数,但它确实使用了一些高阶函数:

(define (wordlist2para wl)
  (string-trim 
    (apply string-append 
        (map (lambda(x) (string-append x " ")) wl))))

(wordlist2para '("this" "is" "a" "test"))

输出:

"this is a test"