Skip to content

Commit 5379f2e

Browse files
author
Release Manager
committed
gh-40176: Trac #40167: Fix incorrect parent reuse in matrix-vector multiplication over GF(2)
<!-- ^ Please provide a concise and informative title. --> <!-- ^ Don't put issue numbers in the title, do this in the PR description below. --> <!-- ^ For example, instead of "Fixes #12345" use "Introduce new method to calculate 1 + 2". --> <!-- v Describe your changes below in detail. --> <!-- v Why is this change required? What problem does it solve? --> <!-- v If this PR resolves an open issue, please link to it here. For example, "Fixes #12345". --> Fixes [#40167](#40167). This PR fixes a bug in `Matrix_mod2_dense._matrix_times_vector_` revealed in [#40167](#40167), where the parent of the resulting vector was incorrectly reused from the input vector. The regression was introduced in [PR #37375](#37375), which added an optimization to speed up matrix-vector multiplication when the matrix is square and matches the vector dimension. However, it failed to account for edge cases where the input vector's parent is not the full ambient vector space—for example, when working with subspaces. In this case, we can no longer assume that the ambient space is the vector's ambient space. In such cases, reusing the parent leads to incorrect coercion or a result vector with an invalid parent space. This patch introduces an explicit check: if the vector's parent is the full space `GF(2)^n`, it is reused; otherwise, a default parent is constructed to ensure correctness. ### Example (correct behavior restored) ```python sage: M = Matrix(GF(2), [[1, 1], [0, 1]]) sage: v = vector(GF(2), [0, 1]) sage: V = span([v]) # one-dimensional subspace of GF(2)^2 sage: image_basis = [M * b for b in V.basis()] sage: image = span(image_basis) sage: image.basis() == [(1, 1)] True # now returns True ``` ### 📝 Checklist <!-- Put an `x` in all the boxes that apply. --> - [x] The title is concise and informative. - [x] The description explains in detail what this PR is about. - [x] I have linked a relevant issue or discussion. - [x] I have created tests covering the changes. - [ ] I have updated the documentation and checked the documentation preview. ### ⌛ Dependencies <!-- List all open PRs that this PR logically depends on. For example, --> <!-- - #12345: short description why this is a dependency --> <!-- - #34567: ... --> URL: #40176 Reported by: Aolong Li Reviewer(s): Travis Scrimshaw
2 parents 5b324d1 + 6532b20 commit 5379f2e

File tree

3 files changed

+18
-4
lines changed

3 files changed

+18
-4
lines changed

build/pkgs/configure/checksums.ini

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
11
tarball=configure-VERSION.tar.gz
2-
sha1=2b82d3f61ce5242564303693ec5cf868bed70e67
3-
sha256=307a4306540a791edb795baad821ebc708a589960146c4a20d3d14aa730fc1ea
2+
sha1=11062cbee8ecac01543919cb9f8da3a38dbea65a
3+
sha256=80999cd87c7f1585cf63e873bd3a1725fa7630a4cbc1b96b2a1d35897cf77d39
Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
731c1bad33aa2dc17ded3fb92e76203331ecd3f5
1+
987b4a607790c21641793798e19ef977df1f78e8

src/sage/matrix/matrix_mod2_dense.pyx

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -677,9 +677,23 @@ cdef class Matrix_mod2_dense(matrix_dense.Matrix_dense): # dense or sparse
677677
sage: r1 = A*v1
678678
sage: r0.column(0) == r1
679679
True
680+
681+
Check that :issue:`40167` is fixed::
682+
683+
sage: M = matrix(GF(2), [[1,1],[0,1]])
684+
sage: v = vector(GF(2), [0, 1])
685+
sage: V = span([v]) # one-dimensional subspace of GF(2)^2
686+
sage: image_basis = [M * b for b in V.basis()]
687+
sage: image = span(image_basis)
688+
sage: image_basis[0] in image.basis()
689+
True
680690
"""
681691
cdef mzd_t *tmp
682-
if self._nrows == self._ncols and isinstance(v, Vector_mod2_dense):
692+
if (
693+
self._nrows == self._ncols and
694+
isinstance(v, Vector_mod2_dense) and
695+
v.parent().rank() == self._ncols # check if the parent of v is full rank
696+
):
683697
VS = v.parent()
684698
else:
685699
global VectorSpace

0 commit comments

Comments
 (0)