Carl Love

Carl Love

28010 Reputation

25 Badges

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

MaplePrimes Activity


These are answers submitted by Carl Love

Their are 9 vertices that I'll order top-down, left-to-right. That makes 18 variables. By making the lower right vertex the origin and the right edge the y-axis, we can make 5 variables 0. By reflecting the given image over the y-axis, we can constrain all points to the 1st quadrant. I generate 13 equations from the given information in your diagram, then use fsolve. The 13 equations are:

  • Perimeters of each of the 7 primary triangles
  • Perimeters of the 2 composite triangles
  • Collinearity of the left side (2 equations because it's 4 points)
  • Collinearity of the bottom side
  • Collinearity of the bottoms of the triangles with perimeters 9 and 12.

I'll leave it to you to color them.

restart
:

#9 points, each with x and y coordinates.
P:= Matrix((9,2), symbol= p)
:

#distance-between-points function:
d:= (i,j)-> sqrt((p[i,1]-p[j,1])^2 + (p[i,2]-p[j,2])^2)
:

#perimeter-of-triangle:
T:= (i,j,k)-> d(i,j)+d(j,k)+d(k,i)
:
#co-linearity constraint generator
CoL:= (i,j,k)-> d(i,j)+d(j,k) = d(i,k)
:
#the primary triangles:

Ts:= [[1,2,3], [2,4,5], [2,3,5], [3,5,6], [4,7,8], [4,6,8], [6,8,9]]
:
#their perimeters:
Ps:= [20, 9, 13, 12, 10, 15, 11]
:

#Make lower right corner the origin, and right edge the y-axis:
eqs0:= {p[9,1], p[9,2], p[1,1], p[3,1], p[6,1]}=~ 0
:
eqs:= eval(
    {
        ((T@op)~(Ts) =~ Ps)[],
        CoL(1,2,4), CoL(2,4,7), CoL(4,5,6), CoL(7,8,9),
        T(1,4,6) = 20+9+12 - 13, T(1,7,9) = 20+9+12+10+11 -13-15
    },
    eqs0
):

#1st quadrant:
Q1:= ({seq}(P) minus lhs~(eqs0))=~ 0..infinity:

P:= eval(P, fsolve(eqs, Q1) union eqs0);

Matrix(9, 2, {(1, 1) = 0, (1, 2) = 14.90060263, (2, 1) = 3.382184235, (2, 2) = 10.23285104, (3, 1) = 0, (3, 2) = 6.046658910, (4, 1) = 5.188020843, (4, 2) = 7.740618787, (5, 1) = 3.710858752, (5, 2) = 6.351898354, (6, 1) = 0, (6, 2) = 2.863276643, (7, 1) = 5.954748645, (7, 2) = 6.682472994, (8, 1) = 3.216507499, (8, 2) = 3.609582404, (9, 1) = 0, (9, 2) = 0})

Poly:= T->
    plottools:-polygon(
        convert(P[T], listlist), linestyle= solid, color= white
    )
:
Label:= k-> local i;
    plots:-textplot([seq(add(P[Ts[k][i]], i= 1..3)/3), Ps[k]])
:

plottools:-rotate(
    plottools:-reflect(
        plots:-display(
            Poly~(Ts)[], seq(Label(k), k= 1..nops(Ts)),
            axes= none, scaling= constrained, gridlines= false
        ),
        [[0,0],[0,1]]  #reflect over y-axis
    ),
    Pi/6
);

;

 

Download TrianglesByPerimeters.mw

Your initial expression V__phi has a pair of square brackets [ ]. These need to be replaced by round brackets ( ) (also known as parentheses). In Maple (and most computer languages) square brackets can't be used as a "higher level" of parentheses like they are used in math books. Only parentheses can be used for algebraic groupings.

Making this change, the whole expression simplifies quickly.

You can use Edit ==> Find from the menus to find the square brackets.

The read command is for reading files of plaintext Maple code, not Maple worksheets. The file that you tried to read, "EKHAD.mw", is a worksheet. You should open it like you'd open any other worksheet: through the File ==> Open menu dialog.

The first read command that you gave has already loaded the code. Just type

ezra();

I believe that many of the algorithms from A=B have been directly implemented in Maple already.

The difference between eval (in its form used in this Question) and subs is that eval follows rules that are often specified in Maple code. The rule in this case is the procedure `eval/Int`. Presumably this procedure has been updated since Maple 2015. After a restart (to clear remember tables), do

trace(`eval/Int`);

and rerun your problem.

This should work for all your cases:

SeriesInt:= e->
    subsindets(
        e, specfunc({Int, int, Intat, intat}),
        J-> op(0, J)(mtaylor(op(1, J), op([2,1], J)= 0, 5), op(2.., J))
    )
;

The suggestion by @dharr will work in most cases. But it won't work when the subscript is an integer because then the subscript will be interpreted as an index into the list on its left. The command Typesetting:-Typeset can be used to turn mathematical expressions into inert objects that display exactly like the original expressions. So, this works:

restart:
`print/SubSup`:= (e, a, b)->
    [e][Typesetting:-Typeset(a)]^Typesetting:-Typeset(b)
:
SubSup:= (e::uneval, a, b)-> 'procname'(e,a,b)
:
SubSup(int(x^2, x), 2, 5);


 

The plot command is only for 2D. For 3D, use

plots:-spacecurve([t*sin(t), t*cos(t), (2*sqrt(2))/3*t^(3/2)], t= 0..Pi);

For 2D (assuming (just to keep this Answer simple) the orthogonal projection into the xy-plane), use

plot([t*sin(t), t*cos(t), t= 0..Pi]);

Note that in the first command, the range t= 0..Pi is outside the square brackets, and in the second command, it's inside.

(simplify@eval)(
    sqrt(a^2+b^2),
    solve({d-b = c-d, a/d = tan(45*Pi/180), a*(c-b)/2 = 60, a^2+c^2 = 19^2})
);

                               11

The variables sx, and y are clearly irrelevant because they only appear once in the problem.

Since the constraints are all easily made polynomial, this works also:

(simplify@@2)(
    sqrt(a^2+b^2), 
    {d-b = c-d, a/d = tan(45*Pi/180), a*(c-b)/2 = 60, a^2+c^2 = 19^2}
);

                               
11

This form of simplify requires only the constraints, not the objective, to be polynomial, or easily convertible to polynomial (as in a/d = ...). It's help page is ?simplify,siderels.

The extra simplify (as in simplify@@2) is unfortunately required to simplify sqrt(121) to 11. To avoid that awkwardness, you could do this:

(sqrt@simplify)(
    a^2+b^2, 
    {d-b = c-d, a/d = tan(45*Pi/180), a*(c-b)/2 = 60, a^2+c^2 = 19^2}
);

                               11

The other responders are making the mistake of assuming that all the variables are integer. The problem only requires AD to be integer. On a number line, let A, B, C, D 0, 7/3, 20/3, 21/3. Then AD = 7.

This is an excellent problem for testing any mathematical natural-language AI system. Solving it requires more than just middle-school Algebra I. This is a GRE-level problem (admittedly a fairly easy one). (GRE = Graduate Record Exam, a nationally standardized exam that one takes in the U.S. before applying to graduate school.)

@mmcdara In English, there is no ambiguity or lack of precision in this problem's statement. "Consecutive" means that they are distinct points, and are in the stated order. "Confounded" is not a word used in ordinary mathematical English; its only common usages are to describe mental states.

The diagram has two quadrilaterals that I'll call the "kite" and the "dart". They share two sides. I'll label these points as vertices:

  • A: point at the 60-degree angle
  • N: point where n is used
  • C: point in center where two lines cross
  • M: point where is used
  • X: point where x is used.

The kite is ANCM; the dart is XNCM. Now make two equations using that the sum of the angles of a quadrilateral is 360 degrees.

#quadrilateral ANCM:
Kite:= 60 + (180-2*n) + (180-40) + (180-2*m) = 360;
#       A       N           C          M
                 Kite := 560 - 2 m - 2 n = 360

#quadrilateral XNCM:
Dart:= x + n + (180+40) + m = 360;
#      X   N       C      M
                 Dart := x + m + 220 + n = 360

x = eval(x, solve({Kite, Dart}));
                             x = 40

 

Converting expr to disjunctive normal form makes it much easier to process. We will see that there's no solution, but there's a bug in solve that led you to believe that there was one. Of the 98 cases (as also mentioned by Christian Wolinski), solve finds a solution for 3, it's the same solution for all 3, and it's essentially the same solution that you got with RealDomain:-solve. But it's very easy to show (done below) that these solutions are incorrect.

restart;

expr := Or(And(-p^2 + 3*q < 0, p < 0, p^2 - 4*q < 0, Or(And(p < 0, -q < 0), p < 0, q < 0), Or(And(-2*p^2 + 3*q < 0, -q^2 < 0), And(p <= 0, Or(-2*p^2 + 3*q < 0, q^2 < 0))), Or(And(Or(And(p < 0, -q < 0), p < 0, q < 0), Or(And(-2*p^2 + 3*q < 0, -q^2 < 0), And(p <= 0, Or(-2*p^2 + 3*q < 0, q^2 < 0)))), And(p < 0, -q < 0), p < 0, q < 0, And(2*p^2 - 3*q < 0, -q^2 < 0), And(-p <= 0, Or(2*p^2 - 3*q < 0, q^2 < 0))), -2*p^5 + 15*p^3*q - 27*p*q^2 <= 0, p^2*q^2 - 4*q^3 = 0), And(p^2 - 3*q = 0, p < 0, -2*p^2 + 3*q < 0, Or(And(p < 0, -2*p^2 + 3*q < 0), p < 0, 2*p^2 - 3*q < 0), 2*p^3 - 9*p*q = 0), And(-p^2 + 3*q < 0, Or(And(p < 0, p^2 - 4*q < 0), p < 0, -p^2 + 4*q < 0), p < 0, -q < 0, Or(And(-2*p^2 + 3*q < 0, -q^2 < 0), And(-p <= 0, Or(-2*p^2 + 3*q < 0, q^2 < 0))), Or(And(p < 0, -q < 0, Or(And(-2*p^2 + 3*q < 0, -q^2 < 0), And(-p <= 0, Or(-2*p^2 + 3*q < 0, q^2 < 0)))), And(p < 0, -q < 0), And(2*p^2 - 3*q < 0, -q^2 < 0), And(p <= 0, Or(2*p^2 - 3*q < 0, q^2 < 0))), 2*p^5 - 15*p^3*q + 27*p*q^2 <= 0, p^2*q^2 - 4*q^3 = 0)):

Convert to disjunctive normal form (DNF):

use L= Logic in    
    DFT:= eval(
        L:-Convert(eval(expr, [And= L:-`&and`, Or= L:-`&or`]), 'DNF'),
        [L:-`&and`= `{}`, L:-`&or`= `[]`]
     )
end use:

Verify accuracy and feasibility:

nops(%), indets~((S:= {%[]}), name), nops~(S),
type(DFT, list(set({`=`, `<`, `<=`}))), nops~((eq:= select~(type, S, `=`))),
indets~(eq, name);

98, {{p, q}}, {4, 5, 7, 8, 9, 10, 11}, true, {1, 2}, {{p, q}}

Separate sets that should be solved for 1 variable and those solved for 2, based on the number of equations in the set:

(eqs1, eqs2):= selectremove(s-> nops(indets(s, `=`))=1, S):

sols:= remove~(rhs=(), map~(1@@0@curry(op,1)@`[]`=solve, [eqs1$2, eqs2], [{p}, {q}, {p,q}]));

sols := [{{p^2*q^2-4*q^3 = 0, -p <= 0, 2*p^5-15*p^3*q+27*p*q^2 <= 0, p < 0, -q < 0, -2*p^2+3*q < 0, -p^2+3*q < 0} = piecewise(q <= 0, [], 0 < q, [{p = -2*sqrt(q)}, {p = 2*sqrt(q)}]), {p^2*q^2-4*q^3 = 0, 2*p^5-15*p^3*q+27*p*q^2 <= 0, p < 0, -q < 0, -q^2 < 0, -2*p^2+3*q < 0, -p^2+3*q < 0} = piecewise(q <= 0, [], 0 < q, [{p = -2*sqrt(q)}, {p = 2*sqrt(q)}]), {p^2*q^2-4*q^3 = 0, -p <= 0, 2*p^5-15*p^3*q+27*p*q^2 <= 0, p < 0, -q < 0, -q^2 < 0, -2*p^2+3*q < 0, -p^2+3*q < 0} = piecewise(q <= 0, [], 0 < q, [{p = -2*sqrt(q)}, {p = 2*sqrt(q)}])}, {}, {}]

L:= lhs~(sols[1]): <L[]>;

Vector(3, {(1) = {p^2*q^2-4*q^3 = 0, -p <= 0, 2*p^5-15*p^3*q+27*p*q^2 <= 0, p < 0, -q < 0, -2*p^2+3*q < 0, -p^2+3*q < 0}, (2) = {p^2*q^2-4*q^3 = 0, 2*p^5-15*p^3*q+27*p*q^2 <= 0, p < 0, -q < 0, -q^2 < 0, -2*p^2+3*q < 0, -p^2+3*q < 0}, (3) = {p^2*q^2-4*q^3 = 0, -p <= 0, 2*p^5-15*p^3*q+27*p*q^2 <= 0, p < 0, -q < 0, -q^2 < 0, -2*p^2+3*q < 0, -p^2+3*q < 0}})

rhs~(sols[1])[];

piecewise(q <= 0, [], 0 < q, [{p = -2*sqrt(q)}, {p = 2*sqrt(q)}])

So q=1, p=2 is a witness, which we'll test:

W:= [q=1, p=2]:

ormap(evalb, andmap~(evalb, eval(L, W)));

false

It's a bug in solve! Easy to confirm by eye also:

eval(L, W);

{{0 = 0, -2 <= 0, -5 < 0, -1 < 0, 2 < 0}}

Note the 2 < 0.

map(solve, L, {q}), map(solve, L, {p,q}, parametric);

{}, {[]}

evalb(eval(eval(expr, W), [And= `and`, Or= `or`]));

false

Download DisNormForm.mw

The command Worksheet:-WorksheetToMapleText should do most of the work of converting a worksheet to a procedure. You'll still need to do a little clean-up by hand. Save the worksheet without output (Ctrl-D) before doing this.

Yes, the not-publically-documented command for doing this is `tools/genglobal`. Most commands that generate arbitrary constant names use it. I believe that dsolve used to use it but doesn't anymore, instead always using _C1_C2, ..., possibly aliased to c__1c__2, .... So, we just put a little wrapper around commands to change the constants:

restart:
SeqConst:= proc(e, prefix::symbol:= :-_C, new_prefix::symbol:= :-_C)
    subsindets['flat', 2](e, suffixed(prefix, nonnegint), new_prefix, `tools/genglobal`[1]) 
end proc
:
SeqConst(dsolve(diff(y(x),x)=2*y(x)));

                             y(x) = _C2 exp(2 x)

SeqConst(dsolve(diff(y(x),x)=3*y(x)));
                             y(x) = _C3 exp(3 x)
 

Here is my Maple implementation of the Mathematica command Cases that you showed. If that command allows more-complicated patterns or wildcards that you'd like implemented, let me know. The objects in the pattern are either types or the triple-underscore zero-or-more-of-anything wildcard. (All explicit numbers are also considered types in Maple.)

WildcardPatternPredicate:= proc(Pat::list({type, identical(:-___)}))
local P:= Array(1..0, datatype= integer[1]), t, k, np:= nops(Pat);
    for k,t in Pat do
        P,= `if`(k=1, "proc(", `if`(k<np or t::type, ", ", ""));
        if t::type then P,= sprintf("%a::(%a)", _||k, t);
        elif k=np then break
        elif (t:= Pat[k+1]) = :-___ then next
        else P,= sprintf("%a::seq(Not(%a))", _||k, t)
        fi
    od;
    if t::type then P,= ", $" else np-- fi;
    P,= sprintf(") option overload; %a; true end proc", _||np);
    overload([parse(String(P)), ()-> false])@op
end proc
:
Cases:= (L, P::list({type, identical(:-___)}))->
    select(WildcardPatternPredicate(P), L)
:
Cases(combinat:-permute(4), [___,2,___,3,___]);
   [[1, 2, 3, 4], [1, 2, 4, 3], [1, 4, 2, 3], [2, 1, 3, 4], 
     [2, 1, 4, 3], [2, 3, 1, 4], [2, 3, 4, 1], [2, 4, 1, 3], 
     [2, 4, 3, 1], [4, 1, 2, 3], [4, 2, 1, 3], [4, 2, 3, 1]]

#Large-case time test:
CodeTools:-Usage(Cases(combinat:-permute(9), [___,2,___,3,___])):
nops(%) = 9!/2;
memory used=1.99GiB, alloc change=169.75MiB, 
cpu time=3.16s, real time=6.99s, gc time=2.55s

                        181440 = 181440


The brilliant idea of using overload with the seq parameter modifier to effectively allow type-checking of expression sequences is due to @sursumCorda . Turning the patterns into predicates would be much more complicated without this idea.

This method is somewhat slower than most of the other methods presented in this thread, but it's not horribly slow. However, the patterns that it can handle are much more complicated than just permutations; in particular, the non-wildcards can be any type; they needn't be specific entities such as 2 or 3

I don't know the extent of all your cases, but in this case the following does it:

primpart(factor(expr));
                        40 x - 24 y - 3

primpart returns what's left after all the constants have been factored out.

Your error was mixing up the argument order for has. The object being searched is its first argument; the things being searched for (disjunctively) are its second argument.

I know that you like rule-based and pattern-based constructs. Unfortunately, the command applyrule (and its ilk, such as patmatch) has very limited capability, was written decades ago, the writer likely left Maple decades ago, and likely will never be significantly improved. So, you might as well stop torturing yourself by trying to use these commands, because it's usually impossible. (There might be a way to use applyrule in this case, but I'm not going to take the time to find out.)

Here's a way with subsindets:

subsindets(
    eq, `*`,   
    proc(e) 
    local (S,R):= selectremove(type, e, anything^(And(fraction, 2 &under denom)));
        `if`(denom(R)=1 or S=1, e, R %* S)
    end proc
);    
4 5 6 7 8 9 10 Last Page 6 of 394