【SICP练习】66 练习2.37

简介:


练习2.37

这道题花了我太长的时间了,一开始我就把题目中的m看成了w。然后题中给出的dot-product的两个参数我还以为一个是向量另一个是矩阵。怎么算都算不出来,直到看到“返回求和...”里的w只有一个i而没有j。好了,那么开始按照题目的要求来做题了。

既然发现了自己的错误,那么就知道了dot-product是干嘛的了,它可以用来求一个矩阵中的一列和一个向量的积。因此定义出matrix-*-vector就不难了。

(define (matrix-*-vector m v)

   (map (lambda (col)

             (dot-product col v))

          m))

下面就来用题目中的数据来测试一下。

(matrix-*-vector ‘( (1 2 3 4) (4 5 6 6)(6 7 8 9) ) )

;Value: (30 56 80)

接下来我们来看看transpose,之所以把matrix-*-matrix放在最后是因为其的定义中需要transpose

(define (transpose mat)

  (accumulate-n cons ‘() mat))

看似这么一行代码,但其功能可强大了。

(transpose ‘((1 2 3 4) (4 5 6 6) (6 7 89)))

;Value: ((1 4 6) (2 5 7) (3 6 8) (4 69))

如果这里accumulate的变化有什么不明白的,可以回过头看看练习2.33的解答中的截图。而accumulate-n只不过是个accumulate的外壳而已,在变换中accumulate-n都将会慢慢变成accumulate

在线性代数里我们学过,两个矩阵的乘积mn的第一列第一行的值等于m的第一列和n的第一行的点积,mn的第一列第二行的值等于m的第一列和n的第二行的点积……

(define (matrix-*-matrix m n)

   (let ((cols (transpose n)))

      (map (lambda (col-of-m)

                (matrix-*-vector colscol-of-m))

             m)))

目录
相关文章