acer

32348 Reputation

29 Badges

19 years, 329 days
Ontario, Canada

Social Networks and Content at Maplesoft.com

MaplePrimes Activity


These are replies submitted by acer

What have you done so far, for this homework question?

@Carl Love That's right, on all counts. But I have a hazy idea that issuing gc() explicitly may not always force a garbage-collection in modern versions the way it did some years back. I suspect that sometimes it does it when it wants to.

I suppose that, with enough calls to a Matrix initializer it might be quicker to Compile after burning the N parameter into the proc template. But that may be academic as far as optimality goes, since an in-place single procedure could walk a preformed empty Matrix and be compiled.

I left the extra procedure layer since then it had the same construction mechanism as the routine I wrote. But I was just curious about a different short way to generate the values from the indices. I have doubts that I proved much, performance-wise.

@gawati2611 Here another variant on a procedure which generates the entry value from an index pair.

Q:=proc(r::integer,c::integer,N::integer)
  local d::integer,t::integer;
  d:=c+r-2; t:=iquo(d*(d+1),2);
  `if`(d<N, t+`if`(d::even,c,r), N*(2*(d+1)-N)-t+1-`if`(d::even,r,c));
end proc:


# For example, second row for size N=6
seq(Q(2,j,6),j=1..6);
               3, 5, 8, 14, 17, 26

Matrix(3,(i,j)->Q(i,j,3));
                  [1  2  6]
                  [3  5  7]
                  [4  8  9]

And here is a worksheet, for fun.

[edit] Don't take the timings too seriously. If you wanted better performance for the Matrix construction then I expect that you could Compile a decent procedure which walked the entries of the Matrix in bands using loops, and acted in-place (thus avoiding overhead of calling a Matrix initializer procedure on each entry).

restart;

#
# This used indexing started from 0, which of course is
# accomodated merely by subtracting 1 from each passed index,
# as used below in the Matrix entry-generator.
#

P:=proc(r::integer,c::integer,N::integer)
  local d::integer,t::integer;
  d:=c+r; t:=iquo(d*(d+1),2);
  `if`(d<N, 1+t+`if`(d::even,c,r), N*(2*(d+1)-N)-t-`if`(d::even,r,c));
end proc:

# For example, second row for size N=6
seq(P(1,j-1,6),j=1..6);

3, 5, 8, 14, 17, 26

#
# If you prefer your indexing to start from 1,
# then it could be as follows:
#

Q:=proc(r::integer,c::integer,N::integer)
  local d::integer,t::integer;
  d:=c+r-2; t:=iquo(d*(d+1),2);
  `if`(d<N, t+`if`(d::even,c,r), N*(2*(d+1)-N)-t+1-`if`(d::even,r,c));
end proc:

# For example, second row for size N=6
seq(Q(2,j,6),j=1..6);

3, 5, 8, 14, 17, 26

Matrix(3,(i,j)->Q(i,j,3));

Matrix(3, 3, {(1, 1) = 1, (1, 2) = 2, (1, 3) = 6, (2, 1) = 3, (2, 2) = 5, (2, 3) = 7, (3, 1) = 4, (3, 2) = 8, (3, 3) = 9})

H:=(N::posint)->Matrix(N,(i,j)->P(i-1,j-1,N)):

H(2);

Matrix(2, 2, {(1, 1) = 1, (1, 2) = 2, (2, 1) = 3, (2, 2) = 4})

H(3);

Matrix(3, 3, {(1, 1) = 1, (1, 2) = 2, (1, 3) = 6, (2, 1) = 3, (2, 2) = 5, (2, 3) = 7, (3, 1) = 4, (3, 2) = 8, (3, 3) = 9})

H(6);

Matrix(6, 6, {(1, 1) = 1, (1, 2) = 2, (1, 3) = 6, (1, 4) = 7, (1, 5) = 15, (1, 6) = 16, (2, 1) = 3, (2, 2) = 5, (2, 3) = 8, (2, 4) = 14, (2, 5) = 17, (2, 6) = 26, (3, 1) = 4, (3, 2) = 9, (3, 3) = 13, (3, 4) = 18, (3, 5) = 25, (3, 6) = 27, (4, 1) = 10, (4, 2) = 12, (4, 3) = 19, (4, 4) = 24, (4, 5) = 28, (4, 6) = 33, (5, 1) = 11, (5, 2) = 20, (5, 3) = 23, (5, 4) = 29, (5, 5) = 32, (5, 6) = 34, (6, 1) = 21, (6, 2) = 22, (6, 3) = 30, (6, 4) = 31, (6, 5) = 35, (6, 6) = 36})

