找出给定数的因子的方案程序

  • 本文关键字:方案 程序 scheme
  • 更新时间 :
  • 英文 :


我最近开始学习scheme,为了测试我的技能,我决定设计一个程序,打印出给定数字的所有因子。

但是,程序不会返回任何输出。我不知道原因,因为我认为我已经很好地检查了划分的条件。

这是我的密码。问题出在哪里?我无法准确定位。

(define 
    (factors n f)
    (if (= 0 (remainder n f) )
        f )
    (if (< f n) 
        (factors n (+ f 1))))

程序的名称是因子。它需要两个输入数字:nfN是必须为其找到因子的数字。F是将从中打印n的因子的数字。

您的代码中有几个错误。对于初学者来说,永远不应该有一个武装的if表达式(也就是说,一个没有"else"部分的if);如果发生这种情况,一些解释器会更进一步,并引发编译错误。此外,您应该使用cond而不是嵌套if s。

请记住,在Scheme中,所有内容都是表达式,并且必须返回一个值,但有一种情况您没有考虑:如果(>= f n)会发生什么?这是函数逻辑中的一个漏洞,这就是我的意思:

(define (factors n f)
  (if (= 0 (remainder n f))
      f
      (if (< f n) 
          (factors n (+ f 1))
          ; else?
          )))

此外,如果要返回所有因子,则必须在递归的每个点打印它们或将它们累积在列表中,否则只返回最后一个结果。最后但并非最不重要的是,该算法根本不起作用。它需要从头开始重写。假设你只想打印结果,这个解决方案考虑了我以前的所有建议:

(define (factors n f)
  (cond ((> f n) 'done)
        ((= 0 (remainder n f))
         (display f)
         (newline)
         (factors n (+ f 1)))
        (else
         (factors n (+ f 1)))))
(factors 23174 1)
=> 1
   2
   11587
   23174
   'done

Scheme中更惯用的解决方案是返回一个包含所有值的列表,而不是一路上打印它们,使用尾部递归来获得更好的性能:

(define (factors n f)
  (let loop ((f f) (acc '()))    
    (cond ((> f n) (reverse acc))
          ((zero? (remainder n f))
           (loop (add1 f) (cons f acc)))
          (else (loop (add1 f) acc)))))
(factors 23174 1)
=> '(1 2 11587 23174)

最新更新