How to overcome "Variable returned by scilab argument function is incorrect" while using fsolve in scilab? - scilab

While solving one problem in the fluid mechanics topic, I came across a situation where I have to solve 4 non linear equation to get 4 unknown variable values. So, I used fsolve function in scilab to solve the equations. My code is as follows:
clc
clear
function f=F(x)
f(1)=x(1)-(0.4458*x(2)^(-2))
f(2)=x(3)-(0.26936*x(2)*(-1))
f(3)=(2.616*x(2))-(x(4)*x(1)^2)
f(4)=(0.316/(x(3)^(1/4)))
endfunction
function j=jacob(x)
j(1,1)=1;j(1,2)=0.8916*x(2)^(-3);j(1,3)=0;j(1,4)=0
j(2,1)=0;j(2,2)=0.26936*x(2)^(-2);j(2,3)=1;j(2,4)=0;
j(3,1)=-2*x(1)*x(4);j(3,2)=2.616;j(3,3)=0;j(3,4)=-1*x(1)^2;
j(4,1)=0;j(4,2)=0;j(4,3)=-2/x(3)/log(10);j(4,4)=(-0.5*x(4)^(-1.5))-(1/x(4)/log(10));
endfunction
x0=[1 1 2000 1];
[x,v,info]=fsolve(x0,F,jacob);
disp(x);
Error:
[x,v,info]=fsolve(x0,F,jacob);
!--error 98
Variable returned by scilab argument function is incorrect.
at line 17 of exec file called by :
exec('D:\Desktop files\Ajith\TBC\SCILAB code\Chapter_08\fsolve.sce', -1)
Details of the question:-
Actual question: Heated air at 1 atm and 35 degree C is to be transported in a 150m long circular plastic duct at a rate of 0.35 m3/s. If the head loss in the pipe is not to exceed 20m, determine the minimum diameter of the duct?
Book name: Fluid Mechanics: Fundamentals and Applications by Y.A.Cengel and J.M.Cimbala.
Page and question number: Page no.: 345, EXAMPLE 8-4
ISBN of the book: 0-07-247236-7
Textbook link: https://www.academia.edu/32439502/Cengel_fluid_mechanics_6_edition.PDF
In my code: x(1) is velocity, x(2) is the diameter, x(3) is the Reynolds number, x(4) is the friction factor
Expected answers: x(1)=6.24, x(2)=0.267, x(3)=100800, x(4)=0.0180.
My thoughts about the error:
What is see is that if I change the power of the variable such as from 0.5 to 2 or -1.5 to 1, answer is calculated and displayed. So, the problem is somewhere around the power of the variables used.
Also the initial values of the x, I saw that for some initial value there is no error and I got the output.

After reading the description of the problem in the book, there is only one non-trivial equation (the third) all other give directly other unknowns as functions of D. Here is the code to determine the diameter:
function out=F(D)
V = 0.35/%pi/D^2*4;
Re = V*D/1.655e-5;
f = 20/(150/D*V^2/2/9.81);
out = 1/sqrt(f) + 2*log10(2.51/Re/sqrt(f));
endfunction
D0 = 1;
[D,v,info]=fsolve(D0,F);
disp(D)

Related

Solve equation of mean field theory with Scilab

