acer

32363 Reputation

29 Badges

19 years, 332 days
Ontario, Canada

Social Networks and Content at Maplesoft.com

MaplePrimes Activity


These are replies submitted by acer

@herclau Try this (Linux/Unix file/directory paths, similar to your code),

with(ImageTools):

plotsetup(default);

img := Matrix(ToGrayscale(Read(cat(kernelopts(datadir),
                                   "/images/FingerPrint.jpg")))):

vsize,hsize:=op(1,img);

P:=plots:-textplot([1, .5, "take from A"], align = {above, right},
                   font = [TIMES,ROMAN,16], axes = none):

plotsetup('jpeg','plotoutput'="text1.jpg",
          'plotoptions'=cat("height=",vsize+6+4,",width=",hsize+5+5));

P; # Wait until this gets exported and written to OS! How long? It depends...

Threads:-Sleep(3): # This waits long enough, on my host. YMMV.

T := Read("text1.jpg"):

correctedT := rtable_redim(T[1+6 .. (-1)-4,
                           1+5 .. (-1)-5, 1 .. -1],
                           1 .. vsize, 1 .. hsize, 1 .. 3):

View(correctedT);

newQ := ImageTools:-Mask(img, ToGrayscale(correctedT)):

View(newQ);

I made a change to mask with ToGrayscale(correctedT), because your example uses a gray scale image for the background.

@herclau What dimensions did you use for creating text1.jpg?

Before I applied `redim`, I created my "text" jpg image file in this way,

plotsetup('jpeg','plotoutput'=tempfile,'plotoptions'=cat("height=",vsize+6+4,
                                                         ",width=",hsize+5+5));

What I was trying to do was to stretch the "text" image, when exporting it, by some amounts that would (hopefully) match the whitespace borders. Above, vsize and hsize are the dimensions of the background image onto which I overlaid the "text" image.

Maybe you could attach your sample image and text plot command that you want, and we could work out the commands in full.

@herclau What dimensions did you use for creating text1.jpg?

Before I applied `redim`, I created my "text" jpg image file in this way,

plotsetup('jpeg','plotoutput'=tempfile,'plotoptions'=cat("height=",vsize+6+4,
                                                         ",width=",hsize+5+5));

What I was trying to do was to stretch the "text" image, when exporting it, by some amounts that would (hopefully) match the whitespace borders. Above, vsize and hsize are the dimensions of the background image onto which I overlaid the "text" image.

Maybe you could attach your sample image and text plot command that you want, and we could work out the commands in full.

The cited reference seems more about a different problem, of optimizing parameters appearing in the IVP.

One thing to be careful about, if calling fsolve (or another rootfinder) for this task, is ensuring that the appropriate range of the independent variable (t) is used.

A slightly different target value for y(t) in Markiyan's example can illustrate this,

sys := (D(x))(t) = y(t)-x(t), (D(y))(t) = x(t)*(D(x))(t)-2*y(t):
ic := x(0) = 1, y(0) = -1:
sol := dsolve({ic, sys}, numeric):

fsolve('t ->rhs(sol(t)[3])-(-0.85) ');

                         -0.2029134387

fsolve('t ->rhs(sol(t)[3])-(-0.85) ', 0..infinity);

                          0.2639507984

acer

The cited reference seems more about a different problem, of optimizing parameters appearing in the IVP.

One thing to be careful about, if calling fsolve (or another rootfinder) for this task, is ensuring that the appropriate range of the independent variable (t) is used.

A slightly different target value for y(t) in Markiyan's example can illustrate this,

sys := (D(x))(t) = y(t)-x(t), (D(y))(t) = x(t)*(D(x))(t)-2*y(t):
ic := x(0) = 1, y(0) = -1:
sol := dsolve({ic, sys}, numeric):

fsolve('t ->rhs(sol(t)[3])-(-0.85) ');

                         -0.2029134387

fsolve('t ->rhs(sol(t)[3])-(-0.85) ', 0..infinity);

                          0.2639507984

acer

Thanks to you both. Presumably this means you could create your own images, using it in Maple 15/16.

@Christipher2222 I had a fast engine for this back in 2009 (see Comment here). But what I recently realized was that programmatically updating the image on a GUI Label Component -- even though it uses a temp image file -- was fast enough to make repeatedly re-embedding the images into the worksheet perform well enough.

I find that using a Label Component to embed a fine detail image gives a better impression that would using either of ImageTools:-Preview (very sluggish densityplot, or coarse rendition) or ImageTools:-View (Maplet popup).

