Assume I have
result = mynet1(input)
calculated_value1 = result
calculated_value2 = calculated_value1 * result
and I want to only derive result using backward, in the calculated_value2 expression, but not the inner result which comes from calculated_value1
Meaning, I want
calculated_value2.backward()
to refer to calculated_value1 as a constant, even though it depends on result, so that the gradient would only depend on result once, rather that on result^2.
Obviously, result.detach() won't do the trick, because then the entire expression would have no parameters to optimize.
How can I achieve the described behavior?
Clarification of intent:
I intend to implement section 13.5 of this book
In which delta depends on V, but is not being derived, while V itself IS being derived.
Also, if there is a more suitable name for this question, please tell me so that I could change it.
Related
I am doing control engineering and I often face problems of the type below and I want to know if there is a way to deal with this in sympy.
question:
tl:dr: I want to make a MatrixSymbol dependent on a scalar Symbol representing time, to allow differentiation w.r.t. time.
Actual problem: v(t)=[v1(t),v2(t),v3(t)] is a vector function of the time t and I want to calculate the Projection into the direction of v and it's time derivative. In the end I would love to get an expression of v, v.diff(t) and v.T (the transpose).
attempts:
I've tried different things and show the closest one:
This does the algebra I need, but I cannot take derivatives w.r.t. time
v = MatrixSymbol('v',3,1)
# here i'm building the terms I want
projection_v = v*sqrt(v.T*v).inverse()*v.T
orthogonal_v = Identity(3)-projection_v
orthogonal_v.as_explicit()
orthogonal_v shows the abstract equation form that I need. In the end - to check and see the result again, I'd also like to make it explicit and see the expression as a function of v[0,0], v[1,0], and v[2,0] for MatrixSymbol the function .as_explicit() does exactly that beginning with sympy version 1.10. (Thanks Francesco Bonazzi for pointing this out.)
The problem however is, that I cannot make these a function of t and take the derivative of projection_v w.r.t. the time t.
I also tried
t = Symbol('t',real=True,positive=True)
v1 = Function('v1',real=True)(t)
v2 = Function('v2',real=True)(t)
v3 = Function('v3',real=True)(t)
v_mat = FunctionMatrix(3,1,[v1,v2,v3]);
but it seems FunctionMatrix is meant to evaluate the functions directly instead of being an analog to the scalar Function.
Effectively I want to be able to calculate orthogonal_v.diff(t) and then see the component wise operations with something like orthogonal_v.diff(t).as_explicit(). Is this possible?
I'd like to use if operation in tensorflow, as I've learned tf.cond()should be used here. While I'm confused about what if i'd like to use only if operation instead else operation. For example:
a = tf.Constant(10)
b = tf.Constant(5)
for i in range(5):
tmp = tf.greater_equal(a,b)
result = tf.cond(tmp, lambda:tf.constant(i), None)
if result is not None:
return i
as above, I want to do nothing in else operation, while tf.cond() ask there has to be a value to return.Hope someone can provide some help.
To answer the actual question, if you understand the graph execution model of Tensorflow, you will see that after the conditional, your execution flow must converge again. Meaning that the operations you perform on the result of tf.cond must be technically possible independent of the branch taken in tf.cond. If they are dependent, they should be part of the tf.cond itself.
For the convergence to happen, you have to return same looking tensors from both branches. If you "don't want to do anything" in the else branch, you can just return some zero tensors or some reshaped input from there. What exactly makes sense, depends on your exact use case.
I am using a scipy.minimize function, where I'd like to have one parameter only searching for options with two decimals.
def cost(parameters,input,target):
from sklearn.metrics import mean_squared_error
output = self.model(parameters = parameters,input = input)
cost = mean_squared_error(target.flatten(), output.flatten())
return cost
parameters = [1, 1] # initial parameters
res = minimize(fun=cost, x0=parameters,args=(input,target)
model_parameters = res.x
Here self.model is a function that performs some matrix manipulation based on the parameters. Input and target are two matrices. The function works the way I want to, except I would like to have parameter[1] to have a constraint. Ideally I'd just like to give an numpy array, like np.arange(0,10,0.01). Is this possible?
In general this is very hard to do as smoothness is one of the core-assumptions of those optimizers.
Problems where some variables are discrete and some are not are hard and usually tackled either by mixed-integer optimization (working good for MI-linear-programming, quite okay for MI-convex-programming although there are less good solvers) or global-optimization (usually derivative-free).
Depending on your task-details, i recommend decomposing the problem:
outer-loop for np.arange(0,10,0.01)-like fixing of variable
inner-loop for optimizing, where this variable is fixed
return the model with the best objective (with status=success)
This will effect in N inner-optimizations, where N=state-space of your to fix-var.
Depending on your task/data, it might be a good idea to traverse the fixing-space monotonically (like using np's arange) and use the solution of iteration i as initial-point for the problem i+1 (potentially less iterations needed if guess is good). But this is probably not relevant here, see next part.
If you really got 2 parameters, like indicated, this decomposition leads to an inner-problem with only 1 variable. Then, don't use minimize, use minimize_scalar (faster and more robust; does not need an initial-point).
Say, I have an equation f(x) = x**2 + 1, I need to find the value of f(2).
Easiest way is to create a function, accept a parameter and return the value.
But the problem is, f(x) is created dynamically and so, a function cannot be written beforehand to get the value.
I am using cvxpy for an optimization value. The equation would look something like below:
x = cvx.Variable()
Si = [(cvx.square(prev[i] + cvx.sqrt(200 - cvx.square(x))) for i in range(3)]
prev is an array of numbers. There will be a Si[0] Si[1] Si[2].
How do i find the value of Si[0] for x=20?
Basically, Is there any way to substitue the said Variable and find the value of equation When using cvxpy ?
Set the value of the variables and then you can obtain the value of the expression, like so:
>>> x.value = 3
>>> Si[0].value
250.281099844341
(although it won't work for x = 20 because then you'd be taking the square root of a negative number).
The general solution to interpreting code on-the-fly in Python is to use the built-in eval() but eval is dangerous with user-supplied input which could do all sorts of nasty to your system.
Fortunately, there are ways to "sandbox" eval using its additional parameters to only give the expression access to known "safe" operations. There is an example of how to limit access of eval to only white-listed operations and specifically deny it access to the built-ins. A quick look at that implementation looks close to correct, but I won't claim it is foolproof.
The sympy.sympify I mentioned in my comment uses eval() inside and carries the same warning.
In parallel to your cvx versions, you can use lambda to define functions on the fly :
f=[lambda x,i=j : (prev[i] + (200 - x*x)**.5)**2 for j in range(3)] #(*)
Then you can evaluate f[0](20), f[1](20), and so on.
(*) the i=j is needed to fit each j in the associated function.
The following example is stated just for the purpose of precise definition of the query. Consider a recursive equation x[k+1] = a*x[k] where a is some constant. Now, is there an easier way or an existing method within sympy/numpy that does the following (i.e., gives an expression over a horizon for a given recursive equation):
def get_expr(init, num):
a = Symbol('a')
expr = init
for i in range(num):
expr = a*expr
return expr
x0 = Symbol('x0')
get_expr(x0,3)
Horizon above is 3.
I was going to suggest using SymPy's rsolve to try to find a closed form solution to your equation, but it seems that at least for this specific one, there is a bug that prevents it from working. See http://code.google.com/p/sympy/issues/detail?id=2943. Maybe if you really want to know for a more complicated expression you could try that. For this one, the closed form solution is just a**n*x0.
Aside from that, SymPy doesn't have any functions that would do this evaluation directly, but it does have some things that can help. There are some memoization decorators in sympy.utilities.memoization that are made for internal use, but should work just fine for external uses. They can help make your evaluation more efficient by caching the result of previous evaluations. You'll need to write the get_expr recursively for it to work effectively. Or you could just write your own cacher. It's not that complicated.