i try to evaluate the equation =tanh(zJ/k_B T)
using newton rampson method. when i run the program i got an error:
plot: Wrong size for input arguments #2 and #3: Incompatible
dimensions.
and a blank graph. plz help me out whats the problem in my code.
z=4\\ no. of nearest neighbours
m=1;//value of J/K
T=[0.1:0.1:8]\\value of temerature
s(1)=-0.5;//initial value
n=100;\\no. of iterations
for i=1:n \\ running of for loop
f= s(i)-tanh(z*m*s(i)./T);//equation of mean field theory
l=derivat(f); // derivative of f
s(i+1)=s(i)-(f/l); // implementation of newton rampson method
if abs(s(i+1)-s(i)) <= 10^-8 then
end
s(i)=s(i+1)
i=i+1;//increment in i values
end
plot(T,s,'.r')
What I understand after reading about equation of mean field theory is that you want to solve s=tanh(zms/T) for different values of T then plot s versus T. Here is how you can do it in Scilab (no need to code Newton's method yourself you can use fsolve (see the help page of this function)
function out = eq(s,T)
out = s-tanh(z*m*s/T)
end
z=4;
m=1;
T=[0.1:0.1:8];
for i=1:length(T)
s(i) = fsolve(-0.5,list(eq,T(i)))
end
clf
plot(T,s)
xlabel T
ylabel s

Reinforcement learning SARSA algorithm decreases values over time

I am currently trying to implement the SARSA algorithm, as described in Sutton, Barto "Reinforcement Learning, An Introduction" on a gridworld with a windy upstream. (I am using the same environment as Sutton, Barto - p.130.) Basically, there are 70 fields and one can move in four directions: up, down, left or right. On some states, a wind will cause the movement to shift up one step. The reward is -1 for each timestep, where the goal has not been reached.
I implemented the environment and everything seems to be working fine. However, the learning algorithm does not seem to work. The authors of the book claim that when using certain parameters, the algorithm converges to a near optimal solution after about 150 episodes learned. This is not the case for my code (written in Julia v1.1.0)
g = GridWorld()
α = 0.5
γ = 1
ϵ = 0.1
Q = zeros(70,4)
for episode in 1:100000
isDone = false
S = g.start
A = eps_greedy(Q,ϵ,S)
while !isDone
(R,isDone) = action(g,A)
S´ = g.position
A´ = eps_greedy(Q,ϵ,S´)
Q[S,A] += α*(R + γ* Q[S´,A´] - Q[S,A])
S = S´
A = A´
end
end
The object g stores the current state, which gets changed according to action A when calling action(g,A). The function eps_greedy(Q,epsilon,S) just takes a current state and chooses an epsilon-greedy action from the action-value function Q.
The problem is: The longer I train, the lower the action values, stored in Q, will get. For example, training for about 2000 episodes, the action values of the starting state are all similar at approximately -950. Training for 20000 will yield action values of around -10000.
I don't think this is supposed to happen, but I am not quite sure what causes the problem. Any help would be greatly appreciated!

Iteration / Maximization Excel solver in R

I am trying to do a maximization in R that I have done previously in Excel with the solver. The problem is that I don't know how to deal with it (i don't have a good level in R).
let's talk a bit about my data. I have 26 Swiss cantons and the Swiss government (which is the sum of the value of the 26 cantons) with their population and their "wealth". So I have 27 observatios by variable. I'm not sure that the following descriptions are useful but I put them anyway. From this, I calculate some variables with while loops. For each canton [i]:
resource potential = mean(wealth2011 [i],wealth2012 [i],wealth2013 [i])
population mean = mean(population2011 [i],population2012 [i],population2013 [i])
resource potential per capita = 1000*resource potential [i]/population [i]
resource index = 100*resource potential capita [i]/resource potential capita [swiss government]
Here a little example of the kind of loops I used:
RI=0
i = 1
while(i<28){
RI[i]=resource potential capita [i]/resource potential capita [27]*100
i = i+1
}
The resource index (RI) for the Swiss government (i = 27) is 100 because we divide the resource potential capita of the swiss government (when i = 27) by itself and multiply by 100. Hence, all cantons that have a RI>100 are rich cantons and other (IR<100) are poor cantons. Until here, there was no problem. I just explained how I built my dataset.
Now the problem that I face: I have to create the variable weighted difference (wd). It takes the value of:
0 if RI>100 (rich canton)
(100-RI[i])^(1+P)*Pop[i] if RI<100 (poor canton)
I create this variable like this: (sorry for the weakness of the code, I did my best).
wd=-1
i = 1
a = 0
c = 0
tot = 0
while(i<28){
if(i == 27) {
wd[i] = a
} else if (RI[i] < 100) {
wd[i] = (100-RI[i])^(1+P)*Pop[i]
c = wd[i]
a = a+c
} else {
wd[i]= 0
}
i = i+1
}
However, I don't now the value of "p". It is a value between 0 and 1. To find the value of p, I have to do a maximization using the following features:
RI_26 = 65.9, it is the minimum of RI in my data
RI_min = 100-((x*wd [27])/((1+p)*z*100))^(1/p), where x and z are fixed values (x = 8'677, z = 4'075'977'077) and wd [27] the sum of wd for each canton.
We have p in two equation: RI_min and wd. To solve it in Excel, I used the Excel solver with the following features:
p_dot = RI_26/RI_min* p ==> p_dot =[65.9/100-((x* wd [27])/((1+p)*z*100))^(1/p)]*p
RI_26 = RI_min ==>65.9 =100-((x*wd [27])/((1+p)*z*100))^(1/p)
In Excel, p is my variable cell (the only value allowed to change), p_dot is my objective to define and RI_26 = RI_min is my constraint.
So I would like to maximize p and I don't know how to do this in R. My main problem is the presence of p in RI_min and wd. We need to do an iteration to solve it but this is too far from my skills.
Is anyone able to help me with the information I provided?
you should look into the optim function.
Here I will try to give you a really simple explanation since you said you don't have a really good level in R.
Assuming I have a function f(x) that I want to maximize and therefore I want to find the parameter x that gives me the max value of f(x).
First thing to do will be to define the function, in R you can do this with:
myfunction<- function(x) {...}
Having defined the function I can optimize it with the command:
optim(par,myfunction)
where par is the vector of initial parameters of the function, and myfunction is the function that needs to be optimized. Bear in mind that optim performs minimization, however it will maximize if control$fnscale is negative. Another strategy will be to change the function (i.e. changing the sign) to suit the problem.
Hope that this helps,
Marco
From the description you provided, if I'm not mistaken, it looks like that everything you need to do it's just an equation.
In particular you have the following two expressions:
RI_min = 100-((x*y)/((1+p)*z*100))^(1/p)
and, since x,y,z are fixed, the only variable is p.
Moreover, having RI_26 = RI_min this yields to:
65.9 =100-((x*y)/((1+p)*z*100))^(1/p)
Plugging in the values of x,y and z you have provided, this yields to
p=0.526639915936052
I don't understand what exactly you are trying to maximize.

