Collecting terms in multivariate polynomial

218 views
Skip to first unread message

Daniel Larsson

unread,
Feb 25, 2010, 4:40:25 AM2/25/10
to sage-support
Hi,

this is probably a trivial question but I haven't been able to figure
it out:

I have a matrix (rather gruesome) with two variables (X, Y) and
computing the determinant I get a polynomial in X and Y. Now, this
polynomial is a mess as given and I want to collect X and Y-terms into
the nice form we expect and love.

I've tried simplify_full() on the suggestion of a similar discussion
here on the forum but this doesn't seem to work; it just goes on and
on chewing this. In the end I had to interrupt the computation.

There should be a simple way to do this (like "collect" in maple) but
I can't for the life of me figure it out.

/Daniel

Simon King

unread,
Feb 25, 2010, 5:03:12 AM2/25/10
to sage-support
Hi Daniel!

On Feb 25, 9:40 am, Daniel Larsson <number...@gmail.com> wrote:
> I have a matrix (rather gruesome) with two variables (X, Y) and
> computing the determinant I get a polynomial in X and Y. Now, this
> polynomial is a mess as given and I want to collect X and Y-terms into
> the nice form we expect and love.

Can you explain in more detail what you mean by "mess" and by "nice
form we expect"?

People interested in commutative algebra are likely to expect that the
polynomial ring is equipped with a monomial order, and that the terms
of any polynomial are sorted accordingly. On the other hand, people
interested in symbolics/calculus/whatever may prefer another form.

So, the decisive question is:
Are you really talking about polynomials, or are you talking about
symbolic expressions?

The difference is as follows:

1) Polynomials:
sage: R.<x,y> = QQ[]
sage: type(x)
<type
'sage.rings.polynomial.multi_polynomial_libsingular.MPolynomial_libsingular'>
sage: (x^2*y+3*x)*(y^4-2*y^2*x*2)
x^2*y^5 - 4*x^3*y^3 + 3*x*y^4 - 12*x^2*y^2

2) Symbolic expressions:
sage: var('x,y')
(x, y)
sage: type(x)
<type 'sage.symbolic.expression.Expression'>
sage: (x^2*y+3*x)*(y^4-2*y^2*x*2)
(x^2*y + 3*x)*(y^4 - 4*x*y^2)

Depending on your application, it might be reasonable to use proper
polynomials. By the way, if you use it in a Python script, the
notation "R.<x,y> = QQ[]" wan't work. Instead, you may do
R = QQ['x, y']
x, y = R._first_ngens(2)

Best regards,
Simon

Daniel Larsson

unread,
Feb 25, 2010, 5:22:02 AM2/25/10
to sage-support
Hi Simon,

Hmmm, I hadn't thought about this with the difference between
polynomials and symbolic expressions. I'm rather new to Sage and the
likes (as you probably can tell :) ).

Anyway, when I compute the determinant the result is a long sequence
of terms but where there are multiple instances of terms with X^n or
Y^n (for instance). I wan't to collect these into one X^n-term or Y^n-
term.

I'm not that interested in which monomial order is being used.

So, maybe I should work with polynomial rings instead? I assume I can
take determinants of matrices with polynomial entries? Also, my base
ring is actually a cyclotomic field, I assume that this doesn't pose
any problem?

/Daniel

Simon King

unread,
Feb 25, 2010, 5:56:11 AM2/25/10
to sage-support
Hi Daniel!

On Feb 25, 10:22 am, Daniel Larsson <number...@gmail.com> wrote:
> So, maybe I should work with polynomial rings instead? I assume I can
> take determinants of matrices with polynomial entries? Also, my base
> ring is actually a cyclotomic field, I assume that this doesn't pose
> any problem?

I wouldn't go as far as expecting "no problems" (I mean, no big
program is without bugs, and I think matrices over polynomial rings
over cyclotomic fields aren't totally trivial). But one can do this:

sage: F = CyclotomicField(3)
sage: R.<x,y> = F[]
sage: MS = MatrixSpace(R,2,2)
sage: M = MS.random_element()
sage: M.determinant()
(-49157/2400*zeta3 - 113351/240)*x^4 + (1327/26460*zeta3 +
499/13230)*x^3*y + (-1972/45*zeta3 - 31207/720)*x^2*y^2 +
(95/441*zeta3 + 401/2646)*x*y^3 + (11/12*zeta3 + 23/12)*y^4 +
(82058/15015*zeta3 + 226369427/720720)*x^3 + (-7157/588*zeta3 +
3223/6615)*x^2*y + (224287447/30270240*zeta3 - 2817037/7567560)*x*y^2
+ (253/420*zeta3 + 47/42)*y^3 + (68627729/600600*zeta3 +
809819237/900900)*x^2 + (1709/38220*zeta3 + 209/13230)*x*y +
(6517/300*zeta3 - 1967/300)*y^2 + (-40057/770*zeta3 + 40207/25025)*x +
(-979/350*zeta3 - 16/7)*y + (-319/2*zeta3 + 13/10)

Is this close to your expectations?

But again, it really depends on your applications. And in more
complicated applications, it might even pay off to use different data
types in parallel and transform back and forth:

# create polynomials


sage: R.<x,y> = QQ[]

sage: p_poly = R.random_element()
sage: q_poly = R.random_element()

# transform into symbolic data
sage: p_symb = SR(p_poly) # SR is the Symbolic Ring
sage: q_symb = SR(q_poly)

# I understood that here you prefer polynomials...
sage: p_symb*q_symb
1/360*(180*x^2 - 360*y^2 + 45*y + 52)*(3*x^2 - 4*y^2 + 3*x - 16*y)
sage: p_poly*q_poly
3/2*x^4 - 5*x^2*y^2 + 4*y^4 + 3/2*x^3 - 61/8*x^2*y - 3*x*y^2 +
31/2*y^3 + 13/30*x^2 + 3/8*x*y - 116/45*y^2 + 13/30*x - 104/45*y

# ... but when solving (=finding roots), only symbolics work:
sage: solve(p_symb*q_symb,SR(x))
[x == -1/30*sqrt(360*y^2 - 45*y - 52)*sqrt(5), x ==
1/30*sqrt(360*y^2 - 45*y - 52)*sqrt(5), x == -1/6*sqrt(16*y^2 + 64*y +
3)*sqrt(3) - 1/2, x == 1/6*sqrt(16*y^2 + 64*y + 3)*sqrt(3) - 1/2]
sage: solve(p_poly*q_poly,x)
--------
TypeError
...
TypeError: object of type
'sage.rings.polynomial.multi_polynomial_libsingular.MPolynomial_libsingular'
has no len()


Best regards,
Simon

Daniel Larsson

unread,
Feb 25, 2010, 6:19:45 AM2/25/10
to sage-support
Yes!

Now, it works like a charm! Thanks!

It still is a bit illogical how things work here, but maybe I get used
to someday :)

/Daniel

Daniel Larsson

unread,
Feb 25, 2010, 7:41:05 AM2/25/10
to sage-support
Sorry,

One more question:

suppose I want to make variable change later in the computation, say
X---> a*Z+b. How do I do this as easy as possible? (Of course, a and
b are in the ground ring.) The "obvious" method by putting X=a*Z+b
didn't work (I kind of suspected it wouldn't; it's never quite that
easy, is it? :) )

/Daniel

Simon King

unread,
Feb 25, 2010, 8:08:20 AM2/25/10
to sage-support
Hi Daniel!

On Feb 25, 12:41 pm, Daniel Larsson <number...@gmail.com> wrote:
> Sorry,
>
> One more question:
>
> suppose I want to make variable change later in the computation, say
> X---> a*Z+b.  How do I do this as easy as possible? (Of course, a and
> b are in the ground ring.)

I guess that Z is another variable. So, let's first create a matrix
over a polynomial ring with generators x,y, then create a new
polynomial ring with variables y,z, and then the substitution is done
by the method "substitute":

sage: F = CyclotomicField(3)
sage: R.<x,y> = F[]
sage: MS = MatrixSpace(R,2,2)
sage: M = MS.random_element()

