例如,我可以定义一个递归Python lambda函数来计算斐波那契数列,如下所示:
fn = lambda z: fn(z-1)+fn(z-2) if z > 1 else z但是,如果我尝试将其转换为Theano函数,Theano将不会接受fn,因为fn调用了布尔运算">“。所以这段代码崩溃了:
z = T.scalar('z')
fn = lambda z: fn(z-1)+fn(z-2) if z > 1 else z
fibby = theano.function([z], fn(z))但是如果我将布尔运算符替换为theano.tensor.gt(z,1),代码将进入无限递归,因此theano.tensor.gt(z,1)不起“>”的作用:
z = T.scalar('z')
fn = lambda z: fn(z-1)+fn(z-2) if theano.tensor.gt(z,1) else z
lappy = theano.function([z], fn(z))
print(lappy(4))运行此命令会导致“超过最大递归深度”。怎么了?如果我将fn的定义替换为,我得到相同的“最大递归深度超过”错误
fn = lambda z: theano.ifelse(theano.tensor.gt(z,1),fn(z-1)+fn(z-2),z)另外,我不希望使用theano.scan来做这件事。因为我想学习如何递归地执行此计算,而不是求助于显式循环。
--肯
发布于 2018-08-15 21:44:09
在Theano中,您可以使用theano.scan(fn=myfunc(), outputs_info=...)的outputs_info参数进行递归,并在myfunc()的下一次迭代中将myfunc()之前的输出作为参数传递。
在斐波那契序列的情况下,代码可能如下所示:
import numpy as np
import theano
import theano.tensor as T
# placeholder for the number of elements in the Fibonacci sequence
t_N = T.iscalar('N')
# first two elements for Fibonacci sequence
initial = np.array([1,1], dtype=np.int32)
t_initial = theano.shared(initial)
def fibonacci_iter(prev1_value, prev2_value):
return prev1_value + prev2_value
# Iterate N-2 times over fibonacci() function
# ('taps': [-2,-1] means take two previous values in the sequence of outputs):
outputs, updates = theano.scan(
fn=fibonacci_iter,
outputs_info = [{'initial': t_initial, 'taps': [-2,-1]}], # a list of dicts or a dict
n_steps=t_N-2)
# compiled function:
fibonacci = theano.function(
inputs=[t_N],
outputs=outputs)
n = 10
fibonacci_seq = fibonacci(n)
print(np.concatenate([initial, fibonacci_seq]))输出:
[ 1 1 2 3 5 8 13 21 34 55]参考资料:
http://deeplearning.net/software/theano/library/scan.html#theano.scan
https://stackoverflow.com/questions/42480494
复制相似问题