cvxpy icon indicating copy to clipboard operation
cvxpy copied to clipboard

AttributeError: 'reshape' object has no attribute '_lazy_canonical_form'. Did you mean: 'canonical_form'?

Open raff0722 opened this issue 1 year ago • 6 comments

Description Although the problem is convex and the formulation DCP, the compilation fails.

To Reproduce import cvxpy as cp x = cp.Variable(d) objective = cp.Minimize( cp.sum_squares(A@x) + cp.mixed_norm( cp.hstack( [B@x, C@x, np.ones(d)] ), 1, 2 ) )

Expected behavior Solution to the convex problem.

Output

                                 CVXPY
                                 v1.5.1

=============================================================================== (CVXPY) May 30 11:40:45 AM: Your problem has 4096 variables, 0 constraints, and 0 parameters. (CVXPY) May 30 11:40:45 AM: It is compliant with the following grammars: DCP, DQCP (CVXPY) May 30 11:40:45 AM: (If you need to solve this problem multiple times, but with different data, consider using parameters.) (CVXPY) May 30 11:40:45 AM: CVXPY will first compile your problem; then, it will invoke a numerical solver to obtain a solution. (CVXPY) May 30 11:40:45 AM: Your problem is compiled with the CPP canonicalization backend.

                              Compilation

(CVXPY) May 30 11:40:45 AM: Compiling problem (target solver=CLARABEL). (CVXPY) May 30 11:40:45 AM: Reduction chain: Dcp2Cone -> CvxAttr2Constr -> ConeMatrixStuffing -> CLARABEL (CVXPY) May 30 11:40:45 AM: Applying reduction Dcp2Cone (CVXPY) May 30 11:40:45 AM: Applying reduction CvxAttr2Constr (CVXPY) May 30 11:40:45 AM: Applying reduction ConeMatrixStuffing Traceback (most recent call last): File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\utilities\performance_utils.py", line 37, in _lazyprop return getattr(self, attr_name) ^^^^^^^^^^^^^^^^^^^^^^^^ AttributeError: 'reshape' object has no attribute '_lazy_canonical_form'. Did you mean: 'canonical_form'?

During handling of the above exception, another exception occurred:

Traceback (most recent call last): File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\utilities\performance_utils.py", line 37, in _lazyprop return getattr(self, attr_name) ^^^^^^^^^^^^^^^^^^^^^^^^ AttributeError: 'Sum' object has no attribute '_lazy_canonical_form'. Did you mean: 'canonical_form'?

During handling of the above exception, another exception occurred:

Traceback (most recent call last): File "c:\Users\raff\Python\Localization\twoD_deblurr_image\Problem_data\conf1\sam_fM_check_eps2\main.py", line 85, in main() File "c:\Users\raff\Python\Localization\twoD_deblurr_image\Problem_data\conf1\sam_fM_check_eps2\main.py", line 70, in main MAP_eps.main(par, sam) File "C:\Users\raff\Python\Localization\twoD_deblurr_image\MAP_eps.py", line 115, in main res = problem.solve(verbose=1, max_iter=20000) # The optimal value for x is stored in x.value. ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\problems\problem.py", line 503, in solve return solve_func(self, *args, **kwargs) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\problems\problem.py", line 1073, in _solve data, solving_chain, inverse_data = self.get_problem_data( ^^^^^^^^^^^^^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\problems\problem.py", line 696, in get_problem_data data, inverse_data = solving_chain.apply(self, verbose) ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\reductions\chain.py", line 76, in apply problem, inv = r.apply(problem) ^^^^^^^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\reductions\dcp2cone\cone_matrix_stuffing.py", line 379, in apply params_to_problem_data = extractor.affine(expr_list) ^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\utilities\coeff_extractor.py", line 71, in affine op_list = [e.canonical_form[0] for e in expr_list] ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\utilities\coeff_extractor.py", line 71, in op_list = [e.canonical_form[0] for e in expr_list] ^^^^^^^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\utilities\performance_utils.py", line 39, in _lazyprop setattr(self, attr_name, func(self)) ^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\utilities\canonical.py", line 45, in canonical_form return self.canonicalize() ^^^^^^^^^^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\atoms\atom.py", line 322, in canonicalize obj, constr = arg.canonical_form ^^^^^^^^^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\utilities\performance_utils.py", line 39, in _lazyprop setattr(self, attr_name, func(self)) ^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\utilities\canonical.py", line 45, in canonical_form return self.canonicalize() ^^^^^^^^^^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\atoms\atom.py", line 327, in canonicalize graph_obj, graph_constr = self.graph_implementation(arg_objs, ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ File "C:\Users\raff\Python\Localization\env\Lib\site-packages\cvxpy\atoms\affine\sum.py", line 94, in graph_implementation const_shape = (arg_objs[0].shape[1],) ~~~~~~~~~~~~~~~~~^^^ IndexError: tuple index out of range

Version

  • OS: Windows
  • CVXPY Version: 1.5.1

Additional context Add any other context about the problem here.

raff0722 avatar May 30 '24 09:05 raff0722

I was able to reproduce the issue.

SteveDiamond avatar May 30 '24 20:05 SteveDiamond

import cvxpy as cp
import numpy as np
d = 10
np.random.seed(0)
A = np.random.randn(5, 10)
B = np.random.randn(4, 10)
C = np.random.randn(3, 10)
x = cp.Variable(d)
objective = cp.Minimize(cp.sum_squares(A@x) + cp.mixed_norm(cp.hstack([B @ x, C @ x, np.ones(d)]), 1, 2))

I was unable to reproduce the issue with this script. Is there any info I'm missing?

PTNobel avatar May 30 '24 20:05 PTNobel

You have to solve the problem.

SteveDiamond avatar May 30 '24 20:05 SteveDiamond

@raff0722 you're hitting this bug https://github.com/cvxpy/cvxpy/issues/1963 In your problem mixed_norm isn't doing anything different than regular norm because the hstack output is 1D. Possibly you didn't mean for it to be 1D. We follow NumPy conventions for hstack, vstack, concatenate, etc.

SteveDiamond avatar May 30 '24 20:05 SteveDiamond

Here's the minimized script:

import cvxpy as cp
import numpy as np
d = 10
objective = cp.Minimize(0)
constr = [cp.mixed_norm(cp.hstack([np.ones(d)]), 1, 2) <= 1]
cp.Problem(objective, constr).solve()

It is worth at least fixing its error message.

PTNobel avatar May 30 '24 20:05 PTNobel

@raff0722 you're hitting this bug #1963 In your problem mixed_norm isn't doing anything different than regular norm because the hstack output is 1D. Possibly you didn't mean for it to be 1D. We follow NumPy conventions for hstack, vstack, concatenate, etc.

Yes, that was the issue. Thank you! I expected a matrix with d rows and 3 columns. Now I used bmat as follows

cp.mixed_norm( cp.bmat([ [B@x], [C@x], [np.ones(d)] ), 1, 2 )

which works.

However, I find the doc about bmat a bit confusing. It says

Takes a list of lists. Each internal list is stacked horizontally. The internal lists are stacked vertically.

Morevoer, based on Meaning in image I would expect that I have to transpose the matrix, i.e., use

cp.mixed_norm( cp.bmat( [ [B@x], [C@x], [np.ones(d)] ] ).T, 1, 2 )

which however gave the wrong result.

raff0722 avatar May 31 '24 06:05 raff0722