# author: Carl Love, (types specs added by acer)
ZigZag:= proc(i::integer,j::integer,n::integer)
 local d::integer;
 d:=i+j-1;
 `if`(d>n, thisproc(n+1-j,n+1-i,n)+(d-n)*(3*n-d),
      (d^2+1+(-1)^d*(d+1-2*j))/2);
end proc:
ZZ:=N->Matrix(N, (i,j)->ZigZag(i,j,N)):

LinearAlgebra:-Norm( H(10^2) - ZZ(10^2) );

0

# These routines can be sped up somewhat by compilation.
# Tming comparison to be taken very circumspectly, as
# garbage-collection cost may occur by ill-fortune here.

cP:=Compiler:-Compile(P):
cH:=(N::posint)->Matrix(N,(i,j)->cP(i-1,j-1,N)):
cZigZag:=Compiler:-Compile(ZigZag):
cZZ:=N->Matrix(N, (i,j)->cZigZag(i,j,N)):
LinearAlgebra:-Norm( cH(10^3) - cZZ(10^3) );

0.

a:='a':b:='b':c:='c':gc(): CodeTools:-Usage(cH(10^3)):

memory used=83.93MiB, alloc change=7.63MiB, cpu time=1.19s, real time=1.06s, gc time=0ns

a:='a':b:='b':c:='c':gc(): CodeTools:-Usage(cZZ(10^3)):

memory used=129.71MiB, alloc change=32.00MiB, cpu time=1.77s, real time=1.42s, gc time=551.00ms

a:='a':b:='b':c:='c':gc(): CodeTools:-Usage(cH(10^3)):

memory used=83.93MiB, alloc change=0 bytes, cpu time=1.35s, real time=1.16s, gc time=292.64ms

a:='a':b:='b':c:='c':gc(): CodeTools:-Usage(cZZ(10^3)):

memory used=129.71MiB, alloc change=32.00MiB, cpu time=1.96s, real time=1.45s, gc time=717.32ms

 

Download mattrav_ac3.mw

@Thomas Dean Yes, it is strange indeed that you would not mention at the beginning that it was for a specific x value.

@nm Your interpretation of what is going on is not correct.

If you do the parse without the eval (or statement option, which induces an evaluation) then the variable ode is assigned the unevaluated expression. That happens whether done at the top-level or inside a procedure while assigning to a local name. What gets assigned to name ode is the same in both cases.

What makes a difference is the degree of evaluation when that assigned name ode is subsequently passed as argument to another procedure -- such as dsolve. In the top-level case it is evaluated, and in the procedure local case it is not.

The difference is in how the assigned name ode is subsequently evaluated (or not) when passed around. Contrary to what you suggested, the difference is not the degree of evaluation during the assignment to the name ode.

The 1-level of locals within a procedure is clearly documented on the Help page for Topic procedure.

What is incorrect is your surmise, "...semantics of assignment to local variable is different than assignment to the variable when in global context". The difference is not in the assignment to the local name, but in how it gets subsequently evaluated when referenced/passed.

restart;

ode := :-parse("diff(y(x),x$2)=0"):

#
# In this top-case the name `ode` is assigned
# the unevaluated expression.
#
lprint(eval(ode, 1));

diff(y(x),x $ 2) = 0

lprint(ode);

diff(diff(y(x),x),x) = 0

f := proc()
  local ode;
  ode := :-parse("diff(y(x),x$2)=0");
  lprint(ode);
end proc:
f();

diff(y(x),x $ 2) = 0

trace(dsolve);

dsolve

# Look at the first line, at what gets passed in.
dsolve(ode):

{--> enter dsolve, args = diff(diff(y(x), x), x) = 0

<-- exit dsolve (now at top level) = y(x) = _C1*x+_C2}

# Look at the first line, at what gets called.
dsolve(eval(ode, 1)):

{--> enter dsolve, args = diff(y(x), x$2) = 0

Warning, it is required that the numerator of the given ODE depends on the highest derivative. Returning NULL.

<-- exit dsolve (now at top level) = }

g := proc()
  local ode;
  ode := :-parse("diff(y(x),x$2)=0");
  dsolve(ode);
end proc:
g():

{--> enter dsolve, args = diff(y(x), x$2) = 0

Warning, it is required that the numerator of the given ODE depends on the highest derivative. Returning NULL.

<-- exit dsolve (now in g) = }

 

Download parse_example2.mw

Which side buttons do you mean, left (palettes) or right (context-menu)?

Does it improve if you close the left panel and the right panel?

@AHSAN At lower working precision the floating-point evaluation of the expression (at different values of lambda) might suffer from roundoff error and inaccurate results might get be produced.

Presumably your expression is as you intended it.

You have asked about other rootfinding methods before (and been answered!). I see no reason to encourage you in such duplication of questioning, or to reinvent the wheel.

