@@ -12,81 +12,34 @@ function conicconstraintdata(m::Model)
1212 stoch = getStructure (m)
1313 parent = stoch. parent
1414 numMasterCols = 0
15- if parent != nothing
15+ if parent != = nothing
1616 numMasterCols = parent. numCols
1717 end
1818 v = Symbol[]
19- obj_coeff = zeros (m. numCols)
20- for i in eachindex (m. obj. aff. vars)
21- var = m. obj. aff. vars[i]
22- coeff = m. obj. aff. coeffs[i]
23- obj_coeff[var. col] = coeff
24- end
2519
2620 var_cones = Any[cone for cone in m. varCones]
2721 con_cones = Any[]
2822 nnz = 0
2923
24+ numSDPRows, numSymRows, nnz = JuMP. getSDrowsinfo (m)
25+
3026 linconstr:: Vector{LinearConstraint} = m. linconstr
3127 numLinRows = length (linconstr)
32- numBounds = 0
33- nonNeg = Int[]
34- nonPos = Int[]
35- free = Int[]
36- zeroVar = Int[]
37- for i in 1 : m. numCols
38- seen = false
39- lb, ub = m. colLower[i], m. colUpper[i]
40- for (_,cone) in m. varCones
41- if i in cone
42- seen = true
43- @assert lb == - Inf && ub == Inf
44- break
45- end
46- end
47-
48- if ! seen
49- if lb != - Inf && lb != 0
50- numBounds += 1
51- end
52- if ub != Inf && ub != 0
53- numBounds += 1
54- end
55- if lb == 0 && ub == 0
56- push! (zeroVar, i)
57- elseif lb == 0
58- push! (nonNeg, i)
59- elseif ub == 0
60- push! (nonPos, i)
61- else
62- push! (free, i)
63- end
64- end
65- end
6628
67- if ! isempty (zeroVar)
68- push! (var_cones, (:Zero ,zeroVar))
69- end
70- if ! isempty (nonNeg)
71- push! (var_cones, (:NonNeg ,nonNeg))
72- end
73- if ! isempty (nonPos)
74- push! (var_cones, (:NonPos ,nonPos))
75- end
76- if ! isempty (free)
77- push! (var_cones, (:Free ,free))
78- end
29+ numBounds = JuMP. variable_range_to_cone! (var_cones, m)
7930
8031 nnz += numBounds
8132 for c in 1 : numLinRows
8233 nnz += length (linconstr[c]. terms. coeffs)
8334 end
8435
85- numSOCRows = 0
86- for con in m. socconstr
87- numSOCRows += length (con. normexpr. norm. terms) + 1
88- end
89- numRows = numLinRows + numBounds + numSOCRows
36+ numSOCRows = JuMP. getNumSOCRows (m)
37+ numNormRows = length (m. socconstr)
38+
39+ numRows = numLinRows + numBounds + numSOCRows + numSDPRows + numSymRows
40+
41+ # constr_to_row is not used but fill_bounds_constr! and fillconstr! for SDP needs them
42+ constr_to_row = Array {Vector{Int}} (numBounds + 2 * length (m. sdpconstr))
9043
9144 b = Array (Float64, numRows)
9245
@@ -98,134 +51,56 @@ function conicconstraintdata(m::Model)
9851 V_s = Float64[]
9952
10053 # Fill it up
101- nnz = 0
10254 tmprow = JuMP. IndexedVector (Float64,m. numCols)
103- tmpelts = tmprow. elts
104- tmpnzidx = tmprow. nzidx
105- nonneg_rows = Int[]
106- nonpos_rows = Int[]
107- eq_rows = Int[]
108- for c in 1 : numLinRows
109- if linconstr[c]. lb == - Inf
110- b[c] = linconstr[c]. ub
111- push! (nonneg_rows, c)
112- elseif linconstr[c]. ub == Inf
113- b[c] = linconstr[c]. lb
114- push! (nonpos_rows, c)
115- elseif linconstr[c]. lb == linconstr[c]. ub
116- b[c] = linconstr[c]. lb
117- push! (eq_rows, c)
118- else
119- error (" We currently do not support ranged constraints with conic solvers" )
120- end
12155
122- JuMP. assert_isfinite (linconstr[c]. terms)
123- coeffs = linconstr[c]. terms. coeffs
124- vars = linconstr[c]. terms. vars
125- # eliminated collect duplicates
126- for ind in eachindex (coeffs)
127- if vars[ind]. m === parent
128- push! (I_m, c)
129- push! (J_m, vars[ind]. col)
130- push! (V_m, coeffs[ind])
131- else
132- push! (I_s, c)
133- push! (J_s, vars[ind]. col)
134- push! (V_s, coeffs[ind])
135- end
136- end
56+ JuMP. fillconstrRHS! (b, con_cones, 0 , m. linconstr)
57+ if numMasterCols > 0
58+ JuMP. fillconstrLHS! (I_m, J_m, V_m, tmprow, 0 , m. linconstr, parent, true )
13759 end
60+ c = JuMP. fillconstrLHS! (I_s, J_s, V_s, tmprow, 0 , m. linconstr, m, true )
13861
139- c = numLinRows
140- bndidx = 0
14162 for idx in 1 : m. numCols
142- lb = m. colLower[idx]
14363 # identify integrality information
14464 push! (v, m. colCat[idx])
145- if lb != - Inf && lb != 0
146- bndidx += 1
147- nnz += 1
148- c += 1
149- push! (I_s, c)
150- push! (J_s, idx)
151- push! (V_s, 1.0 )
152- b[c] = lb
153- push! (nonpos_rows, c)
154- end
155- ub = m. colUpper[idx]
156- if ub != Inf && ub != 0
157- bndidx += 1
158- c += 1
159- push! (I_s, c)
160- push! (J_s, idx)
161- push! (V_s, 1.0 )
162- b[c] = ub
163- push! (nonneg_rows, c)
164- end
16565 end
66+ c, d = JuMP. fill_bounds_constr! (I_s, J_s, V_s, b, con_cones, constr_to_row, c, 0 , m)
67+
68+ @assert c == numLinRows + numBounds
69+ @assert d == numBounds
16670
167- if ! isempty (nonneg_rows)
168- push! (con_cones, (:NonNeg ,nonneg_rows))
71+ JuMP. fillconstrRHS! (b, con_cones, c, m. socconstr)
72+ if numMasterCols > 0
73+ JuMP. fillconstrLHS! (I_m, J_m, V_m, tmprow, c, m. socconstr, parent, true )
16974 end
170- if ! isempty (nonpos_rows)
171- push! (con_cones, (:NonPos ,nonpos_rows))
75+ c = JuMP. fillconstrLHS! (I_s, J_s, V_s, tmprow, c, m. socconstr, m, true )
76+
77+ @assert c == numLinRows + numBounds + numSOCRows
78+
79+ if numMasterCols > 0
80+ c, d = JuMP. fillconstr! (I_m, J_m, V_m, b, con_cones, tmprow, constr_to_row, c, d, m. sdpconstr, m, true )
17281 end
173- if ! isempty (eq_rows)
174- push! (con_cones, (:Zero ,eq_rows))
82+ c, d = JuMP. fillconstr! (I_s, J_s, V_s, b, con_cones, tmprow, constr_to_row, c, d, m. sdpconstr, m, true )
83+
84+ if c < length (b)
85+ # This happens for example when symmetry constraints are dropped with SDP
86+ resize! (b, c)
17587 end
176- @assert c == numLinRows + numBounds
17788
178- tmpelts = tmprow. elts
179- tmpnzidx = tmprow. nzidx
180- socidx = 0
181- for con in m. socconstr
182- socidx += 1
183- expr = con. normexpr
184- c += 1
185- soc_start = c
186- JuMP. collect_expr! (m, tmprow, expr. aff)
187- nnz = tmprow. nnz
188- indices = tmpnzidx[1 : nnz]
189- vars = expr. aff. vars
190- for i in eachindex (vars)
191- if vars[i]. m === parent
192- push! (I_m, c)
193- push! (J_m, indices[i])
194- push! (V_m, tmpelts[indices[i]])
195- else
196- push! (I_s, c)
197- push! (J_s, indices[i])
198- push! (V_s, tmpelts[indices[i]])
199- end
200- end
201- b[c] = - expr. aff. constant
202- for term in expr. norm. terms
203- c += 1
204- JuMP. collect_expr! (m, tmprow, term)
205- nnz = tmprow. nnz
206- indices = tmpnzidx[1 : nnz]
207- vars = term. vars
208- for i = 1 : length (vars)
209- if vars[i]. m == parent
210- push! (I_m, c)
211- push! (J_m, indices[i])
212- push! (V_m, - expr. coeff* tmpelts[indices[i]])
213- else
214- push! (I_s, c)
215- push! (J_s, indices[i])
216- push! (V_s, - expr. coeff* tmpelts[indices[i]])
217- end
218- end
219- b[c] = expr. coeff* term. constant
220- end
221- push! (con_cones, (:SOC , soc_start: c))
89+ f_s = JuMP. prepAffObjective (m)
90+
91+ # The conic MPB interface defines conic problems as
92+ # always being minimization problems, so flip if needed
93+ m. objSense == :Max && scale! (f_s, - 1.0 )
94+
95+ if numMasterCols > 0
96+ JuMP. rescaleSDcols! (spzeros (numMasterCols), J_m, V_m, parent)
22297 end
223- @assert c == numLinRows + numBounds + numSOCRows
98+ JuMP . rescaleSDcols! (f_s, J_s, V_s, m)
22499
225100 A = sparse (I_m, J_m, V_m, numRows, numMasterCols)
226101 B = sparse (I_s, J_s, V_s, numRows, m. numCols)
227-
228- return obj_coeff , A, B, b, var_cones, con_cones, v
102+
103+ return f_s , A, B, b, var_cones, con_cones, v
229104end
230105
231106function BendersBridge (m:: Model , master_solver, sub_solver)
0 commit comments