将列表分成3个组和插入符号

时间:2017-03-01 00:44:15

标签: list split scheme common-lisp racket

我试图创建一个函数,该函数将接受一个整数参数,并返回那些整数,其位置在拼写的数字内。例如。

  

(编号2135567667)

     

'(20亿1.35亿567千667)

我想我会用整数和余数将整数从右到左分成3到3组。并使用句子

  

'(千亿亿亿千万亿)

在输出句子中插入适当的符号。但是,有些情况下整个组将为零,例如:

  

(号码1000000)

     

'(100万)

  

(1000000001)

     

10亿1

有没有更好的方法来解决这个问题?或者,如果它是零,我怎么能省略一个组及其名称?

(define 1to19 '(one two three four five six seven eight nine ten eleven twelve thirteen fourteen fifteen sixteen seventeen eighteen nineteen))
(define multiple '(twenty thirty forty fifty sixty seventy eighty ninety))

(let loop ((n n) (units thousands) (acc '()))
       (cond
         ((= n 0)    acc)
         ((< 0 n 20) (cons (list-ref 1to19    (- n 1)) acc))
         ((< n 100)  (cons (list-ref multiples (- (quotient n 10) 2))
                           (loop (remainder n 10) '() acc)))
         ((< n 1000) (loop (quotient n 100)
                           '()
                           (cons 'hundred (loop (remainder n 100) '() res))))

1 个答案:

答案 0 :(得分:1)

您可以采用一种方法来构建列表,方法是以单位添加将数字拆分为多个组。例如,在Racket中你可以拥有:

(define (number n)
  (define units '(thousand million billion trillion quadrillion))
  (define (nsplit n units acc lst)
    (define q (quotient n 1000))
    (define r (remainder n 1000))
    (if (zero? n) lst
        (cond [(zero? acc)
               (if (zero? r)
                   (nsplit q units (add1 acc) lst)
                   (nsplit q units (add1 acc) (cons r lst)))]
              [(zero? r)
               (nsplit q (cdr units) acc lst)]
              [else
               (nsplit q (cdr units) acc (cons r (cons (car units) lst)))])))
  (nsplit n units 0 empty))

然后:

> (number 2135567667)
'(2 billion 135 million 567 thousand 667)
> (number 1000000)
'(1 million)
> (number 1000000001)
'(1 billion 1)