Actually it looks like a lot of the logic is already there. For anyone
interested in fixing this, we just need to add a refine handler for
MatrixElement that handles symmetry. One already exists for Transpose

>>> X = MatrixSymbol("X", n, m)
>>> refine(Transpose(X), Q.symmetric(X))
X

I opened https://github.com/sympy/sympy/issues/16234, which should be
easy to fix.

Aaron Meurer

On Mon, Mar 11, 2019 at 1:16 PM Aaron Meurer <[email protected]> wrote:
>
> I don't think that exists yet, aside from the assumptions in the new
> assumptions Q.symmetric and Q.positive_definite. It would be useful to
> be able to bind those assumptions to the matrix object itself.
>
> Also ideally you would be able to put it under a "with
> assuming(Q.symmetric(q))" block (where q is your matrix Q, not to be
> confused with Q the SymPy object that hold the assumptions
> predicates), but that doesn't work yet either. As far as I know, the
> matrix assumptions so far only do anything for deduction (ask()).
>
> For now, you can use replace to make the resulting matrix symmetric
>
> >>> from sympy.matrices.expressions.matexpr import MatrixElement
> >>> p, Q = sospoly(Matrix([1, 2, 3]), 'Q')
> >>> p
> Q[0, 0] + 2*Q[0, 1] + 3*Q[0, 2] + 2*Q[1, 0] + 4*Q[1, 1] + 6*Q[1, 2] +
> 3*Q[2, 0] + 6*Q[2, 1] + 9*Q[2, 2]
> >>> p.replace(lambda x: isinstance(x, MatrixElement) and x.args[0] == Q, 
> >>> lambda x: x if x.args[1] <= x.args[2] else x.args[0][x.args[2],x.args[1]])
> Q[0, 0] + 4*Q[0, 1] + 6*Q[0, 2] + 4*Q[1, 1] + 12*Q[1, 2] + 9*Q[2, 2]
>
> Or you could use a custom MatrixSymbol subclass
>
> >>> class SymmetricMatrixSymbol(MatrixSymbol):
> ...     def _entry(self, i, j):
> ...         i, j = sympify((i, j))
> ...         if (i - j).could_extract_minus_sign():
> ...             i, j = j, i
> ...         return MatrixElement(self, i, j)
> >>> Q = SymmetricMatrixSymbol("Q", 3, 3)
> >>> Q[0, 1]
> Q[1, 0]
> >>> Q[1, 0]
> Q[1, 0]
> >>> x = Matrix([1, 2, 3])
> >>> (x.T*Matrix(Q)*x)[0]
> Q[0, 0] + 4*Q[1, 0] + 4*Q[1, 1] + 6*Q[2, 0] + 12*Q[2, 1] + 9*Q[2, 2]
>
> I used could_extract_minus_sign() instead of i < j because it handles
> symbolic entries as well.
>
> >>> i, j = symbols('i j')
> >>> Q[i, j]
> Q[i, j]
> >>> Q[j, i]
> Q[i, j]
>
> Aaron Meurer
>
> On Mon, Mar 11, 2019 at 12:04 PM <[email protected]> wrote:
> >
> > Hi,
> >
> > I was wondering how I can create symbolic symmetric positive definite 
> > (s.p.d.) Matrices.
> >
> > I would like to get a symbolic (symbolic in the Q-matrix) quadratic form
> >
> > def sospoly(x, varname):
> >     N = x.shape[0]
> >     Q = MatrixSymbol(varname, N, N)
> >     p = (x.T * Matrix(Q) * x)[0]
> >     return p, Q
> >
> >
> > where Q is s.p.d.
> > It would be enough to enforce symmetry actually ( making sure that Q[i,j] 
> > == Q[j,i]).
> > If there is no "SymmetricMatrixSymbol" is there an easy way to create a 
> > symbolic lower triangular matrix?
> >
> > Thank you!
> >
> > --
> > You received this message because you are subscribed to the Google Groups 
> > "sympy" group.
> > To unsubscribe from this group and stop receiving emails from it, send an 
> > email to [email protected].
> > To post to this group, send email to [email protected].
> > Visit this group at https://groups.google.com/group/sympy.
> > To view this discussion on the web visit 
> > https://groups.google.com/d/msgid/sympy/7e3c8066-b165-4226-b690-7810a6d22472%40googlegroups.com.
> > For more options, visit https://groups.google.com/d/optout.

-- 
You received this message because you are subscribed to the Google Groups 
"sympy" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To post to this group, send email to [email protected].
Visit this group at https://groups.google.com/group/sympy.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/sympy/CAKgW%3D6%2BwSs4v%2BReTycdEJjrZWC%3DNTEvFo8j8jQHd6E5m8mDcrg%40mail.gmail.com.
For more options, visit https://groups.google.com/d/optout.

Reply via email to