2017-01-21 13 views
1

Я пытаюсь подставить IndexedBase внутри суммирования в sympy. Вне суммирования он работает, но внутри я получаю обратно выражение без подстановки:Замена IndexedBase внутри суммирования

In [125]: (f, n) = sympy.symbols("f n") 

In [126]: foo = sympy.IndexedBase(f)[n] 

In [127]: foo.subs(foo, 1) 
Out[127]: 1 

In [128]: sympy.Sum(foo, (n, 0, 5)).subs(foo, 1) 
Out[128]: 
    5  
___  
╲   
    ╲ f[n] 
    ╱  
╱   
‾‾‾  
n = 0  

Почему последний шаг не заменит f[n] 1, и как мне нужно изменить свой код, чтобы убедиться, что он делает?

ответ

2

Это не работает, потому что n - это фиктивная переменная, и она изменит значение суммирования. То есть, .subs() должны дать вам такое же значение, когда применяются к расширенному суммированию:

In [7]: sympy.Sum(foo, (n, 0, 5)).doit() 
Out[7]: f[0] + f[1] + f[2] + f[3] + f[4] + f[5] 

В этом выражении нет никакого е [п] больше, так как он был заменен соответствующие числовые значения. Замена не будет работать:

In [8]: sympy.Sum(foo, (n, 0, 5)).doit().subs(foo, 1) 
Out[8]: f[0] + f[1] + f[2] + f[3] + f[4] + f[5] 

Поэтому .subs() будет игнорировать матчи на переменные, которые суммируются в течение (в данном случае п).

заменить() с другой стороны, не заботиться о последовательности значений и заменяет выражение соответствия в любом случае:

In [9]: sympy.Sum(foo, (n, 0, 5)).replace(foo, 1) 
Out[9]: 
    5  
___ 
╲  
    ╲ 1 
    ╱  
╱  
‾‾‾ 
n = 0 

Конечно, результирующее значение теперь отличается:

In [10]: sympy.Sum(foo, (n, 0, 5)).replace(foo, 1).doit() 
Out[10]: 6 
0

Это работает, если вы используете replace method вместо:

In [129]: sympy.Sum(foo, (n, 0, 5)).replace(foo, 1) 
Out[129]: 
    5  
___ 
╲  
    ╲ 1 
    ╱  
╱  
‾‾‾ 
n = 0 

Смотрите также this answer.