Как проиндексировать список Python в Sympy Sum? - PullRequest
3 голосов
/ 26 февраля 2020

Я хочу вычислить следующую сумму (последнюю строку кода) в Python, используя Sympy:

# Theta Functions, n = 0, 1, ... , x
theta_n = [0]*(x+1)
sig = sy.symbols('sigma^2', real=True)
j = sy.symbols('j', integer=True)
theta_n[0] = 1
theta_n[1] = 1 
for n in range(2,x+1):
   theta_n[n] = sy.Sum( sig**j * theta_n[n-2*j], (j,1,int(n/2))).doit()

, но я получаю следующую ошибку

TypeError: list индексы должны быть целыми числами или кусочками, а не Add

Я - полный новичок Sympy ie и хотел бы знать, как сделать это правильно. Одним из обходных путей было бы вычисление суммы с помощью a для l oop, что хорошо работает, но я думаю, что это не правильный способ сделать это. Возможно, мне нужно другое представление для тэтана, или я могу каким-то образом преобразовать j в целое число в сумме, чтобы получить доступ к элементам списка python.

Ответы [ 2 ]

2 голосов
/ 26 февраля 2020

Вместо использования Sum используйте al oop over j

for j in range(1, n//2 + 1):
    theta_n[n] += theta_n[n-2*j]*sig**j

Эти две строки заменяют вашу единственную строку на Sum.

Как только вы посмотрите на результаты, которые вы получить вы могли заметить шаблон и переписать n-й термин как

>>> theta_n = lambda x: 2**max(0, x//2-1)*sig**(x//2)
>>> theta_n(100)
562949953421312*sigma^2**50
1 голос
/ 26 февраля 2020

Основная проблема заключается в том, что вы пытаетесь использовать символ симпйи (j) для индексации в списке. Индексирование списка работает только с Python целыми числами. В вашем случае вы можете использовать j для обычного Python целого числа и использовать обычное Python sum. Эта обычная сумма будет сначала преобразована в сложение, а затем в Add при необходимости. Обратите внимание, что команде диапазона Python нужно на одно число больше, чем последний индекс.

import sympy as sy

x = 12

theta_n = [0]*(x+1)
sig = sy.symbols('sigma^2', real=True)
theta_n[0] = 1
theta_n[1] = 1
for n in range(2, x+1):
    theta_n[n] = sum(sig ** j * theta_n[n - 2 * j] for j in range(1, n//2+1) )

Обратите внимание, что в выражении sympy sy.Sum( sig**j * theta_n[n-2*j], (j,1,int(n/2))), j - полная переменная symboli c, и j на самом деле не принимает все значения одно за другим, например, в итерации Python.

Рассмотрим, например:

print(sy.Sum(j*j, (j, 1, 1_000_000_000)).doit())

Sympy немедленно дает правильный результат (333333333833333333500000000) путем преобразования выражения в n**3/3 + n**2/2 + n/6. Это займет много времени для вычисления с регулярным суммированием Python.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...