Even though it (behind the scenes, internally) writes the image to a file, and then embeds that on the Label, this mechanism is still fast enough that for lower resolutions like 200x200 or 400x400 I can usefully toggle the color control continuous (float) Sliders to "update continuously while sliding". Despite the i/o! I'm still shocked how fast that GUI action is, and it evokes other apps that might work similarly. (Faster still would be insertion of the "right" XML, buffered and streamed instead of as file i/o. But I'm still trying to figure that out.)

@PatrickT I'm incorporating the items in my wishlist Comment above. This should include zooming in/out as well as arbitrary scene selection. But it is work for evening time.

You can run the code behind a Code Edit region while it is collapsed by giving it a single left-click with the mouse cursor, . While it is expanded you get a choice to either execute the code or collapse the region if you right-click-and-hold on it. I intend on moving the code into the Startup region.

I didn't add instruction (or even tooltips) for this simple draft version. I was interested in whether it would run at all, for other people. And I figured that by having no instruction I'd learn from you just what needs adding or changing. Ideally, I prefer apps which can be used with no instruction, being just simple or obvious. I'll try.

Another thing to improve: disable Sliders when in Black & White (grayscale) mode, as they only affect color.

I should probably mention some possible improvements:

  • Multi-threading (easy for evalhf mode, maybe less so for Compiled)
  • Julia sets (input the additional complex point using coarse preview?)
  • Zoom tool (maybe click&drag in inner rectangle with coarse preview, & In and Out buttons)
  • Explanatory tooltips on Components
  • Expository text (Intro, or popup, or below Components?)
  • Comments in code
  • Continuous update as Sliders' setting, when at lowest resolution(?)

acer

@Preben Alsholm Perhaps a little bit of indenting might help Patrick see your point -- that what comes after the colon in catch: does not control what gets caught.

> a:="56":

> try
>    sin(a);
> catch:
>    StringTools:-FormatMessage(lastexception[2..-1]);
>    45;
> end try;

   "invalid input: sin expects its 1st argument, x, to be of type algebraic, but received 56"

                               45

> try
>    sin(a);
> catch "invalid":
>    StringTools:-FormatMessage(lastexception[2..-1]);
>    45;
> end try;

   "invalid input: sin expects its 1st argument, x, to be of type  algebraic, but received 56"

                               45
> try
>    sin(a);
> catch "foobar":
>    StringTools:-FormatMessage(lastexception[2..-1]);
>    45;
> end try;
Error, invalid input: sin expects its 1st argument, x, to be of type algebraic, but received 56

I have some other comments for Patrick. Earlier on, above, you explicitly describe two kinds of "Warning" -- one about events and one about singularities. But the try...catch mechanism catches errors but not warnings. And dsolve/numeric solution procedures emit warnings about events, so try..catch isn't going to handle those, no? 

If you want to have your code recognize an event occurence then you can query the eventstop item following each evaluation. For example,

> g := dsolve({diff(y(t),t,t)+y(t)=0,y(0)=0,D(y)(0)=1}, numeric,
>             events=[[[y(t),diff(y(t),t)>0],halt],
>                     [[y(t),diff(y(t),t)<0],halt]]):

> g(2):

> g(eventstop);
                               0

> g(10):
Warning, cannot evaluate the solution further right of 3.1415926, event #2 triggered a halt

> g(eventstop);
                               2

You also wrote that the singularity situation produces a "Warning". But it causes an catchable error to be emitted instead.

> f:=dsolve({diff(f(x),x)=1/x, f(-1)=1/10},numeric):
> f(10);
Error, (in f) cannot evaluate the solution further right of -0.10619384e-304, probably a singularity

And so that error can be trapped with try..catch. Your final code could do both: check the eventstop and trap errors using try..catch.

You also mentioned "n" the length of characters in the fragment of the error to be caught, as the help-page describes it. The reason no specific value for "n" is given is that it is up to you. You specify the initial catch-string to be compared against an emitted error. You supply a catch-string of n characters, so it is you who decides how many characters to match, which is "n". And then Maple will compare only the first n characters of an emitted error against that catch-string.

@Preben Alsholm Perhaps a little bit of indenting might help Patrick see your point -- that what comes after the colon in catch: does not control what gets caught.

> a:="56":

> try
>    sin(a);
> catch:
>    StringTools:-FormatMessage(lastexception[2..-1]);
>    45;
> end try;

   "invalid input: sin expects its 1st argument, x, to be of type algebraic, but received 56"

                               45