You are free to utilize your own numeric root-finding algorithms, and you might find the range lambda=0.4..0.85 helpful.

If I'm not mistaken, the original product expression P has -- as one of its multiplicands -- a 5th degree polynomial,
   57441.45187*lambda^5 - 174030.6883*lambda^4 + 209711.5508*lambda^3
   - 125674.0589*lambda^2 + 37467.33188*lambda - 4446.983589

which may be factored approximately to obtain this factor:
   lambda - 0.4632186949799427

@Jak So just use the red curve(s), and not the blue curve(s).

The red is for eq1=0, and the blue is for eq2=0.

They already (each) have a line style (dash, solid) that changes when eq1<eq2 or not.

I threw both the red and the blue. It is trivial to exclude either in the code I gave.

You can also restrict to any particular quadrant -- just specify the ranges and/or view.

For example, also using an alternate approach with an explicit solve, instead of an implicit plot, for eq1=0. You may wish to treat x[u]=0 specially, or exclude it, say with the view. I used a style dot instead of dash. Adjust as desired.

restart;

with(plots): with(plottools,transform):

r:=0.927: K:=1.8182*10^8:d[v]:=0.0038:d[u]:=2: delta:=1: p[m]:=2.5:
M:=10^4: p[e]:=0.4: d[e]:=0.1: d[t]:=5*10^(-9): omega:=2.042: b:=1000:
h[e]:=1000:h[u]:=1:h[v]:=10^4:

eq1 := r*d[t]*h[e]*x[u]^3+(r*h[e]*(-K*d[t]+d[t]*h[v]+d[e])
+r*p[e]*x[m])*x[u]^2+(r*h[e]*(-K*d[t]*h[v]-K*d[e]+d[e]*h[v])
+K*p[e]*(d[u]-r)*x[m])*x[u]-r*K*h[e]*d[e]*h[v]:

eq2 := (d[t]*x[u]+d[e])*(2*r*x[u]/K+d[u]*p[e]*x[m]*x[u]/((h[v]+x[u])
*(d[t]*x[u]+d[e])*(h[e]+p[e]*x[m]*x[u]/((h[v]+x[u])*(d[t]*x[u]+d[e]))))-r)
+d[u]*h[e]*x[u]*(p[e]*h[v]*x[m]/(h[v]+x[u])^2-d[t]*p[e]*x[m]*x[u]/((h[v]+x[u])
*(d[t]*x[u]+d[e])))/(h[e]+p[e]*x[m]*x[u]/((h[v]+x[u])*(d[t]*x[u]+d[e])))^2:

Digits:=40:

TL:=transform(proc(a,b)
                `if`(evalf(eval(eq1<eq2,[x[m]=a,x[u]=b])),
                     [a,b],[undefined,undefined]); end proc):
TU:=transform(proc(a,b)
                `if`(evalf(eval(eq1>=eq2,[x[m]=a,x[u]=b])),
                          [a,b],[undefined,undefined]); end proc):

P1:=implicitplot(eq1=0, x[m]=-1e3..1e3, x[u]=-3e8..3e8,
                 color=red, thickness=3,
                 grid=[151,51], gridrefine=0, crossingrefine=0):
PC:=display(TL(P1),
            display(TU(P1),overrideoption,linestyle=dot),
            labels=[x[n],x[u]], size=[400,400]):
PC;

display(transform((a,b)->[b,a])(PC),
        view=[0..2e8,0..500],
        labels=[x[u],x[m]], size=[400,400]);

P1:=plot([solve(eq1,x[u])],x[m]=0..460,color=red,thickness=3,adaptive=false,numpoints=1000):
PC:=display(TL(P1),
            display(TU(P1),overrideoption,linestyle=dot),
            labels=[x[n],x[u]], size=[400,400]):
PC;

display(transform((a,b)->[b,a])(PC),
        view=[0..2e8,0..500],
        labels=[x[u],x[m]], size=[400,400]);

 

Download eq1eq2_rev2.mw

@Jak I don't understand what you're saying, sorry.

In what I showed the red curve denotes eq1=0 and the blue curve denotes eq2=0, and their linestyle is solid when eq1<eq2 and dashed otherwise.

Could you explain more explicitly how that is not what you requested?

Is it just that you want the two linestyles reversed in purpose? That's a simple edit to the code I gave -- by just switching the instances of the linestyle override. eq1eq2_rev.mw 

Such a flip produces these:

The cube of the rhs of the first equation is not equal to the rhs of the second equation, so are you sure that you have transcribed it correctly?

You had them as,

  y = (sqrt(x) + 10)^(1/3) - (sqrt(x) - 10)^(1/3);

