Ask Your Question

Revision history [back]

Here is a function kdet that will compute the determinant as desired.

It works by creating a copy of the matrix, redefining the _mul_ method of its elements as kronecker_product, and computing the determinant of that matrix.

This does not completely answer the question, since the "Kronecker product determinant" of a matrix a has to be computed as kdet(a) rather than a.det().

Here is the proposed function kdet:

def kdet(a):
    r"""
    Return the "Kronecker product determinant" of the matrix `a`.

    That is, compute the determinant of `a` as usual except
    multiplying entries using the Kronecker product.
    """
    nr = a.nrows()
    nc = a.ncols()
    R = a.base_ring()
    z = R.zero()
    aa = a.list()
    mci = lambda e: e.monomial_coefficients().items()
    new = lambda e: sum((c * R(m) for m, c in mci(e)), z)
    bb = [new(e) for e in aa]
    for e in bb:
        e._mul_ = e.kronecker_product
    b = matrix(R, nr, nc, bb)
    return b.det()

Usage:

sage: S = SymmetricFunctions(QQ)
sage: s = S.schur()

sage: f = s[2]

sage: m = matrix([[f, 0], [0, f]])
sage: m
[s[2]    0]
[   0 s[2]]

sage: m.det()
s[2, 2] + s[3, 1] + s[4]

sage: det(a)
s[2, 2] + s[3, 1] + s[4]

sage: kdet(a)
s[2]

Compare:

sage: f * f
s[2, 2] + s[3, 1] + s[4]

sage: f.kronecker_product(f)
s[2]

To go further and enable using a.det, one is tempted to define a method _matrix_determinant for the ring s using kdet, but since kdet uses det, this leads to a recursion error.

sage: s._matrix_determinant = kdet
sage: a = matrix([[f, 0], [0, f]])
sage: a.det()
Traceback (most recent call last)
...
RecursionError: maximum recursion depth exceeded while calling a Python object

Hopefully the workaround provided by the function kdet is still useful.

Here is a function kdet that will compute the determinant as desired.

It works by creating a copy of the matrix, redefining the _mul_ method of its elements as kronecker_product, and computing the determinant of that matrix.

This does not completely answer the question, since the "Kronecker product determinant" of a matrix a has to be computed as kdet(a) rather than a.det().

Here is the proposed function kdet:

def kdet(a):
    r"""
    Return the "Kronecker product determinant" of the matrix `a`.

    That is, compute the determinant of `a` as usual except
    multiplying entries using the Kronecker product.
    """
    nr = a.nrows()
    nc = a.ncols()
    R = a.base_ring()
    z = R.zero()
    aa = a.list()
    mci = lambda e: e.monomial_coefficients().items()
    new = lambda e: sum((c * R(m) for m, c in mci(e)), z)
    bb = [new(e) for e in aa]
    for e in bb:
        e._mul_ = e.kronecker_product
    b = matrix(R, nr, nc, bb)
    return b.det()

Usage:

sage: S = SymmetricFunctions(QQ)
sage: s = S.schur()

sage: f = s[2]

sage: m a = matrix([[f, 0], [0, f]])
sage: m
a
[s[2]    0]
[   0 s[2]]

sage: m.det()
a.det()
s[2, 2] + s[3, 1] + s[4]

sage: det(a)
s[2, 2] + s[3, 1] + s[4]

sage: kdet(a)
s[2]

Compare:

sage: f * f
s[2, 2] + s[3, 1] + s[4]

sage: f.kronecker_product(f)
s[2]

To go further and enable using a.det, one is tempted to define a method _matrix_determinant for the ring s using kdet, but since kdet uses det, this leads to a recursion error.

sage: s._matrix_determinant = kdet
sage: a = matrix([[f, 0], [0, f]])
sage: a.det()
Traceback (most recent call last)
...
RecursionError: maximum recursion depth exceeded while calling a Python object

Hopefully the workaround provided by the function kdet is still useful.