如何对Theano矩阵逐元素赋值?NumPy和Theano之间的区别是什么?

3

我是theano的新手。我想用theano函数代替我的脚本中的numpy函数以加速计算过程。我不确定该如何做。

我的最终目标是对三维刚体应用仿射变换,为每次变换后的构象分配一个得分,并对决定得分的参数进行优化。

以下是我想要实现的一个示例。

import numpy as numpy 
import theano 
import theano.tensor as T 

pi = 3.141592653
deg2rad = lambda angle: (angle/180.)*pi 

# generate 3D transformation matrix for rotation around x axis by angle 

def rotate_x_axis_numpy(angle):  # my old numpy function 
    a    = deg2rad(angle)
    cosa = np.cos(a)
    sina = np.sin(a)
    R    = np.identity(4)
    R[1][1] = cosa; R[1][2] = -sina
    R[2][1] = sina; R[2][2] =  cosa
    return R    

angle_var = T.dscalar()

def rotate_x_axis_expr(angle): # new theano function expression I expected to work  
    a    = T.deg2rad(angle)
    cosa = T.cos(a)
    sina = T.sin(a)   
    R    = theano.shared(np.identity(4))
    R[1][1] = cosa; R[1][2] = -sina
    R[2][1] = sina; R[2][2] =  cosa
    return R

rotate_x_axis_theano = theano.function([angle_var], rotate_x_axis_expr(angle_var))

上述的 Theano 函数没有通过编译。我收到了以下错误信息。
---------------------------------------------------------------------------
TypeError     Traceback (most recent call last)<ipython-input-85-8d98ae1d1c9b> in <module>()
      17     return R
      18 
 ---> 19 rotate_x_axis_theano = theano.function([angle_var],rotate_x_axis_expr(angle_var))

<ipython-input-85-8d98ae1d1c9b> in rotate_x_axis_expr(angle)
      12   
      13 
 ---> 14     R[1][1] = cosa; R[1][2] = -sina
      15     R[2][1] = sina; R[2][2] =  cosa
      16 

TypeError: 'TensorVariable' object does not support item assignment

一般而言,我的问题是:

(1) 有没有一种方法可以逐元素地为Theano矩阵分配、更新或初始化特定形状的值,

(2) 由于Theano与NumPy密切相关,在定义、优化和评估数学表达式方面有什么区别,

以及(3) Theano能否取代NumPy,我们可以仅使用Theano函数来定义、优化和评估数学表达式而不调用NumPy函数。


只是提供信息,np.deg2rad 也存在,你使用 lambda 的原因是什么? - askewchan
啊,我之前不知道那个。谢谢你指出来! - Wang Zong'an
你可能想为关于Theano更一般的问题提问一个单独的问题。虽然谁知道你是否会得到太多回应。 - askewchan
2个回答

2

我无法回答你的问题1、2、3,因为十分钟前我还没有使用过theano。但是,在theano中定义函数时,似乎不需要使用def语句,你需要像这样做:

angle_var = T.dscalar('angle_var')
a    = T.deg2rad(angle_var)
cosa = T.cos(a)
sina = T.sin(a)   

R = theano.shared(np.identity(4))
R = T.set_subtensor(R[1,1],  cosa)
R = T.set_subtensor(R[1,2], -sina)
R = T.set_subtensor(R[2,1],  sina)
R = T.set_subtensor(R[2,2],  cosa)

rotate_x_axis_theano = theano.function([angle_var], R)

不过,对于标量角度而言,这并没有太大帮助:

In [368]: timeit rotate_x_axis_theano(10)
10000 loops, best of 3: 67.7 µs per loop

In [369]: timeit rotate_x_axis_numpy(10)
The slowest run took 4.23 times longer than the fastest. This could mean that an intermediate result is being cached
10000 loops, best of 3: 22.7 µs per loop

In [370]: np.allclose(rotate_x_axis_theano(10), rotate_x_axis_numpy(10))
Out[370]: True

是的,你说得对:theano并不需要def构造。我也遇到了关于项目分配的同样问题。 - Wang Zong'an
我想我弄清楚了,基于这封电子邮件。无论如何似乎比仅使用numpy版本要慢:我怀疑执行这些项目分配并不是那么快速的。 - askewchan
很酷,T.set_subtensor有效。我尝试过R = T.set_subtensor(R [1] [1],cosa),但是它没有起作用。谢谢。 - Wang Zong'an

2
为了让上面发布的theano函数正常工作,我的版本如下:
angle_var = T.dscalar()

def rotate_x_axis_expr(angle):
    a    = T.deg2rad(angle)
    cosa = T.cos(a)
    sina = T.sin(a)   

    R = theano.shared(np.identity(4))
    R = T.set_subtensor(R[1,1],  cosa)
    R = T.set_subtensor(R[1,2], -sina)
    R = T.set_subtensor(R[2,1],  sina)
    R = T.set_subtensor(R[2,2],  cosa)

    return R

rotate_x_axis = theano.function([angle_var],rotate_x_axis_expr(angle_var))

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接