How to improve accuracy in fsolve?

Hello to everyone,
I am unfamiliar with MATLAB software and I am trying to solve some nonlinear equations. The problem that I have is that the results are not accurate enough. I don't have any initial guess, but I know that the results must be between 0 and pi/2 rads. Any idees?
f=@(a) [(4/pi)*(1-2*cos(a(1))+2*cos(a(2))-2*cos(a(3))+2*cos(a(4)))-0.5;
(4/(5*pi))*(1-2*cos(5*a(1))+2*cos(5*a(2))-2*cos(5*a(3))+2*cos(5*a(4)));
(4/(7*pi))*(1-2*cos(7*a(1))+2*cos(7*a(2))-2*cos(7*a(3))+2*cos(7*a(4)));
(4/(17*pi))*(1-2*cos(17*a(1))+2*cos(17*a(2))-2*cos(17*a(3))+2*cos(17*a(4)))];
[r]=fsolve(f,[1 1 1 1])
(4/pi)*(1-2*cos(r(1))+2*cos(r(2))-2*cos(r(3))+2*cos(r(4)))-0.5
(4/(5*pi))*(1-2*cos(5*r(1))+2*cos(5*r(2))-2*cos(5*r(3))+2*cos(5*r(4)))
(4/(7*pi))*(1-2*cos(7*r(1))+2*cos(7*r(2))-2*cos(7*r(3))+2*cos(7*r(4)))
(4/(17*pi))*(1-2*cos(17*r(1))+2*cos(17*r(2))-2*cos(17*r(3))+2*cos(17*r(4)))

1 Comment

The equations in f cannot distinguish between a(1) and a(3), or between a(2) and a(4) .

Sign in to comment.

 Accepted Answer

fsolve cannot limit the range of values.
fzero can limit the range of variables but only for a single function in one variable.
vpasolve can limit the range of values.
You can often get useful results by minimizing sum of f squared over a range as fmincon can handle range constraints

5 Comments

Call the initial set of equations EQN1.
It is easy to solve the first equation EQN1(1) for a(1) in terms of a(2), a(3), a(4). You can substitute that a(1) into the other equations and simplify, giving equations EQN2 for which the first value should be theoretically 0 (but might not simplify to that without help.)
Then you can solve the (new) second equation EQN2(2) for a(2) in terms of a(3), a(4). This might be a bit more difficult. Depending on the assumption information you provide, you will get either 4 or 8 solutions.
You can then go through each of the solutions for a(2) one at a time. For any one of them, substitute the individual solution into EQN2(3:end) to produce a new system of equations EQN3. This new equation will be essentially impossible to solve for a(3) or a(4) because it will be too complicated.
However, these EQN3 equations are now reduced down to equations in two variables, with known bounds on the solutions. You can now use graphical techniques to plot them and hope to see intersections that both happen to be 0. But there are places where there is a division by 0, so in practice you are not likely to find solutions.
What you can do from there is construct EQN4 = EQN3(1)^2 + EQN3(2)^2 -- a single equation in two variables. It should be 0 in exactly the places where the individual equations are both solved. It will never be negative (in this situation.) You can now do plotting a bit more easily.
In my testing, I find that there are locations that graphically appear to be 0 for EQN4, but are not really 0. A few of the places are below 1/50 . I have not been able to track yet to determine whether there are any true 0's in the first of the potential solutions; I might have to go into the next potential solution for a(2)
There are solutions near to the 20 locations.
In the list below, values that are very similar in the same column, are potentially theoretically the same value (e.g., same a(1) value with different a(2) values.); I did not do the experiment of substituting to cross-checking that.
0.129731796069698 0.940291782884622 0.651264645259325 0.465245158372017
0.129731802354687 0.465245134402887 0.651264658517594 0.940291798560176
0.228036235102928 0.606081795216662 0.809568247156701 1.00227510922701
0.228036249261262 1.00227513115422 0.809568264689928 0.606081766638158
0.313215812470401 1.19345827142967 1.0387937399123 0.665658508445344
0.313215818595677 0.665658500745977 1.0387937496734 1.19345825434456
0.423201748896644 1.45258038211177 1.1570289093431 0.46849443031859
0.423201765974992 0.468494451112171 1.1570289248585 1.45258038262956
0.651264644774352 0.940291781007099 0.129731791941977 0.46524512400967
0.65126465887644 0.465245125708235 0.129731792674384 0.94029178401124
0.809568252057574 1.00227513979009 0.228036242146361 0.60608177196509
0.809568296787102 0.606081765677461 0.228036268134433 1.00227511902445
0.996298433534377 0.956610699801552 1.12078425696144 1.47219047490911
0.99629845153618 1.47219047250849 1.12078426392851 0.956610735918245
1.03879372194761 0.665658483725666 0.313215830539873 1.19345825474443
1.03879373161139 1.19345825752266 0.313215806933001 0.66565848000289
1.12078425648552 1.47219047214067 0.996298429419116 0.956610706389639
1.12078426553805 0.95661073610026 0.996298446769472 1.47219047389983
1.15702890772427 1.45258039134833 0.423201727920535 0.468494430439295
1.15702891729818 0.468494467331498 0.423201769633769 1.45258037686134
I would like to thank you for your time and help. I would prefer to work with the functions that are already build in the matlab software.
To get this list of 20 approximate solutions, I used some software that I wrote in MATLAB. I formed the sum of squares of the original equations, and then run minimizers on the result, starting from many many many different locations.
You could do the same sort of thing: if you were to construct a 4D grid from 0:0.1:pi/2 and use the 50000 or so resulting 4D points as starting points for fmincon() and look for the places that get you a function value close to 0. Yes, that does take a bunch of computation, but it gets the job done.
Thank you for your help and time. I managed to find a method.

Sign in to comment.

More Answers (1)

There are multi-solutions with high enough accurancy, even given the range limition in [0, pi/2]:
1:
a1: 0.996298496311242
a2: 0.956610794085768
a3: 1.12078428609661
a4: 1.47219048531321
feval:
-1.58206781009085E-14
1.27222187258541E-15
-4.64461953483561E-15
-1.99564215307515E-16
2:
a1: 0.423201820072776
a2: 1.45258039750964
a3: 1.15702893242895
a4: 0.468494500989183
feval:
2.22044604925031E-15
-4.63654193564459E-15
7.59294323955735E-15
7.45663375320891E-15
3:
a1: 1.15702893242895
a2: 0.468494500989183
a3: 0.423201820072776
a4: 1.45258039750964
feval:
2.22044604925031E-15
-4.69308512998172E-15
7.59294323955735E-15
7.46702772275618E-15

4 Comments

Also
A1 = .78451894548220254322e-1
A2 = .93410371642501077229
A3 = 1.5575352805569076563
A4 = 1.4585657816429797632
I would like to thank you for your time and help. Which function have you used for the results above?
Alex used a commercial package to find the roots. I do not know what algorithm it is using, but it does find good solutions quickly.
For this list of A1, A2, A3, A4 values, I used the approach I described above in https://www.mathworks.com/matlabcentral/answers/515215-how-to-improve-accuracy-in-fsolve#comment_820992 to find EQ4 in two variables, and then I found a numeric solution for A3 and A4, and then back substituted to find A1 and A2 and then cross-checked. I did the work in Maplesoft's Maple software, but I think you might be able to do the same thing in MATLAB (not sure; MATLAB gives up on roots of symbolic nonlinear equations relatively easily.)
Thank you both for your help and time. I managed to find a method.

Sign in to comment.

Categories

Find more on Programming in Help Center and File Exchange

Products

Release

R2019b

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!