Scheme - 如何在通过字符串时查找字符索引

时间:2014-11-21 20:36:22

标签: hash scheme lambda

功能问题我在Scheme中写作。该方法将表示为符号列表的单词作为输入,并且对于每个字符,执行散列等式并返回值。最终值是集合中每个字符的哈希值的总和。

想象一个字符串作为一个字符数组,' w',其中w [i]是数组中每个字符的索引。

等式是 - >的总和。 7 ^ i * ctv(w [i])代表单词中的每个字符。

对于每个字母,ctv(“character-to-value”)将'a'映射为1,'b'映射为2,...和'z'映射为26。

例如,键(“d y y”)      =(7 ^ 0 * ctv('d'))+(7 ^ 1 ctv('a'))+(7 ^ 2 ctv('y'))= 1236

所以,我关于这个的实际问题是我如何找到索引,w [i]中的每个字符中的i。 这是我的第一个想法,使用(长度为w)作为索引,但我知道这是不正确的。

(define keys
  (lambda(w)
    (if(null? w)
      0
    (+ (* (ctv(car w)) (expt 7 (length w)))  (keys (cdr w)))))
   )

我的下一个想法可能是它的大小lambda,就像这样。 注意 - 我知道需要将其更改为(size-1)。

(define keys
  (lambda(size)
    (lambda(w)
      (if(null? w)
        0
      (+ (* (ctv(car w)) (expt 7 (size w)))  (keys (cdr w)))))
     )

但即便如此,尺寸仍然是指数的另一端,例如“' day'”,尺寸-1为' d'将是2,大小为1' y'将是0.

无论如何,如果有人知道我在谈论什么,并有可能的解决方案或建议,请回复!!

2 个答案:

答案 0 :(得分:1)

这里的技巧是将索引作为参数传递,并在遍历列表的同时递增它。此外,如果我们将输入字符串转换为字符列表,则更容易,例如:

(define (key word)
  (let loop ((chars (string->list word)) ; list of chars
             (idx 0)  ; current index
             (acc 0)) ; accumulated result
    (if (null? chars) ; if the list is empty
        acc           ; return the accumulator
        (loop (cdr chars) ; otherwise go to the next char
              (add1 idx)  ; advance the index
              (+ acc (* (expt 7 idx) (ctv (car chars)))))))) ; compute result

假设正确实现了ctv过程,它应该按预期工作:

(key "day")
=> 1236

答案 1 :(得分:1)

由于此问题也标记为 Racket ,因此您可能会欣赏使用for/sumin-indexed的优雅,仅限Racket的解决方案:

(define (key word)
  (for/sum (((c i) (in-indexed word)))
    (* (expt 7 i) (cvt c))))

测试:

> (key "day")
1236