> try
>    sin(a);
> catch "invalid":
>    StringTools:-FormatMessage(lastexception[2..-1]);
>    45;
> end try;

   "invalid input: sin expects its 1st argument, x, to be of type  algebraic, but received 56"

                               45
> try
>    sin(a);
> catch "foobar":
>    StringTools:-FormatMessage(lastexception[2..-1]);
>    45;
> end try;
Error, invalid input: sin expects its 1st argument, x, to be of type algebraic, but received 56

I have some other comments for Patrick. Earlier on, above, you explicitly describe two kinds of "Warning" -- one about events and one about singularities. But the try...catch mechanism catches errors but not warnings. And dsolve/numeric solution procedures emit warnings about events, so try..catch isn't going to handle those, no? 

If you want to have your code recognize an event occurence then you can query the eventstop item following each evaluation. For example,

> g := dsolve({diff(y(t),t,t)+y(t)=0,y(0)=0,D(y)(0)=1}, numeric,
>             events=[[[y(t),diff(y(t),t)>0],halt],
>                     [[y(t),diff(y(t),t)<0],halt]]):

> g(2):

> g(eventstop);
                               0

> g(10):
Warning, cannot evaluate the solution further right of 3.1415926, event #2 triggered a halt

> g(eventstop);
                               2

You also wrote that the singularity situation produces a "Warning". But it causes an catchable error to be emitted instead.

> f:=dsolve({diff(f(x),x)=1/x, f(-1)=1/10},numeric):
> f(10);
Error, (in f) cannot evaluate the solution further right of -0.10619384e-304, probably a singularity

And so that error can be trapped with try..catch. Your final code could do both: check the eventstop and trap errors using try..catch.

You also mentioned "n" the length of characters in the fragment of the error to be caught, as the help-page describes it. The reason no specific value for "n" is given is that it is up to you. You specify the initial catch-string to be compared against an emitted error. You supply a catch-string of n characters, so it is you who decides how many characters to match, which is "n". And then Maple will compare only the first n characters of an emitted error against that catch-string.

@Denis ...so post a full working example which could be used to reproduce the problem.

@Denis ...so post a full working example which could be used to reproduce the problem.

If you uploaded the example (in a worksheet, say, using the green up-arrow) then we'd have a better chance at helping you.

Numerical rootfinding of multi-dimension nonlinear functions can be tricky. The width of the ranges (domain) of the variables, the choice (if any) of initial point, the precision and accuracy, all these can come to bear hard on such problems.

Yes, the order of terms in a SUM (or PROD) Maple expression (DAG) can be session dependent. And that can cause a measurable numeric difference, which can in principle cascade down and amplify to the point that it's significant enough to make a method succeed of fail. But hopefully, if that is the case then the example could be solved more reliably by making some adjustment.

It's pretty hard to say more specifically, if you don't show the full example. (And even if you do, of course, it still might be hard.)

restart:
expression:=a+b+c:
1e20*eval(expression,[a=1e20,b=1e-20,c=-1e20]);
                               0.
restart:
expression:=c+a+b:
1e20*eval(expression,[a=1e20,b=1e-20,c=-1e20]);
                               1.

There are several ways to dispel the issue in the above example. But, sight unseen, we cannot know whether your case is even remotely similar.

acer

@Markiyan Hirnyk  Your understated original Answer only mentioned `evalf` and `solve`, but otherwise did not specify the order in which you intended they be applied. You just wrote that `evalf` would be useful, but not at which juncture. Two natural interpretations are evalf([solve(p)]) and [solve(evalf(p))] since you certainly did not specify at what point `evalf` ought to be used.

Your followup comment, in the midst of this thread, does specify which usage you intended. But the Answer was ambiguous, until then.

One of those two ways, [solve(evalf(p))], does in fact produce significantly less accurate results than those from fsolve, when Digits=12, in Maple 15. And the other, evalf([solve(p)]), produces essentially the same result as from fsolve. So that resolves the silly argument about ambiguous claims whether the fsolve or solve results are more accurate here.

The accuracy issue should not be of central importance here, anyway, since both results can be the same when used properly. What is important is that `solve` is the wrong tool for this task. This is clearly demonstrated, and should be the focus.

Here is `solve` calling `fsolve` to do the actual work, repeated degree=5 times,

restart:

trace(fsolve):

[evalf(solve(z^5-5*z^4-5*z-5, z))]: # 5-fold repetition

