Você precisa usar Sympy: sympy.org/en/index.html Numpy é uma biblioteca de computação numérica para Python
prrao
Alternativamente, você quer um método para estimar o valor numérico da derivada? Para isso, você pode usar um método de diferenças finitas, mas tenha em mente que eles tendem a ser terrivelmente barulhentos.
Diferenças finitas não requerem ferramentas externas, mas estão sujeitas a erros numéricos e, se você estiver em uma situação multivariada, pode demorar um pouco.
A diferenciação simbólica é ideal se o seu problema for simples o suficiente. Os métodos simbólicos estão ficando bastante robustos atualmente. SymPy é um excelente projeto para isso que se integra bem com o NumPy. Veja as funções autowrap ou lambdify ou confira a postagem do blog de Jensen sobre uma questão semelhante .
Derivados automáticos são muito legais, não estão sujeitos a erros numéricos, mas requerem algumas bibliotecas adicionais (google para isso, existem algumas boas opções). Esta é a escolha mais robusta, mas também a mais sofisticada / difícil de configurar. Se você está bem restringindo-se à numpysintaxe, Theano pode ser uma boa escolha.
Aqui está um exemplo usando SymPy
In[1]:from sympy import*In[2]:import numpy as npIn[3]: x =Symbol('x')In[4]: y = x**2+1In[5]: yprime = y.diff(x)In[6]: yprimeOut[6]:2⋅xIn[7]: f = lambdify(x, yprime,'numpy')In[8]: f(np.ones(5))Out[8]:[2.2.2.2.2.]
Desculpe, se isso parece estúpido, quais são as diferenças entre 3. Diferenciação simbólica e 4. diferenciação manual ??
DrStrangeLove
11
Quando eu disse "diferenciação simbólica", pretendia sugerir que o processo era controlado por um computador. Nos princípios 3 e 4 diferem apenas por quem faz o trabalho, o computador ou o programador. 3 é preferível a 4 devido à consistência, escalabilidade e preguiça. 4 é necessário se 3 não conseguir encontrar uma solução.
MRocklin
4
Na linha 7 fizemos f, uma função que calcula a derivada de y wrt x. Em 8, aplicamos esta função derivada a um vetor de todos os uns e obtemos o vetor de todos os dois. Isso ocorre porque, conforme declarado na linha 6, yprime = 2 * x.
MRocklin
Apenas para fins de integridade, você também pode fazer diferenciação por integração (consulte a fórmula integral de Cauchy), ela é implementada, por exemplo, em mpmath(não tenho certeza, porém, do que eles fazem exatamente).
DerWeh
Existe uma maneira fácil de fazer diferenças finitas em numpy sem implementá-lo sozinho? por exemplo, eu quero encontrar o gradiente de uma função em pontos predefinidos.
x = numpy.linspace(0,10,1000)
dx = x[1]-x[0]
y = x**2+1
dydx = numpy.gradient(y, dx)
Dessa forma, dydx será calculado usando diferenças centrais e terá o mesmo comprimento que y, ao contrário de numpy.diff, que usa diferenças diretas e retornará o vetor de tamanho (n-1).
@ weberc2, nesse caso você deve dividir um vetor por outro, mas tratar as arestas separadamente com derivadas para frente e para trás manualmente.
Sparkler
2
Ou você pode interpolar y com um dx constante e calcular o gradiente.
IceArdor
@Sparkler Obrigado por sua sugestão. Se eu puder fazer 2 pequenas perguntas, (i) por que passamos dxpara em numpy.gradientvez de x? (ii) Podemos também fazer a sua última linha da seguinte forma dydx = numpy.gradient(y, numpy.gradient(x)):?
user929304
2
A partir de v1.13, o espaçamento não uniforme pode ser especificado usando uma matriz como o segundo argumento. Veja a seção de exemplos desta página .
Nathaniel Jones
26
NumPy não fornece funcionalidade geral para calcular derivados. Ele pode lidar com o caso especial simples de polinômios, no entanto:
>>> p = numpy.poly1d([1,0,1])>>>print p21 x +1>>> q = p.deriv()>>>print q2 x>>> q(5)10
Se você deseja calcular a derivada numericamente, pode usar os quocientes de diferença centrais para a grande maioria das aplicações. Para a derivada em um único ponto, a fórmula seria algo como
'Calcular derivadas numéricas para casos mais gerais é fácil' - discordo, calcular derivadas numéricas para casos gerais é bastante difícil. Você acabou de escolher funções bem comportadas.
High Performance Mark
o que significa 2 após >>> imprimir p ?? (na 2ª linha)
DrStrangeLove
@DrStrangeLove: Esse é o expoente. Destina-se a simular notação matemática.
Sven Marnach
@SvenMarnach é o expoente máximo ?? ou o que?? Por que ele acha que o expoente é 2 ??
Inserimos
2
@DrStrangeLove: A saída deve ser lida como 1 * x**2 + 1. Eles colocam o 2na linha acima porque é um expoente. Olhe à distância.
Sven Marnach
14
Supondo que você queira usar numpy, você pode calcular numericamente a derivada de uma função em qualquer ponto usando a definição Rigorous :
def d_fun(x):
h =1e-5#in theory h is an infinitesimalreturn(fun(x+h)-fun(x))/h
Você também pode usar a derivada simétrica para obter melhores resultados:
def d_fun(x):
h =1e-5return(fun(x+h)-fun(x-h))/(2*h)
Usando seu exemplo, o código completo deve ser semelhante a:
def fun(x):return x**2+1def d_fun(x):
h =1e-5return(fun(x+h)-fun(x-h))/(2*h)
Agora, você pode encontrar numericamente a derivada em x=5:
scipy.interpolateOs muitos splines de interpolação do são capazes de fornecer derivadas. Portanto, usando um spline linear ( k=1), a derivada do spline (usando o derivative()método) deve ser equivalente a uma diferença direta. Não tenho certeza, mas acredito que usar uma derivada de spline cúbica seria semelhante a uma derivada de diferença centrada, pois usa valores anteriores e posteriores para construir a spline cúbica.
from scipy.interpolate importInterpolatedUnivariateSpline# Get a function that evaluates the linear spline at any x
f =InterpolatedUnivariateSpline(x, y, k=1)# Get a function that evaluates the derivative of the linear spline at any x
dfdx = f.derivative()# Evaluate the derivative dydx at each x location...
dydx = dfdx(x)
acabei de tentar fazer isso, continuo recebendo erros desta função AxisError: o eixo -1 está fora dos limites para a matriz de dimensão 0 e não vejo nenhuma resposta para isso na comunidade, qualquer ajuda?
Ayan Mitra
Poste seu problema como uma nova pergunta e crie um link para ela aqui. Provavelmente, será necessário fornecer um exemplo que faça com que seu erro ocorra. Os erros que tenho com funções interp geralmente ocorrem porque os dados não estão bem formados ao entrar - como valores repetidos, número incorreto de dimensões, um dos arrays está acidentalmente vazio, os dados não são classificados em x ou quando classificados não é um função válida, etc. É possível que scipy esteja chamando numpy incorretamente, mas é muito improvável. Verifique x.shape e y.shape. Veja se np.interp () funciona - pode fornecer um erro mais útil se não funcionar.
flutefreak7
5
Para calcular gradientes, a comunidade de aprendizado de máquina usa Autograd:
Respostas:
Você tem quatro opções
Diferenças finitas não requerem ferramentas externas, mas estão sujeitas a erros numéricos e, se você estiver em uma situação multivariada, pode demorar um pouco.
A diferenciação simbólica é ideal se o seu problema for simples o suficiente. Os métodos simbólicos estão ficando bastante robustos atualmente. SymPy é um excelente projeto para isso que se integra bem com o NumPy. Veja as funções autowrap ou lambdify ou confira a postagem do blog de Jensen sobre uma questão semelhante .
Derivados automáticos são muito legais, não estão sujeitos a erros numéricos, mas requerem algumas bibliotecas adicionais (google para isso, existem algumas boas opções). Esta é a escolha mais robusta, mas também a mais sofisticada / difícil de configurar. Se você está bem restringindo-se à
numpy
sintaxe, Theano pode ser uma boa escolha.Aqui está um exemplo usando SymPy
fonte
mpmath
(não tenho certeza, porém, do que eles fazem exatamente).A maneira mais direta que consigo pensar é usando a função gradiente do numpy :
Dessa forma, dydx será calculado usando diferenças centrais e terá o mesmo comprimento que y, ao contrário de numpy.diff, que usa diferenças diretas e retornará o vetor de tamanho (n-1).
fonte
dx
para emnumpy.gradient
vez dex
? (ii) Podemos também fazer a sua última linha da seguinte formadydx = numpy.gradient(y, numpy.gradient(x))
:?NumPy não fornece funcionalidade geral para calcular derivados. Ele pode lidar com o caso especial simples de polinômios, no entanto:
Se você deseja calcular a derivada numericamente, pode usar os quocientes de diferença centrais para a grande maioria das aplicações. Para a derivada em um único ponto, a fórmula seria algo como
se você tem uma matriz
x
de abscissas com uma matriz correspondentey
de valores de função, você pode calcular aproximações de derivadas comfonte
1 * x**2 + 1
. Eles colocam o2
na linha acima porque é um expoente. Olhe à distância.Supondo que você queira usar
numpy
, você pode calcular numericamente a derivada de uma função em qualquer ponto usando a definição Rigorous :Você também pode usar a derivada simétrica para obter melhores resultados:
Usando seu exemplo, o código completo deve ser semelhante a:
Agora, você pode encontrar numericamente a derivada em
x=5
:fonte
Vou jogar outro método na pilha ...
scipy.interpolate
Os muitos splines de interpolação do são capazes de fornecer derivadas. Portanto, usando um spline linear (k=1
), a derivada do spline (usando oderivative()
método) deve ser equivalente a uma diferença direta. Não tenho certeza, mas acredito que usar uma derivada de spline cúbica seria semelhante a uma derivada de diferença centrada, pois usa valores anteriores e posteriores para construir a spline cúbica.fonte
Para calcular gradientes, a comunidade de aprendizado de máquina usa Autograd:
Para instalar:
Aqui está um exemplo:
Ele também pode calcular gradientes de funções complexas, por exemplo, funções multivariadas.
fonte
Dependendo do nível de precisão que você precisa, você mesmo pode resolver isso usando a prova simples de diferenciação:
não podemos realmente pegar o limite do gradiente, mas é divertido. Você tem que ter cuidado porque
fonte
Você pode usar
scipy
, o que é bastante simples:scipy.misc.derivative(func, x0, dx=1.0, n=1, args=(), order=3)
No seu caso:
fonte