在Racket

时间:2016-05-26 01:31:08

标签: matrix vector racket

对于大学项目,我必须使用相当大的语言制作基于矩阵的游戏,矩阵被定义为多维向量。 我需要设置矩阵的单个元素,我的代码是:

(require racket/vector)

(define test (make-vector 4 (make-vector 4 0)))

(define (matrix-set matrix row column value)
   (vector-set! (vector-ref matrix row) column value)
)
(display test)(newline)
(matrix-set test 0 0 1)
(display test)

并输出:

#(#(0 0 0 0) #(0 0 0 0) #(0 0 0 0) #(0 0 0 0))
#(#(1 0 0 0) #(1 0 0 0) #(1 0 0 0) #(1 0 0 0))

我搜索了球拍文档,但只找到了通过制作新矩阵thisthis问题来设置元素的函数。

为什么函数设置整列而不是仅设置元素?

可以做些什么来解决它?

2 个答案:

答案 0 :(得分:3)

(make-vector 4 (make-vector 4 0))与:

相同
(let ((x (make-vector 4 0)))
  (vector x x x x))

也就是说,(make-vector 4 0)只被调用一次,其值用于外部向量的所有4个插槽。

您需要的是像(for/vector ((i 4)) (make-vector 4 0))这样的内容,它会为外部向量的每个元素调用(make-vector 4 0)(并创建一个不同的向量)。

答案 1 :(得分:0)

另一种方法是使用生成迭代器for/vector的向量。我不确定语法是否比使用thunk更清晰,但从概念上讲,我觉得它更熟悉,也许更简单。

(define test (for/vector ([i (range 4)])(make-vector 4 0)))

(matrix-set test 0 0 1)  ; '#(#(1 0 0 0) #(0 0 0 0) #(0 0 0 0) #(0 0 0 0))

第三种选择,不像Racket那样,会使用do.

(define test
  (do ((vec (make-vector 4))
       (i 0 (+ i 1)))
      ((= i 4) vec)
    (vector-set! vec i (make-vector 4 0))))

另一方面,有时值得了解do,因为do不需要记住每种类型的不同命令,因为do执行它对矢量的作用,列表和哈希。