Carl Love

Carl Love

28055 Reputation

25 Badges

12 years, 358 days
Himself
Wayland, Massachusetts, United States
My name was formerly Carl Devore.

MaplePrimes Activity


These are answers submitted by Carl Love

Here's an easy way that I think corresponds to what you were asking for. We sort the points returned by LagrangeMultipliers based on the function value, lowest to highest. Then we pair each point with its function value. This requires Maple 18 or later. If you have an earlier Maple, let me know---it can still be made to work.

F:= (x,y,z)-> x*y*z:
Sols:= Student:-MultivariateCalculus:-LagrangeMultipliers(
     F(x,y,z), [x^2+4*y^2+4*z^2-4], [x,y,z]
):
Sols:= sort([Sols], key= evalf@F@op):
map(s-> [F(s[]), s], Sols);

Any data structure can be stored in a Vector. But I think that in your situation storing them in a list would work better. I'm not sure about your situation, and I'd like to see more details.

Here's a procedure that does the job with simply three sorts and a reindexing. It doesn't use any conversion to disjoint cycle form; it works strictly with the permlist form.

Perm1to2_D:= (L1::list, L2::list)->
     sort(L1, 'output'= 'permutation')
          [sort(sort(L2, 'output'= 'permutation'), 'output'= 'permutation')]
:

Here's how it works. Given a permutation in permlist form, its inverse can be obtained by sorting it with output= permutation. Given two permutations P1 and P2 in permlist form, the product or composition of P2 applied to P1 can be obtained by simply indexing: P1[P2]

Here's a time test of the four procedures so far presented for this problem.


Finding the permutation that transforms one list into another

restart:

We start with a basic alphabet. This will work with any list, even with repeated elements.

L:= ['rand()' $ 2^16]:

We scramble it two ways. This will simulate your original two lists (which, of course, must be permutations of each other for this to work).

L||(1..2):= 'combinat:-randperm(L)' $ 2:

 

Here are four procedures which take L1 and L2 as input and return, in permlist form, the permutation that transforms the first to the second.

 

The first procedure uses the deprecated group package to multiply and invert permutations.

Perm1to2_A:= proc(L1::list, L2::list)
local Pdjc:= (`convert/disjcyc`@sort)~([L1,L2], output= permutation);
     convert(group:-mulperms(group:-invperm(Pdjc[2]), Pdjc[1]), permlist, nops(L1))
end proc:

 

The second procedure is very similar, but uses the GroupTheory package for permutation arithmetic.

Perm1to2_B:= (L1::list, L2::list)->

     map2(

          GroupTheory:-PermApply,

          GroupTheory:-PermLeftQuotient((Perm@sort)~([L2,L1], 'output'= 'permutation')[]),

          [$1..nops(L1)]

     )

:

 

The third procedure (written by MaplePrimes user vv), simply uses the builtin member command. Its time complexity is obviously O(nops(L1)^2) (assuming the expected situation that nops(L1) = nops(L2)).

L1toL2_C:= (L1::list, L2::list)->

     map(proc(x,L) local t; member(x,L,t); t end proc, L2, L1)

:

 

The fourth procedure uses just the sort command and indexing. Its time complexity is O(nops(L1)*ln(nops(L1))).

Perm1to2_D:= (L1::list, L2::list)->
     sort(L1, output= permutation)[sort(sort(L2, output= permutation), output= permutation)]
:

 

PA:= CodeTools:-Usage(Perm1to2_A(L1,L2)):

memory used=36.66GiB, alloc change=362.30MiB, cpu time=28.30s, real time=28.48s, gc time=11.09s

evalb(L1[PA] = L2);

true

PB:= CodeTools:-Usage(Perm1to2_B(L1,L2)):

memory used=38.23MiB, alloc change=32.00MiB, cpu time=52.58s, real time=52.79s, gc time=125.00ms

evalb(L1[PB] = L2);

true

PC:= CodeTools:-Usage(L1toL2_C(L1,L2)):

memory used=8.50MiB, alloc change=0 bytes, cpu time=1.41s, real time=1.42s, gc time=0ns

evalb(L1[PC] = L2);

true

PD:= CodeTools:-Usage(Perm1to2_D(L1,L2)):

memory used=6.66MiB, alloc change=0 bytes, cpu time=62.00ms, real time=40.00ms, gc time=0ns

evalb(L1[PD] = L2);

true

 


Download permL1toL2.mw

The first argument to animate shouldn't be a plotting command; rather, it should be just the procedure name of a plotting command. The second argument should be a list of arguments for the procedure in the first argument parametrized by the animation parameter. The third argument should be the animation parameter and its range. So, your command should be

plots:-animate(
     plots:-dualaxisplot,
     [sin(x+A), cos(x+A), x=0..5, style = line, gridlines = false],
     A = 0 .. 5
);

In the call to odeplot, change [x,U(x)] to [[x,U(x)], [x,S(x)]]. In the call to animate, change the range from -2..0 to -2..-0.1 to avoid the singularity at x=0.

If you have an existing proc procedure to which you want to give the property of being distributive over the first argument, then you can include the following statement before the main computation:

if args[1]::`+` then return map(thisproc, args) end if;

The simplest example---a procedure that does nothing other than distribute itself over its first argument---is

