Dense LinearExpression.to_constraint('==') keeps sign '==': repr raises KeyError, differs from sparse '='
Los mantenedores suelen responder en 1 día
Nadie ha tomado este issue todavía.
Evaluación
- Dificultad
- 2/5
- Tiempo estimado
- 1-3 horas
- Aptitud para principiantes
- 78/100
Línea de trabajo
Empieza con LinearExpression.to_constraint y compara cómo maneja los signos en los backends denso y disperso; el issue señala linopy/constants.py y el caso SIGN_EQ de test/test_store_conformance.py como referencias útiles. Comprueba cómo gestiona la ruta densa "==" y ejecuta la prueba de conformidad. El trabajo estará terminado cuando las restricciones densas almacenen "=", su representación funcione y se pueda eliminar el xfail de SIGN_EQ.
Escrito por el modelo de indexación a partir del texto del issue.
Descripción
[!NOTE]
The following content was generated by AI.
Version Checks
- I have confirmed this bug exists on the current
masterbranch of Linopy (95f6bfa4).
Issue Description
LinearExpression.to_constraint("==", rhs) stores the sign verbatim as "==" on the dense backend, while the sparse (CSR) backend normalizes it to "=". linopy's canonical equality sign is EQUAL = "=" (linopy/constants.py; "==" is only in SIGNS_alternative), so the dense backend is the wrong one. Consequences on dense:
repr()of the constraint raisesKeyError: '=='(SIGNS_prettyonly knows"=").- The un-normalized
"=="is carried into the model bym.add_constraints(con).
x == 1, (1*x) == 1 and m.add_constraints(1*x, "==", 1) are fine on both backends; only the to_constraint path skips sign normalization.
Found while building the dense/sparse conformance suite for #1019 (test/test_store_conformance.py, the case marked SIGN_EQ, currently a strict xfail on sparse).
Reproducible Example
from linopy import Model
for sparse in (False, True):
m = Model(sparse=sparse)
x = m.add_variables(name="x")
con = (1 * x).to_constraint("==", 1)
m.add_constraints(con, name="c")
print(f"sparse={sparse}: sign={con.sign.item()!r}, stored={m.constraints['c'].sign.item()!r}")
try:
print(repr(con))
except KeyError as e:
print(f"repr -> KeyError: {e}")
Output:
sparse=False: sign='==', stored='=='
repr -> KeyError: '=='
sparse=True: sign='=', stored='='
Constraint (unassigned)
-----------------------
+1 x = 1.0
Traceback of the dense repr (without try/except)
File "linopy/constraints.py", line 581, in __repr__
f"{header_string}\n{'-' * len(header_string)}\n{expr} {SIGNS_pretty[self.sign.item()]} {self.rhs.item()}"
~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^
KeyError: '=='
Expected Behavior
Dense to_constraint("==", ...) normalizes the sign to "=", as sparse already does and as x == 1 / add_constraints(lhs, "==", rhs) do, so repr works and both backends agree. The xfail in the conformance suite can then be dropped.
- Lenguaje dominante
- Python
- Estrellas
- 262
- Forks
- 89
- Merge medio
- 2 d 5 h
- PR fusionados (30 d)
- 36
Preparar el entorno
- Sin Dockerfile ni archivo de Docker Compose
- Tiene una plantilla de pull request
- Leer la guía de contribución
Primeros pasos
- Lee el issue completo y luego la guía de contribución del proyecto.
- Comenta en el issue que vas a ocuparte — evita que dos personas hagan lo mismo.
- Haz un fork del repositorio y trabaja en una rama.
- Abre un pull request que haga referencia al número del issue.
Más de PyPSA/linopy
-
Constant LinearExpression * multi-term LinearExpression raises TypeError (mirrored product works)Abiertobug
Dificultad 2/5 1-3 horas Aptitud para principiantes 68/100
Los mantenedores suelen responder en 1 día
-
bug solver interface
Dificultad 2/5 1-3 horas Aptitud para principiantes 84/100
Los mantenedores suelen responder en 1 día
-
Drop the per-nonzero cell array from `Store.terms()` to cut transient memory in the dense LP exportAbiertoperformance refactor v1
Dificultad 4/5 3-5 días Aptitud para principiantes 58/100
Los mantenedores suelen responder en 1 día
-
Long-form inputs: tables as bounds, coefficients, constants and rhs; relation group-byPosiblemente ocupada @FabianHofmann la tomó hace 1 día. Abiertorefactor sparse
Dificultad 4/5 3-5 días Aptitud para principiantes 48/100
PyPSA/linopy#1049 · 1 comentario ·
Los mantenedores suelen responder en 1 día
-
Meta: separate dense and sparse stores from the expression and constraint frontendPosiblemente ocupada @Rishabhkanhaiya la tomó hace 18 días. Abiertodiscussion refactor sparse
Dificultad 5/5 Más de una semana Aptitud para principiantes 25/100
PyPSA/linopy#1019 · 1 comentario ·
Los mantenedores suelen responder en 1 día
Todos los issues de PyPSA/linopy
Issues similares
-
Dificultad 2/5 1-3 horas Aptitud para principiantes 75/100
google-agentic-commerce/AP2#388 ·
-
area:codegen backend:cuda backend:hip bug direction:input
Dificultad 2/5 1-3 horas Aptitud para principiantes 78/100
CrossGL/crosstl#3061 · 1 comentario ·
Los mantenedores suelen responder en 1 día
-
Dificultad 2/5 1-3 horas Aptitud para principiantes 85/100
rlaope/oh-my-hermes#2304 ·
Los mantenedores suelen responder en 1 día
-
Dificultad 2/5 1-3 horas Aptitud para principiantes 85/100
mochan-tk/agentic-dev-kit-for-codex#64 ·
Los mantenedores suelen responder en 1 día
-
Windows ARM memory-leakAbiertobug docs performance
Dificultad 1/5 Menos de una hora Aptitud para principiantes 85/100
Los mantenedores suelen responder en 3 días