Skip to content

BUG: _VarArray can't handle MatrixVar #1044

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 17 commits into
base: master
Choose a base branch
from

Conversation

Zeroto521
Copy link
Contributor

fix #1043

Zeroto521 added 10 commits July 31, 2025 17:00
Simplifies and clarifies the logic for initializing _VarArray by restructuring type checks and error handling. Now uses f-strings for error messages and ensures consistent handling of empty lists and invalid types.
Updated the _VarArray class constructor to handle MatrixVariable inputs in addition to Variable, list, and tuple. Refactored pointer allocation logic into a helper function for improved code clarity and maintainability.
Introduces a new test to verify that addConsIndicator works correctly when the binary variable is a matrix variable, addressing issue scipopt#1043.
To fix "Storing unsafe C derivative of temporary Python reference"
The create_ptr function in _VarArray.__cinit__ no longer takes a separate size argument and instead uses len(vars) directly. This simplifies the function signature and reduces redundancy.
Inlined the pointer creation logic in _VarArray's __cinit__ method, removing the inner create_ptr function. This simplifies the code and improves readability while maintaining the same functionality.
The test now checks addConsIndicator with both activeone=True and activeone=False, and updates the objective to use binvar.sum().
Copy link

codecov bot commented Aug 3, 2025

Codecov Report

❌ Patch coverage is 90.00000% with 1 line in your changes missing coverage. Please review.
✅ Project coverage is 54.32%. Comparing base (6452ea6) to head (3b64e79).
⚠️ Report is 20 commits behind head on master.

Files with missing lines Patch % Lines
src/pyscipopt/scip.pxi 90.00% 1 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##           master    #1044      +/-   ##
==========================================
+ Coverage   54.13%   54.32%   +0.19%     
==========================================
  Files          22       23       +1     
  Lines        5045     5257     +212     
==========================================
+ Hits         2731     2856     +125     
- Misses       2314     2401      +87     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

Comment on lines 17 to +20
### Fixed
- Raised an error when an expression is used when a variable is required
- Fixed some compile warnings
- _VarArray can accept MatrixVariable now
Copy link
Contributor

@DominikKamp DominikKamp Aug 5, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
### Fixed
- Raised an error when an expression is used when a variable is required
- Fixed some compile warnings
- _VarArray can accept MatrixVariable now
- addConsIndicator() accepts MatrixVariable as binvar
### Fixed
- Raised an error when an expression is used when a variable is required
- Fixed some compile warnings

As far as I know, indicator constraints do not support matrix variables yet, which would require some documentation of this addition function.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There are many methods like addConsSOS1, addConsSOS2, addConsAnd, and more that use _VarArray
This pr doesn't work for addConsIndicator

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Okay, can we then add a passing test and mention in the changelog what works now?

Comment on lines +190 to +205
x = m.addVar(vtype="B")
binvar1 = m.addMatrixVar(((1, 1, 1)), vtype="B")
m.addConsIndicator(x >= 1, binvar1, activeone=True)
m.addConsIndicator(x <= 0, binvar1, activeone=False)

# test binvar with (2, 3) shape of matrix variable
y = m.addVar(vtype="B")
binvar2 = m.addMatrixVar(((2, 3)), vtype="B")
m.addConsIndicator(y >= 1, binvar2, activeone=True)
m.addConsIndicator(y <= 0, binvar2, activeone=False)

# test binvar with (2, 1) shape of list of lists
z = m.addVar(vtype="B")
binvar3 = [[m.addVar(vtype="B")], [m.addVar(vtype="B")]]
m.addConsIndicator(z >= 1, binvar3, activeone=True)
m.addConsIndicator(z <= 0, binvar3, activeone=False)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there somewhere documented when addConsIndicator() considers a matrix binary variable active?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

binvar1 and binvar2 both are matrix binvary

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I am confused. We add a test for addConsIndicator() although it does not work according to https://github.com/scipopt/PySCIPOpt/pull/1044/files#r2255663332? But it should pass in this form, so the description of addConsIndicator() needs to be extended to explain how a matrix binvar is handled. Are some entries or all entries required to be one so that the indicator constraint considers it active if activeone?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can't directly access _VarArray, so it has to test _VarArray indirectly via addConsIndicator.
If addConsIndicator works fine with a matrix binvar. _VarArray works fine with a matrix too.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

But addConsIndicator() does not work fine with a matrix variable since it only picks the first entry. The bug here rather seems to be that addConsIndicator() does not ensure that binvar is a variable. If this translation of a matrix variable into _VarArray is helpful somewhere, then it should be applied properly there and put on the list of added features, generalizing _VarArray alone without usecase is not enough, so maybe this should be combined with another change.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do you know if any other methods would use all the results of _VarArray? So we could test all elements.
I only met this case in my work.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Constraint addition methods, which get a list of variables like you mentioned in #1044 (comment), but for these I doubt that the ravelling is expected. So _VarArray is not designed for matrix variables, however, one could think about generalizing it to maintain the matrix structure, and if we then want to generalize all addition methods to matrix variables, we would need documented definitions how they are handled respectively. To fix a bug, adding an assertion into _VarArray that the given structure is not a list of lists of variables or a matrix variable and throwing an exception in addConsIndicator() if those are provided is the way to go.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@Joao-Dionisio what do you think about this. In my opinion, matrix is also a list. But _VarArray can’t handle matrix, so it’s a bug for _VarArray. This pr is done for that. So for addConsIndicator binvar type problem should be done in another pr not this one.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

_VarArray should not need to handle a proper matrix because addConsIndicator() currently does not support it. Letting _VarArray support one-dimensional matrices would be possible. But just calling ravel is too general for this, so there should be an exception if multiple dimensions are present.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

BUG: _VarArray can't handle MatrixVar
3 participants