sage: d = M.determinant()
sage: d
(-140*zeta3 + 4)*x^4 + (85/7*zeta3 + 386/35)*x^3*y +
(-29437/210*zeta3 + 269/10)*x^2*y^2 + (1695/91*zeta3 +
25747/1365)*x*y^3 + (1637/390*zeta3 + 196/65)*y^4 + (-1738553/30*zeta3
+ 24494/15)*x^3 + (940484/175*zeta3 + 73366/15)*x^2*y +
(4462909/2730*zeta3 + 27063833/16380)*x*y^2 + (-2149/1950*zeta3 +
33/20)*y^3 + (-10639/45*zeta3 - 3361/20)*x^2 + (2269/180*zeta3 -
1147/180)*x*y + (-7/2*zeta3 - 23/13)*y^2 + (-1656*zeta3 - 2485/3)*x +
(-1/3*zeta3 - 1/6)*y
sage: a = F.random_element()
sage: b = F.random_element()
sage: R2.<y,z> = F[]
sage: d.substitute(x=a*z+b)
(1637/390*zeta3 + 196/65)*y^4 + (1695/91*zeta3 + 25747/1365)*y^3*z +
(-29437/210*zeta3 + 269/10)*y^2*z^2 + (85/7*zeta3 + 386/35)*y*z^3 +
(-140*zeta3 + 4)*z^4 + (-274123/13650*zeta3 + 58571/5460)*y^3 +
(1286639/910*zeta3 + 2756333/2340)*y^2*z + (267139/50*zeta3 +
1031651/210)*y*z^2 + (-1747673/30*zeta3 + 11654/15)*z^3 +
(-3723619/2730*zeta3 + 2848931/3276)*y^2 + (-58806991/6300*zeta3 +
9868003/1575)*y*z + (-16706569/180*zeta3 - 1326249/5)*z^2 +
(-88681681/12600*zeta3 - 127518221/12600)*y + (62993237/180*zeta3 +
4974579/40)*z + (-1187843/360*zeta3 + 31839397/240)


Here are some typical methods to explore Sage:

You can learn about any method by appending it with "?" (and then
press "RETURN", of course), such as:
sage: d.substitute?
You will then be shown the documentation of the method.

By appending "??" instead of just "?", you will in most cases even see
the source code of the method.

And if you want to find a method, you can use autocompletion, by
hitting the TAB key. For example:
sage: d.su<TAB>
d.sub_m_mul_q d.subs d.substitute

This assumes that you have some guessing how the method is called.

For a full text search, do search_doc, search_src or search_def (type
"search_def?" if you want to know what it does...).

And for higher level use of sage, learning Python can not be avoided
(which is a good thing anyway, since Python is a main stream
language).

>  The "obvious" method by putting X=a*Z+b
> didn't work (I kind of suspected it wouldn't; it's never quite that
> easy, is it? :) )

The variable of name "X" in the polynomial is one thing. The
identifier of name "X" in your Sage session is something else. And
when you have a polynomial, then its contents are still bound to the
polynomial ring (hence, to the variable of name "X"), even if you
change the meaning of the identifier "X" in your Sage session.

sage: R
Multivariate Polynomial Ring in x, y over Cyclotomic Field of order
3 and degree 2
sage: x = 'bla'
sage: R.gens()
(x, y)
sage: x
'bla'
sage: R.gen(0)
x
sage: R.gen(0) == x
False

Cheers,
Simon

Daniel Larsson

unread,
Feb 25, 2010, 8:34:41 AM2/25/10
to sage-support
For some reason I don't get what you get; I seem to get some symbolic
expression after the "d.substitute"-call.

In any case, is it necessary to change ring like you did?

/Daniel

Daniel Larsson

unread,
Feb 25, 2010, 8:39:11 AM2/25/10
to sage-support
ahhh, I see where I went gone wrong: in my case I took a square-root
also (my "a"). This is not allowed in the cyclotomic world.

On 25 Feb, 14:08, Simon King <simon.k...@nuigalway.ie> wrote:

Simon King

unread,
Feb 25, 2010, 11:41:51 AM2/25/10
to sage-support
Hi Daniel!

On 25 Feb., 14:34, Daniel Larsson <number...@gmail.com> wrote:
> In any case, is it necessary to change ring like you did?

It is necessary that z is defined somewhere. I guess you also could
create a polynomial ring with variables x,y,z over your cyclotomic
field, define your matrix in terms of x and y, and then substitute x
by something that is expressed in terms of z.

Best regards,
Simon

Reply all
Reply to author
Forward
0 new messages