{--> enter fsolve, args = t^5-5*t^4-5*t-5, t, complex
 enter fsolve, args = t^5-5*t^4-5*t-5, t, complex
 enter fsolve, args = t^5-5*t^4-5*t-5, t, complex
 enter fsolve, args = t^5-5*t^4-5*t-5, t, complex
 enter fsolve, args = t^5-5*t^4-5*t-5, t, complex

@Markiyan Hirnyk  Your understated original Answer only mentioned `evalf` and `solve`, but otherwise did not specify the order in which you intended they be applied. You just wrote that `evalf` would be useful, but not at which juncture. Two natural interpretations are evalf([solve(p)]) and [solve(evalf(p))] since you certainly did not specify at what point `evalf` ought to be used.

Your followup comment, in the midst of this thread, does specify which usage you intended. But the Answer was ambiguous, until then.

One of those two ways, [solve(evalf(p))], does in fact produce significantly less accurate results than those from fsolve, when Digits=12, in Maple 15. And the other, evalf([solve(p)]), produces essentially the same result as from fsolve. So that resolves the silly argument about ambiguous claims whether the fsolve or solve results are more accurate here.

The accuracy issue should not be of central importance here, anyway, since both results can be the same when used properly. What is important is that `solve` is the wrong tool for this task. This is clearly demonstrated, and should be the focus.

Here is `solve` calling `fsolve` to do the actual work, repeated degree=5 times,

restart:

trace(fsolve):

[evalf(solve(z^5-5*z^4-5*z-5, z))]: # 5-fold repetition

{--> enter fsolve, args = t^5-5*t^4-5*t-5, t, complex
 enter fsolve, args = t^5-5*t^4-5*t-5, t, complex
 enter fsolve, args = t^5-5*t^4-5*t-5, t, complex
 enter fsolve, args = t^5-5*t^4-5*t-5, t, complex
 enter fsolve, args = t^5-5*t^4-5*t-5, t, complex

@Markiyan Hirnyk The statement is true for Maple 14, 15, and 16. If you are basing your counterclaim on results from Maple 13 or an even older major release then I would say that the moral obligation is on you to state that up front.

(For example, Maple 13 is three major releases back, and it would be bizarre to think that the unqualified statement should be that relating to some much older release as opposed to all the later releases.)

We should not forget that the rest of the claim is also true: using the solve command to get float approximations of all complex roots of a higher degree univariate polynomial (which does not factor explicitly) is much slower than using fsolve, in general. It is often worse by a multiple of n the degree of the polynomial, as solve simply calls fsolve n times to do the same work. This is demonstrated in the link given. This part is also true in Maple 13, 12, etc.

This accuracy comparison below is done in Maple 14.01 (Windows, 64bit), but the results are similar in 15.01 and 16.00. For these particular computations done under Digits=12 the results from fsolve are shown to have a greater number of accurate decimal digits, and produce smaller absolute forward error with respect to resubstitution in the original polynomial.

 

restart:
Digits:=12:

fsol:=[fsolve(z^5-5*z^4-5*z-5, z, complex)]:

forget(evalf):
ssol:=[solve(z^5-5*z^4-5*z-5.0, z)]:

forget(evalf):
Digits:=100:
highsol:=[fsolve(z^5-5*z^4-5*z-5, z, complex)]:

max(map(abs,sort(highsol)-sort(ssol))):
evalf[4](%);
                                         -12
                                 2.729 10   

max(map(abs,sort(highsol)-sort(fsol))):
evalf[4](%);

                                         -16
                                 8.203 10   

[seq(eval(z^5-5*z^4-5*z-5, z=x), x in fsol)]:
evalf[4](sort(%,(a,b)->abs(a)>abs(b)));

 [        -13           -15           -15             -15           -15    
 [5.476 10   , -2.189 10    - 1.555 10    I, -2.189 10    + 1.555 10    I, 

           -16           -16            -16           -16  ]
   8.853 10    + 2.778 10    I, 8.853 10    - 2.778 10    I]

[seq(eval(z^5-5*z^4-5*z-5, z=x), x in ssol)]:
evalf[4](sort(%,(a,b)->abs(a)>abs(b)));

 [         -10           -11           -11             -11           -11    
 [-7.234 10   , -4.471 10    + 5.918 10    I, -4.471 10    - 5.918 10    I, 

            -12           -12             -12           -12  ]
   -1.190 10    - 5.466 10    I, -1.190 10    + 5.466 10    I]

First 404 405 406 407 408 409 410 Last Page 406 of 592