OpenMDAO 1.2.0 implicit component

I new to OpenMDAO and I'm still learning how to formulate the problems.
For a simple example, let's say I have 3 input variables with the given bounds:
1 <= x <= 10
0 <= y <= 10
1 <= z <= 10
and I have 4 outputs, defined as:
f1 = x * y
f2 = 2 * z
g1 = x + y - 1
g2 = z
my goal is to minimize f1 * g1, but enforce the constraint f1 = f2 and g1 = g2. For example, one solution is x=3, y=4, z=6 (no idea if this is optimal).
For this simple problem, you can probably just feed the output equality constraints to the driver. However, for my actual problem it's hard to find an initial starting point that satisfy all the constraints, and as the result the optimizer failed to do anything. I figure maybe I could define y and z as states in an implicit component and have a nonlinear solver figure out the right values of y and z given x, then feed x to the optimization driver.
Is this a possible approach? If so, how will the implicit component look like in this case? I looked at the Sellar problem tutorial but I wasn't able to translate it to this case.
You could create an implicit component if you want. In that case, you would define an apply_linear method in your component. That is done with the sellar problem here.
In your case since you have a 2 equation set of residuals which are both dependent on the state variables, I suggest you create a single array state variable of length 2, call it foo (I used a new variable to avoid any confusion, but name it whatever you want!). Then you will define two residuals, one for each element of the residual array of the new state variable.
Something like:
resids['foo'][0] = params['x'] * unknowns['foo'][0] - 2 * unknowns['foo'][1]
resids['foo'][1] = params['x'] + unknowns['foo'][0] - 1 - unknowns['foo'][1]
If you wanted to keep the state variable names separate you could, and it will still work. You'll just have to arbitrarily assign one residual equation to one variable and one to the other.
Then the only thing left is to add a non linear solver to the group containing your implicit component and it should work. If you choose to use a newton solver, you'll either need to set fd_options['force_fd'] = True or define derivatives of your residuals wrt all params and state variables.

Calculate the length of a segment of a quadratic bezier

I use this algorithm to calculate the length of a quadratic bezier:
http://www.malczak.linuxpl.com/blog/quadratic-bezier-curve-length/
However, what I wish to do is calculate the length of the bezier from 0 to t where 0 < t < 1
Is there any way to modify the formula used in the link above to get the length of the first segment of a bezier curve?
Just to clarify, I'm not looking for the distance between q(0) and q(t) but the length of the arc that goes between these points.
(I don't wish to use adaptive subdivision to aproximate the length)
Since I was sure a similar form solution would exist for that variable t case - I extended the solution given in the link.
Starting from the equation in the link:
Which we can write as
Where b = B/(2A) and c = C/A.
Then transforming u = t + b we get
Where k = c - b^2
Now we can use the integral identity from the link to obtain:
So, in summary, the required steps are:
Calculate A,B,C as in the original equation.
Calculate b = B/(2A) and c = C/A
Calculate u = t + b and k = c -b^2
Plug these values into the equation above.
[Edit by Spektre] I just managed to implement this in C++ so here the code (and working correctly matching naively obtained arc lengths):
float x0,x1,x2,y0,y1,y2; // control points of Bezier curve
float get_l_analytic(float t) // get arclength from parameter t=<0,1>
{
float ax,ay,bx,by,A,B,C,b,c,u,k,L;
ax=x0-x1-x1+x2;
ay=y0-y1-y1+y2;
bx=x1+x1-x0-x0;
by=y1+y1-y0-y0;
A=4.0*((ax*ax)+(ay*ay));
B=4.0*((ax*bx)+(ay*by));
C= (bx*bx)+(by*by);
b=B/(2.0*A);
c=C/A;
u=t+b;
k=c-(b*b);
L=0.5*sqrt(A)*
(
(u*sqrt((u*u)+k))
-(b*sqrt((b*b)+k))
+(k*log(fabs((u+sqrt((u*u)+k))/(b+sqrt((b*b)+k)))))
);
return L;
}
There is still room for improvement as some therms are computed more than once ...
While there may be a closed form expression, this is what I'd do:
Use De-Casteljau's algorithm to split the bezier into the 0 to t part and use the algorithm from the link to calculate its length.
You just have to evaluate the integral not between 0 and 1 but between 0 and t. You can use the symbolic toolbox of your choice to do that if you're not into the math. For instance:
http://integrals.wolfram.com/index.jsp?expr=Sqrt\[a*x*x%2Bb*x%2Bc\]&random=false
Evaluate the result for x = t and x = 0 and subtract them.

Resources