d:= proc(a,b)
     if args[1]::`+` then return map(thisproc, args) end if;
     'procname'(args)
end proc:

d(a+b, c);

Is r*t-m also negative? If yes, then you can solve the imaginary number problem by

combine(v(t), symbolic);

If no, then the imaginary numbers are "really" part of your problem, and you need to figure out their significance. Just making the ln "disappear" isn't an adequate solution.

 

The command that you tried to post as an "Inline image" didn't show up. In the future, just copy-and-paste plaintext of your command.

I'm going to guess that your command was something close to

plot(x/x, x= -1..1, discont= [showremovable]);

The reason why the hollow point doesn't appear in this case is something called automatic simplification : Certain expressions are automatically simplified before being passed. In this case, x/x is automatically simplified to 1 beforeit's passed to plot. There's nothing that you can do to prevent this.

However, if you want to test the showremovable option, the following works:

plot((x^2-x)/x, x= -1..1, discont= [showremovable]);

Change the line

MM:= Minimize(J, {seq(CC1[i]=0 and CC2[i]=0, i=1..numelems(CC1))});

to

MM:= Minimize(J, {seq([CC1[i]=0, CC2[i]=0][], i=1..numelems(CC1))});

The commands in Optimization don't accept constraints with Boolean operators, such as and.

A very often-discussed topic here on MaplePrimes is a better alternative for the awkward and slow combinat:-cartprod

L:= [ [ [1,2], [2,1] ], [ [3,4], [4,3] ], [ [5] ] ]:

CartProd:= proc(L::list(list))
local S, _i, V:= _i||(1..nops(L));
     [eval(subs(S= seq, foldl(S, [V], (V=~ L)[])))]
end proc:

(op~)~(CartProd(L));

Between the two inner loops you have two statements. The second of those statements needs a semicolon at its end.

Yes, there's a three-argument operator form of if`if`. It's very similiar to the (...?...:...) operator in C. For example:

seq(`if`(k::prime, 1, 0), k= 1..10);

     0, 1, 1, 0, 1, 0, 1, 0, 0, 0

What's a little more difficult in Maple is an embedded assign-and-increment statement such as your idx+= 1. This can be implemented like this:

`&+=`:= proc(x::evaln, inc::algebraic)
     assign(x, eval(x)+inc);
     eval(x)
end proc:

idx:= 1:
seq(`if`(i > 2, idx &+= i, idx+i), i= 1..10);

    2, 3, 4, 8, 13, 19, 26, 34, 43, 53

It's fairly easy. Here's a worksheet for it.


Finding the permutation that transforms one list into another

restart:

We start with a basic alphabet. This will work with any list of distinct elements.

L:= [a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z]:

We scramble it two ways. This will simulate your original two lists (which, of course, must be permutations of each other for this to work).

L||(1..2):= 'combinat:-randperm(L)' $ 2;

[c, h, i, l, g, q, u, k, v, x, m, y, b, s, n, a, r, j, t, p, f, z, o, w, e, d], [e, j, q, w, z, m, f, t, y, i, s, u, v, x, b, c, n, k, o, r, h, a, p, l, d, g]

Now we find the permutation that transforms L1 to L2.

Pdjc:= (`convert/disjcyc`@sort)~([L1,L2], output= permutation):

Pdjc1to2:= group:-mulperms(group:-invperm(Pdjc[2]), Pdjc[1]);

[[1, 25, 26, 5, 22, 16], [2, 18, 8, 19, 23, 20, 17, 15, 13, 9, 12, 7, 21], [3, 6, 11, 14, 10], [4, 24]]

That's the permutation that we want expressed in disjoint cycle (disjcyc) notation. To use it as an index, it needs to be in permlist notation.

P:= convert(Pdjc1to2, permlist, nops(L1));

[25, 18, 6, 24, 22, 11, 21, 19, 12, 3, 14, 7, 9, 10, 13, 1, 15, 8, 23, 17, 2, 16, 20, 4, 26, 5]

Finally, we show that P does indeed transform L1 into L2:

L1[P];

[e, j, q, w, z, m, f, t, y, i, s, u, v, x, b, c, n, k, o, r, h, a, p, l, d, g]

evalb(% = L2);

true

 

Now I put that together into a procedure that returns the permutation in disjcyc notation. If you need permlist notation, it's just a trivial change to the last line.

Perm1to2:= proc(L1::list, L2::list)
uses G= group;
local
     S1:= {L1[]},     
     Pdjc:= (`convert/disjcyc`@sort)~([L1,L2], output= permutation)
;
     if S1 <> {L2[]} or nops(L1) <> nops(S1) then
          error "Invalid input: Lists must have distinct elements and be "
               "permutations of each other"
     end if;
     G:-mulperms(G:-invperm(Pdjc[2]), Pdjc[1])
end proc:

 


Download permL1toL2.mw

Use the command Elements:

Elements(P2);

lprint(%);

{Perm([]), Perm([[1, 3, 5]]), Perm([[1, 5, 3]])}

Using the example that you provided, and automating the process of making the assumptions:

B:= [a-1, b+2, b-c, a*c-1]:
f:= a^2*c-a*c-a+1:
is(f <> 0) assuming (B <>~ 0)[];

     true

Unlike assume, assumptions made with assuming only last for duration of one command.

First 245 246 247 248 249 250 251 Last Page 247 of 395