2010-06-22 10 views
6

Potrzebuję napisać kod, który zajmuje się generowaniem wielomianów wielowymiarowych i manipulowaniem nimi. Opiszę moje zadanie za pomocą uproszczonego przykładu.Biblioteki do obsługi wielomianów wielowymiarowych

Powiedzmy, że otrzymałem trzy wyrażenia: 2x^2, 3y + 1 i 1z. Potem muszę je pomnożyć, co dałoby mi 6x^2yz + 2x^2z. Następnie chciałbym znaleźć częściowe pochodne tego wyrażenia w odniesieniu do x, yi z. To dałoby mi 12xyz + 4xz, 6x^2z i 6x^2y + 2x^2.

Mój problem polega na robieniu prostych manipulacji takich jak to w wyrażeniach zawierających tysiące zmiennych i potrzebuję prostego sposobu, aby zrobić to systematycznie. Naprawdę chciałbym użyć Pythona, ponieważ mam już wiele funkcji związanych z projektem zakończonych przy użyciu numpy/scipy/matplotlib, ale jeśli istnieje solidny zestaw narzędzi w innym języku, jestem również otwarty na używanie tego języka. Prowadzę badania uniwersyteckie, więc jestem również otwarty na korzystanie z Matlaba.

Nie byłem w stanie znaleźć żadnych dobrych bibliotek Pythona, które mogłyby zrobić to dla mnie łatwo i idealnie chciałbym coś podobnego do scipy polynomial routines, które mogłyby pracować na wielowymiarowych wielomianach. Czy ktoś wie o dobrej bibliotece, która wydaje się odpowiednia dla tego problemu i która byłaby łatwa do zintegrowania z już istniejącym kodem Pythona?

Dzięki!

Kontynuacja: Spędziłem kilka dni pracy z sympy, który okazał się bardzo łatwy w użyciu. Jednak rozmiar problemu, nad którym pracuję, znacznie się zmniejszył, więc teraz przejdę do zbadania matlab. Aby uzyskać bardzo przybliżoną ocenę prędkości przy użyciu małego rozmiaru próbki, obliczenie każdej częściowej pochodnej wielomianu rzędu 2 zawierającego 250 zmiennych zajęło około 5 sekund.

Kontynuacja # 2: Prawdopodobnie powinieneś był zrobić to z powrotem, gdy wciąż pracowałem nad tym problemem, ale równie dobrze mogłem poinformować wszystkich, że symboliczna biblioteka matlab była niezwykle porównywalna w tempie do sympy. Innymi słowy, w przypadku dużych obliczeń było ono brutalnie wolne. Obie biblioteki były niezwykle łatwe w obsłudze, więc dla małych obliczeń bardzo polecam albo.

Aby rozwiązać mój problem, ręcznie obliczałem gradienty, uprościłem je, a następnie użyłem znalezionych przeze mnie wzorców do zakodowania pewnych wartości w moim kodzie. To było więcej pracy, ale mój kod był wykładniczo szybszy i ostatecznie użyteczny.

+0

W jaki sposób reprezentatywny jest Twój przykład? Jeśli początkowe polysy są funkcjami tylko jednego var, problem wydaje się łatwiejszy. –

+1

+1: Naprawdę dobre pytanie. Podszedłem * do * zasugerowania SymPy, która oczywiście dokonuje obliczeń symbolicznych (w przeciwieństwie do bibliotek oznaczonych tagami), ale wydaje się, że robi to jedynie numeryczne różnicowanie! http://docs.sympy.org/modules/mpmath/calculus/differentiation.html –

+0

@Nikhil: sympy również robi symboliczne zróżnicowanie. Zobacz mój przykład poniżej. –

Odpowiedz

9

Sympy jest idealny do tego: http://code.google.com/p/sympy/

Dokumentacja: http://docs.sympy.org/

Przykłady różnicowania z samouczka: http://docs.sympy.org/tutorial.html#differentiation

import sympy 

x, y, z = sympy.symbols('xyz') 

p1 = 2*x*x 
p2 = 3*y + 1 
p3 = z 

p4 = p1*p2*p3 

print p4 

print p4.diff(x) 
print p4.diff(y) 
print p4.diff(z) 

wyjściowa:

2*z*x**2*(1 + 3*y) 
4*x*z*(1 + 3*y) 
6*z*x**2 
2*x**2*(1 + 3*y) 
+0

+1: Ponownie przeglądam dokumenty, wspominają, że argumenty liczbowe są opcjonalne i dlaczego ... to dziwne, że mają ** nie ** przykłady z tylko symbolicznym zróżnicowaniem. –

+0

Jest to idealne rozwiązanie dla tego, czego potrzebuję. Dzięki za przykład! – Spike

+0

@Nikhil: Dzięki, że również zaglądasz do mnie! Jestem naprawdę pod wrażeniem pomocy, którą dostałem tutaj na SO – Spike

1

Matlab i inne wspomniane narzędzia zwykle wykonują obliczenia numeryczne. Powinieneś rozważyć użycie Mathematica lub alternatywy Computer Algebra System (CAS) do obliczeń symbolicznych. Zobacz link wiki: http://en.wikipedia.org/wiki/Comparison_of_computer_algebra_systems w celu porównania różnych CAS.

+0

Dzięki za wejście. Mam zamiar spróbować najpierw sympy, bo kocham pythona i będzie to zdecydowanie najłatwiejsze do zakodowania. Jeśli z jakiegokolwiek powodu jest zbyt wolny (niektóre metody optymalizacji scipy były powolne na dużych zbiorach danych), to z pewnością spróbuję w innym środowisku. – Spike

2

Jeśli używasz MATLAB, the n symboliczna gruźlica działa dobrze, JEŚLI masz ją. Jeśli nie, użyj mojego przybornika sympoly. Wystarczy pobrać go z giełdy plików.

sympoly x y z 
A = 2*x^2; B = 3*y + 1;C = 1*z; 
gradient(A*B*C) 

ans = 
Sympoly array has size = [1 3] 

Sympoly array element [1 1] 
    4*x*z + 12*x*y*z 
Sympoly array element [1 2] 
    6*x^2*z 
Sympoly array element [1 3] 
    2*x^2 + 6*x^2*y 

Zauważ, że ten wskazuje, że popełnił błąd w różnicowaniu wynik w odniesieniu do Z w swoim pytaniu.

+0

Dziękuję za znalezienie mojego błędu. Twój zestaw narzędzi sympoly wygląda ładnie i jeśli będę musiał użyć Matlab do tego problemu, dam mu wir. – Spike

Powiązane problemy