(elisp)载体载体的元素

时间:2013-01-30 03:16:48

标签: emacs elisp

我构建了一个由向量​​矢量组成的二维数组(矩阵):

(setq zero-row [0 0 0 0 0])
  => [0 0 0 0 0]

(setq zero-mat (make-vector 4 zero-row))
  => [[0 0 0 0 0] [0 0 0 0 0] [0 0 0 0 0] [0 0 0 0 0]]

我将第2行第3列(0索引)中的元素设置为42,方法是将第2行替换为包含更改元素的向量:

(aset zero-mat 2 [0 0 0 42 0])
  => [0 0 0 42 0]

zero-mat
  => [[0 0 0 0 0] [0 0 0 0 0] [0 0 0 42 0] [0 0 0 0 0]]

有效。

接下来我尝试构建一个函数,该函数采用这种方法在这样的二维数组中设置第(i,j)个元素:

(defun matrix-set (mat i j elt)
"Set the (i, j)-th element of mat to elt. mat is a vector of the row vectors. Indexing is 0-based in each component."
(let ((vect (aref mat i)))
   (aset vect j elt)
   (aset mat i vect)
   mat))

但这不起作用:

(setq zero-row [0 0 0 0 0])
  => [0 0 0 0 0]

(setq zero-mat (make-vector 4 zero-row))
  => [[0 0 0 0 0] [0 0 0 0 0] [0 0 0 0 0] [0 0 0 0 0]]

(matrix-set zero-mat 2 3 42)
  => [[0 0 0 42 0] [0 0 0 42 0] [0 0 0 42 0] [0 0 0 42 0]]

看起来数组的所有行都链接到同一个向量,因此更改该向量会更改所有行。

所以有两个问题:(1)为什么会在第二种情况下发生这种情况,而不是第一种情况? (2)如何解决这个问题(所以我可以访问以这种方式表示的2-dim。数组的第(i,j)个条目)?

(我最初编写了一个小例程来添加两个矩阵,表示为上面的向量向量,并遇到了同样的问题。我认为上面的精简示例可能会使问题更加清晰。)

1 个答案:

答案 0 :(得分:3)

在第一种情况下,您正在用另一个向量替换“外部”向量中的元素(而其他三个“内部”向量仍然指向同一个元素)。在第二种情况下,您替换“内部”向量中的元素(并且根据您的示例,您只有一个内部向量重复四次。将向量初始化为不同的不同向量的简单方法将是像这样的东西:

(let ((i 0) (new-vector (make-vector 4 nil))
 (while (< (progn (aset new-vector i (make-vector 5 0))
                  (incf i))
           (length new-vector)))

很抱歉,如果有任何拼写错误,请将其写入就地。但这个想法应该足够简单,以便弄明白。