roman_pearce

Mr. Roman Pearce

1678 Reputation

19 Badges

20 years, 218 days
CECM/SFU
Research Associate
Abbotsford, British Columbia, Canada

I am a research associate at Simon Fraser University and a member of the Computer Algebra Group at the CECM.

MaplePrimes Activity


These are replies submitted by roman_pearce

Joe Riel's timings for the first example don't really change when you restart Maple in between. Your general point however is important: memory allocation can significantly affect the performance of procedures which operate on a lot of data. This is especially true because Maple garbage collects, which is O(allocated memory), and does not free memory, which is a questionable design. Routines which create a lot of garbage will, generally speaking, degrade the performance of the system. In this case my approach, while faster, actually generates about twice as much garbage compared to the table-based approach (probably due to procedure calls). I consider this a worthwhile tradeoff because the amount of memory we are talking about is small - a few MB perhaps. In a large problem with hundreds of MB allocated, odds are that the system will reassign garbage collected memory and there will be no new allocation in either case. That equals time saved.
Edited to note: The post below is wrong, and Joe Riel's times are correct. Maple fully evaluates global expressions, causing the for loop method to run an order of magnitude slower in the test below than it does in a procedure. The principle of assigning to variables in a seq is a valid one, however to get any performance benefits it seems necessary to have your own procedure do it (as in the irem example below). You will probably never get good performance using the 'assign' command. In light of Joe Riel's timings, I think I need to clarify where this technique is useful and where it is not. The method benefits from the fact that a seq is faster than an explicit loop with multiple statements, but it suffers from the overhead of a Maple procedure call in each iteration. The question is: how many variables are needed to describe the "state" of your loop ? If the answer is "more than one" then you can probably derive a benefit from this technique. The second problem (nested lists) illustrates this pretty well:
restart;
L := [seq(i,i=1..5000)]:
TIMER := time():
L1 := []: 
for i in L do
  L1 := [i, L1]
end do: 
TIMER1, TIMER := time()-TIMER, time():
for i to nops(L) do
  M[i] := L1[1];
  L1 := L1[2]
end do:
TIMER1, time()-TIMER;

restart;
L := [seq(i,i=1..5000)]:
TIMER := time():
L1 := []:
seq(assign('L1', [i,L1]), i=L):
TIMER1, TIMER := time()-TIMER, time():
L1 := [seq([L1[1], assign('L1', L1[2])][1], i=1..nops(L))]:
TIMER1, time()-TIMER;
Of course you can get even more improvement by writing your own procedure instead of using Maple's assign, which as Joe pointed out, is not built-in (sadly).
f7a := proc(n1,n2,N1,N2)
  N1 := n2;
  N2 := n1+n2;
end proc:

f7 := proc(N)
  local i, n1, n2;

   n1 := 1;
   n2 := 1;
   [1, 1, seq(f7a(n1,n2,'n1','n2'),i=3..N)]
end proc:
I timed it in my own code, where I was building lists of polynomials by extracting terms one by one from external code and updating multiple pointers using external calls. The assign technique had better average-case performance, probably because it generated less garbage. It would have also helped that I was already building a product, so the `+`() call (`*` in my case) was not extraneous. These examples were really just to illustrate the technique, which can be useful when it fits your situation. I appreciate your timings however.
I didnt realise this before. I just simply expected Maple to give me the correct answers. So what you are suggesting is that Maple is incapable of meeting my needs ? Well, you have to understand that the way you have approached the problem has this ill-conditioned step. In theory Maple can solve the problem, however it may require thousands of digits of precision to produce a meaningful result. However, it may be possible to solve using a different method and obtain more accurate results. You should try to combine steps, so that less error accumulates from one step to another. This may make the problem harder. If you have exact data instead of floating point numbers that might help as well. When I have a minute I'll take a look at this and try to offer you some better suggestions.
I didnt realise this before. I just simply expected Maple to give me the correct answers. So what you are suggesting is that Maple is incapable of meeting my needs ? Well, you have to understand that the way you have approached the problem has this ill-conditioned step. In theory Maple can solve the problem, however it may require thousands of digits of precision to produce a meaningful result. However, it may be possible to solve using a different method and obtain more accurate results. You should try to combine steps, so that less error accumulates from one step to another. This may make the problem harder. If you have exact data instead of floating point numbers that might help as well. When I have a minute I'll take a look at this and try to offer you some better suggestions.
Evaluate either function at the value of x: f := x^2 - 1; g := 2*x+1; S := [fsolve(f-g)]; eval(f, x=S[1]); eval(g, x=S[1]);
Evaluate either function at the value of x: f := x^2 - 1; g := 2*x+1; S := [fsolve(f-g)]; eval(f, x=S[1]); eval(g, x=S[1]);
The method of generating the equation is numerically unstable, up to 500 digits. At different settings of Digits - I tried 15, 50, 100, 200, and 500 - you get terms which are order 10^(Digits) in the numerator and denominator. The problem is here: > solns := simplify(solve({eq1,eq2,eq3,eq4},{A1c,A2c,A3c,A4c})); You are trying to symbolically solve a non-linear system with coefficients order 10^15 and one free parameter. Maple doesn't have a method for this (assuming there even is one) and as you can see the result is garbage: > simplify(subs(solns, {eq1,eq2,eq3,eq4})); Does anyone have any suggestions ?
The method of generating the equation is numerically unstable, up to 500 digits. At different settings of Digits - I tried 15, 50, 100, 200, and 500 - you get terms which are order 10^(Digits) in the numerator and denominator. The problem is here: > solns := simplify(solve({eq1,eq2,eq3,eq4},{A1c,A2c,A3c,A4c})); You are trying to symbolically solve a non-linear system with coefficients order 10^15 and one free parameter. Maple doesn't have a method for this (assuming there even is one) and as you can see the result is garbage: > simplify(subs(solns, {eq1,eq2,eq3,eq4})); Does anyone have any suggestions ?
f := x^2 - 1; g := 2*x+1; fsolve(f-g); # check solve(f=g); evalf(%);
f := x^2 - 1; g := 2*x+1; fsolve(f-g); # check solve(f=g); evalf(%);
Use a list of digits, ie: [0,1,2,3]. It is probably what you will want eventually anyway.
http://www-sop.inria.fr/coprin/logiciels/ALIAS/ I don't think there is anything built into Maple yet, but you can try the ALIAS package linked above. It's a C++ binary with a Maple wrapper.
It is very unlikely that Maple will ever be GPL'd, for essentially the same reason that Windows will never be GPL'd. It's popular, the company is doing well financially, and there are third party contributions to consider. That being said, in the long term Maplesoft needs some sort of program (like Microsoft Shared Source) to make the kernel source available to researchers. There have been many instances of somebody wanting to implement something in the kernel, to the benefit of Maple and it's users, but they can't unless Maplesoft provides access to the kernel source. These people usually work in AXIOM instead.
First 31 32 33 34 35 36 37 Page 33 of 39