I have a function f(x,a) where 'x' is a variable and 'a' is a parameter. I want creat a function F(x) that is a sum of f(x,a) for a range of parameter 'a', for instance:
F(x) = f(x,a1) + f(x,a2) + f(x,a3) + ... + f(x,aN) but how I have a large range for 'a' (a=[a1,a2,a3,...,aN]) I want to write a program for this but I don't now how. For instance:
import numpy as np
# Black-Body radiation equation: 'x' is related to frequency and 'a' is related to temperature
def f(x,a):
return x**3/(np.exp(a*x) - 1)
# range for parameter a:
a = [1000,2000,3000,4000,5000,6000]
# Superposition of spectrum
def F(x):
return f(x,a[0]) + f(x,a[1]) + f(x,a[2]) + f(x,a[3]) + f(x,a[4]) + f(x,a[5])
The last line for function F(x) isn't very smart, so I tried make a loop in the above sum with sum() function
def F(x):
spectrum = []
for i in a:
spectrum = sum(f(x,i))
return spectrum
But as I don't have much experience with Python this doesn't work and I got the error:
import matplotlib.pyplot as plt
x = np.linspace(0,100,500)
plt.plot(x,F(x))
plt.show()
# ValueError: x and y must have same first dimension, but have shapes (500,) and (1,)
Does anyone know how to do this? thank you very much
From what i understand, this should do the job:
def F(x):
return sum(f(x, _a) for _a in a)
The thing I do in the sum() function is called list comprehension, feel free to look this Python feature if you are interested by Python coding: it is very powerful.
Related
I'd like to write a program in Python where user define a deegre of polynomial and coefficients (a,b,c). When program create a polynomial expression with this data I'd like to use it like function because I need this to other operations. How can i get it? For example when I have polynomial= x^n+a^n-1+b^n-2+c^-3 I'd like to use it in polynomial(x) to calculate value.
Now the creating polynomial method looks:
def polynomial(n,a,b,c):
return a*x**n+b*x**3-c*x
class Polynomial:
def __init__(self, coeficents, degrees=None):
if degrees = None:
self.degree = list(reversed(range(len(coeficents))))
else:
self.degree = degrees
self.coeficents = coeficents
def __call__(self, x):
print(self.coeficents)
print(self.degree)
return sum([self.coeficents[i]*x**self.degree[i] for i in range(len(self.coeficents))])
p = Polynomial([1,2,4],[10,2,0])
print(p(2))
This will compute the polynomial x^10 + 2x^2 + 4 at x = 2. It should be very clear how to use with your example.
The best strategy is not to pass in n, but you will need to pass in x. You should instead pass the coefficients in as a list. You don't need to pass in n as it is calculated from the length of the list.
def poly(coefs, x):
result=0
N=len(coefs)
n=0
while N-n>0:
result+=coefs[n]*(x**(N-n-1))
n+=1
return result
So if you want to calculate, for example x^2 + 3x -5 where x=5, you would use this line:
print(poly([1,3,-5], 5))
For context, I am essentially using a numerical integrator that takes in a set of differential equations defined as functions. A large set of these functions follow a regular pattern and I would like to define them in a loop (or whatever is the most suitable way). For example;
#system coordinates
s = [y1,y2]
#system equations
def e1(s):
x1 = s[1]**2 + 1
return x1
def e2(s):
x1 = s[2]**2 + 2
return x1
#equations of motion
eom = [e1,e2]
Not all of the functions will follow the exact pattern, for those that do though ideally I need something like,
def en(s)
x1 = s[n]**2 + n
return x1
where it is possible to iterate over a range of 'n' values. Thanks for any advice.
Why not simply use a second parameter in your function like so:
def en(s, n)
x1 = s[n]**2 + n
return x1
result = []
for i in range(100): # 100 is just for illustration purposes..
result[0] = en(s, i) # you do not have to store them in a list. just an example
I would use partial, wich bind values to functions arguments:
import functools
def e1(s, n, v1, v2):
x1 = s[n]**v1 + v2
return x1
[functools.partial(e1, n=i, v1=2, v2=1) for i in range(10)] # this was your first example
#your second example
[functools.partial(e1, n=n, v1=2, v2=n) for n in range(10)]
I'm a coding newcomer and I'm trying to work with Bokeh. Newcomer to StackOverflow too, so please tell me if I did something wrong here.
I'm playing with this example from Bokeh website and I ran into a problem. When the x values are set, as in the example, using np.linspace, I'm able to use the interact and play with the update function. But, if I change x to a list, using range(), then I get this error: TypeError: can only concatenate list (not "float") to list. As I understand it, the problem lies in "x + phi", since x is a list and phi is a float.
I get that it's not possible to concatenate a list with a float, but why is it only when I use a numpy.ndarray that Python understands that I want to modify the function that controls the y values?
Here is the code (I'm using Jupyter Notebook):
x = np.linspace(0,10,1000)
y = np.sin(x)
p = figure(title="example", plot_height=300, plot_width=600, y_range=(-5,5))
r = p.line(x, y)
def update(f, w=1, A=1, phi=0):
if f == "sin": func = np.sin
elif f == "cos": func = np.cos
elif f == "tan": func = np.tan
r.data_source.data["y"] = A * func(w * x + phi)
push_notebook()
show(p, notebook_handle=True)
interact(update, f=["sin", "cos", "tan"], w=(0,100), A=(1,5), phi=(0,20, 0.1))
Yes, please compare your numpy documentation with the documentation of lists: https://docs.python.org/3.6/tutorial/datastructures.html
You can also play with the following code:
from numpy import linspace
a = linspace(2, 3, num=5)
b = range(5)
print(type(a), a)
print(type(b), b)
print()
print("array + array:", a + a)
print("list + list:", b + b)
print(a + 3.14159)
print(b + 2.718) # will fail as in your example, because it is a list
My advise is to not mix lists and arrays if there is no other good reason to do so. I personally often cast function arguments to arrays if necessary:
def f(an_array):
an_array = numpy.array(an_array)
# continue knowing that it is an array now,
# being aware that I make a copy of an_array at this point
I am now programming on BFGS algorithm, where I need to create a function with a doulbe sum. I need to return a FUNCTION but not a number, so something like sum+= is not acceptable.
def func(X,W):
return a function of double sum of X, W
A illustrative example:
X = np.array([[1,1,1,1],[2,2,2,2],[3,3,3,3],[4,4,4,4],[5,5,5,5]])
W = np.array([[1,1,1,1],[2,2,2,2],[3,3,3,3]])
I want to get a function that, for each instance X[i] in X, and for each W[j] in W, return a function of the sum of numpy.dot(X[i],W[j]). For example, X[1] dot W[2] shoulde be 2*3+2*3+2*3+2*3
----------This contend is edited by me:-------------
When I saw the answers provided below, I think my question is not clear enough. Actually, I want to get a function:
Func = X[0]W[0]+X[0]W[1]+X[0]W[2]+ X[1]W[0]+X[1]W[1]+X[1]W[2]+
X[2]W[0]+X[2]W[1]+X[2]W[2]+ X[3]W[0]+X[3]W[1]+X[3]W[2] +
X[4]W[0]+X[4]W[1]+X[4]W[2]
-------------------end the edited content--------------
If I only got one dimension of W, the problem is easy by using numpy.sum(X,W).
However, how can I return a function of two sums with Python?
If you want to return the function f(i,j) -> X[i].W[j] :
def func(X,W):
def f(i,j): return np.dot(X[i],W[j])
return f
will work.
EDIT:
The VALUE you name Func in your edit is computed by sum([np.dot(x,w) for x in X for w in W]) or, more efficient, np.einsum('ij,kj->',X,W) .
if you want to return the FUNCTION that return Func, you can do it like that :
def func(X,W):
Func=np.einsum('ij,kj->',X,W)
return lambda : Func
Then f=func(X,W); print(f()) will print 360, the value named Func in your example.
If I got your question right, this should do exactly what you want (python-2.7):
import numpy as np
def sample_main():
X = np.array([[1,1,1,1],[2,2,2,2],[3,3,3,3],[4,4,4,4],[5,5,5,5]])
W = np.array([[1,1,1,1],[2,2,2,2],[3,3,3,3]])
f = lambda i, j : reduce (lambda a, b: a+b, map(lambda x, w: x*w, X[i], W[j]), 0)
return f
if __name__ == '__main__':
f = sample_main()
print (f(0, 0))
Just replace the sample_main function with your function that takes X and W.
Actually, I want to implement L_BFGS algorithm in my Python code. Inspired by the two answers provided by #B.M. and #siebenschlaefer, I figure out how to implement in my code:
func = np.sum(np.sum(log_p_y_xz(Y[i][t], Z[i], sigma_eta_ti(X[i],w[t],gamma[t]))+log_p_z_x(alpha, beta, X[i]) for t in range(3)) for i in range (5))
Please do not mind the details of the formula, what I want to say is that, I use two sum here and just using i in rage (5) and t in range (3) to tell the code do the sums.
Thanks again for the answers provided by #B.M. and #siebenschlaefer!!
I want to have some sort of reference to a function but I do not know if I need to use a def f(x) or a lambda of some kind.
For instance I'd like to print f(3) and have it output 9a, or is this not how python works?
Second question: Assuming I have a working function, how do I return the degree of it?
To create a function, you define it. Functions can do anything, but their primary use pattern is taking parameters and returning values. You have to decide how exactly it transforms parameters into the return value.
For instance, if you want f(x) to return a number, then a should also be a numeric variable defined globally or inside the function:
In [1]: def f(x):
...: a = 2.5
...: return a * x**2
...:
In [2]: f(3)
Out[2]: 22.5
Or maybe you want it to return a string like this:
In [3]: def f(x):
...: return str(x**2) + 'a'
...:
In [4]: f(3)
Out[4]: '9a'
You have to specify your needs if you need more help.
EDIT: As it turns out, you want to work with polynomials or algebraic functions as objects and do some algebraic stuff with them. Python will allow doing that, but not using standard data types. You can define a class for a polynomial and then define any methods or functions to get the highest power or anything else. But Polynomial is not a built-in data type. There may be some good libraries defining such classes, though.
Python (and most other computer languages) don't do algebra, which is what you'll need if you want symbolic output like this. But you could have a function f(a,x) which returns the result for particular (numerical) values of a:
def f(a, x):
return a*x*x
But if you want a program or language which actually does algebra for you, check out sympy or commercial programs like Mathematica.
If you are just working with polynomials, and you just need a data structure which deals well with them, check out numpy and its polynomial class.
I normally use lambda for short and simple functions:
f = lambda a, x: a * x**2
here a and x are parameters of my function. You need to enter a and x
f(2,4)
If you want a as a constant parameter eg. a=2:
f = lambda x: 2 * x**2
f(5)
if you have a list of input values of x, you can combine map with lambda.
it is straighforward and easily readable.
(*map(lambda x: 3 * x**2, [1,2,3,4]),)
or
list(map(lambda x: 3 * x**2, [1,2,3,4])
cheers!
def func():
print "F(x) = 2x + 3"
x = int(raw_input('Enter an integer value for x: '))
Fx = 2 * x + 3
return Fx
print func()
have fun :)
Cheese,
you can use the def function in Python to create a math function, you could type this:
def f(x):
return(2x + (3 + 3) * 11 + 88) # <- you could make your own function.
print(f(3))
Log:
220
Like THAT
or in this:
def f(a, x):
return((a + x) ** (a * x))
then...
print(f(1, 2))
Log...
6