and

  y^3 = 20 - 3*(x - 100)^(2/3);

[edit] As member vv has observed, you may have written down the second equation wrongly, and intended to have written it instead as,

   y^3 = 20 - 3*(x - 100)^(1/3)*y;

Have you considered uploading and attaching a worksheet that reproduces your problem?

Attach the original document that contains all the relevant definitions (i(t), delta, sol4, and so on).

@gawati2611 Your example was exp(w*x*I) and you stated that x and w should be real-valued, and that you'd want the height to be taken as the modulus.

abs(exp(w*x*I)) assuming x::real, w::real;
                 1

evalc(abs(exp(w*x*I)));
                 1

(I mentioned this earlier, in my original Comment, for the very reason that I wanted to check with you that you understood this.)

You could contact Maplesoft Technical Support about this.

The OP also asked about floating-point error and using the Optimization package.

There is no general facility in that package for estimating quantity of the floating-point error, but there are options for controlling (bounding it). Depending on the method, there are options for specifying a tolerance for optimaility of the objective as well as a tolerance for maximal, absolute constraint violation. (See the Help pages.)

Apart from specifying those tolerances, you can also get additional printing of what value gets used for them (either specified, or as defaults).

Note that actual results may be more accurate (ie. smaller error) than the tolerance -- which is meant to serve as a bound, not an estimate.

Note that additional working precision (Digits) may be required in order to ensure that the tolerances are not met accidentally (wrongly) due to numeric round-off error.

Note that there may be a hard limit (16?) on the number of major iterations for some methods.

restart;

obj:=(x-2*y)/(5*x^2-2*x*y+2*y^2);
cond:=2*x^2-y^2+x*y=1;

(x-2*y)/(5*x^2-2*x*y+2*y^2)

2*x^2+x*y-y^2 = 1

infolevel[Optimization]:=6:

Digits:=10:  # default
fsol1:=Optimization:-Maximize(obj, {cond});
evalf[10]( sqrt(2)/4 - fsol1[1] );

NLPSolve: calling NLP solver

NLPSolve: using method=sqp

NLPSolve: number of problem variables 2

NLPSolve: number of nonlinear inequality constraints 0

NLPSolve: number of nonlinear equality constraints 1

NLPSolve: number of general linear constraints 0

NLPSolve: feasibility tolerance set to 0.1053671213e-7

NLPSolve: optimality tolerance set to 0.3256082241e-11

NLPSolve: iteration limit set to 50

NLPSolve: infinite bound set to 0.10e21

NLPSolve: trying evalhf mode

attemptsolution: number of major iterations taken 14

[.353553390593275063, [x = HFloat(0.8164965809123527), y = HFloat(-0.29885849069043535)]]

-0.1e-9

Digits:=24:
fsol2:=Optimization:-Maximize(obj, {cond});
evalf[24]( sqrt(2)/4 - fsol2[1] );

NLPSolve: calling NLP solver

NLPSolve: using method=sqp

NLPSolve: number of problem variables 2

NLPSolve: number of nonlinear inequality constraints 0

NLPSolve: number of nonlinear equality constraints 1

NLPSolve: number of general linear constraints 0

NLPSolve: feasibility tolerance set to 0.1e-11

NLPSolve: optimality tolerance set to 0.5248074602e-17

NLPSolve: iteration limit set to 50

NLPSolve: infinite bound set to 0.10e21

NLPSolve: trying evalf mode

attemptsolution: number of major iterations taken 15

[.353553390593273762200610, [x = .816496580927725973393146, y = -.298858490722684383537048]]

-0.188e-21

Digits:=30:
fsol3:=Optimization:-Maximize((x-2*y)/(5*x^2-2*x*y+2*y^2), {2*x^2 - y^2 + x*y=1},
                        optimalitytolerance=1e-29, feasibilitytolerance=1e-29,
                        iterationlimit=16);
evalf[30]( sqrt(2)/4 - fsol3[1] );

NLPSolve: calling NLP solver

NLPSolve: using method=sqp

NLPSolve: number of problem variables 2

NLPSolve: number of nonlinear inequality constraints 0

NLPSolve: number of nonlinear equality constraints 1

NLPSolve: number of general linear constraints 0

NLPSolve: feasibility tolerance set to 0.1e-28

NLPSolve: optimality tolerance set to 0.1e-28

NLPSolve: iteration limit set to 16

NLPSolve: infinite bound set to 0.10e21

NLPSolve: trying evalf mode

attemptsolution: number of major iterations taken 16

[.353553390593273762200422181053, [x = .816496580927726032732427201246, y = -.298858490722684508034628621562]]

-0.1e-29

 

Download Opt_userinfo.mw

First 164 165 166 167 168 169 170 Last Page 166 of 592