示例#1
0
 def _dual_apply(c, A, b, K):
     f, G, h, Kd = dualize_problem(c, A, b,
                                   K)  # max{ f @ y : G @ y == h, y in Kd}
     type_selectors = build_cone_type_selectors(Kd)
     G_ineq = G[:, type_selectors['+']]
     f_ineq = f[type_selectors['+']]
     G_free = G[:, type_selectors['fr']]
     f_free = f[type_selectors['fr']]
     G_dexp = G[:, type_selectors['de']]
     f_dexp = f[type_selectors['de']]
     G_soc = G[:, type_selectors['S']]
     f_soc = f[type_selectors['S']]
     f = np.concatenate((f_ineq, f_soc, f_dexp, f_free))
     G = sp.hstack((G_ineq, G_soc, G_dexp, G_free), format='csc')
     cones = {
         '+': np.count_nonzero(type_selectors['+']),
         'S': [Ki.len for Ki in Kd if Ki.type == 'S'],
         'de': len([Ki for Ki in Kd if Ki.type == 'de']),
         'fr': np.count_nonzero(type_selectors['fr'])
     }
     inv_data = {
         'A': A,
         'b': b,
         'K': K,
         'c': c,
         'type_selectors': type_selectors,
         'dual': True,
         'n': A.shape[1]
     }
     data = {'f': f, 'G': G, 'h': h, 'cone_dims': cones}
     return data, inv_data
示例#2
0
 def apply(c, A, b, K, params):
     """
     :return: G, h, cones, A_ecos, b_ecos --- where we expect
      a function call: sol = ecos.solve(c, G, h, cones, A_ecos, b_ecos)
     """
     for co in K:
         if co.type not in {'e', 'S', '+', '0'}:  # pragma: no cover
             msg = """
             ECOS only supports cones with labels in the set {"e", "S", "+", "0"}.
             The provided data includes an invalid cone labeled %s.
             """ % co.type
             raise RuntimeError(msg)
     type_selectors = build_cone_type_selectors(K)
     # find indices of A corresponding to equality constraints
     A_ecos = A[type_selectors['0'], :]
     b_ecos = -b[type_selectors['0']]  # move to RHS
     # Build "G, h".
     G_nonneg = -A[type_selectors['+'], :]
     h_nonneg = b[type_selectors['+']]
     G_soc = -A[type_selectors['S'], :]
     h_soc = b[type_selectors['S']]
     G_exp = -A[type_selectors['e'], :]
     h_exp = b[type_selectors['e']]
     G = sp.vstack([G_nonneg, G_soc, G_exp], format='csc')
     h = np.hstack((h_nonneg, h_soc, h_exp))
     # create cone dims dict for ECOS
     cones = {
         'l': int(np.sum(type_selectors['+'])),
         'e': int(np.sum(type_selectors['e']) / 3),
         'q': util.contiguous_selector_lengths(type_selectors['S'])
     }
     # ^ The block above probably has a bug. What happens when
     # two SOC constraints appear back-to-back?
     data = {
         'G': G,
         'h': h,
         'cones': cones,
         'A': A_ecos,
         'b': b_ecos,
         'c': c
     }
     inv_data = dict()
     return data, inv_data
示例#3
0
 def _primal_apply(c, A, b, K):
     inv_data = {'n': A.shape[1]}
     A, b, K, sep_K = separate_cone_constraints(A,
                                                b,
                                                K,
                                                dont_sep={'0', '+'})
     c = np.hstack([c, np.zeros(shape=(A.shape[1] - len(c)))])
     type_selectors = build_cone_type_selectors(K)
     # Below: inequality constraints that the "user" intended to give to MOSEK.
     A_ineq = A[type_selectors['+'], :]
     b_ineq = b[type_selectors['+']]
     # Below: equality constraints that the "user" intended to give to MOSEK
     A_z = A[type_selectors['0'], :]
     b_z = b[type_selectors['0']]
     # Finally: the matrix "A" and vector "u_c" that appear in the MOSEK documentation as the standard form for
     # an SDP that includes vectorized variables. We use "b" instead of "u_c". It's value in the MOSEK Task will
     # later be specified with MOSEK's "putconboundlist" function.
     A = -sp.vstack([A_ineq, A_z], format='csc')
     b = np.hstack([b_ineq, b_z])
     K = [Cone('+', A_ineq.shape[0]), Cone('0', A_z.shape[0])]
     # Return values
     data = {'A': A, 'b': b, 'K': K, 'sep_K': sep_K, 'c': c}
     return data, inv_data
示例#4
0
 def solve_via_data(data, params):
     import cvxpy as cp
     # linear program solving with cvxpy
     c = data['c']
     b = data['b']
     A = data['A']
     K = data['K']
     m, n = A.shape
     x = cp.Variable(n)
     for co in K:
         if co.type not in {'e', 'S', '+', '0', 'pow'}:  # pragma: no cover
             msg = """
             The CVXPY interface only supports cones with labels in the set
                 {"e", "S", "+", "0", "pow"}.
             The provided data includes an invalid cone labeled %s.
             """ % co.type
             raise RuntimeError(msg)
     type_selectors = build_cone_type_selectors(K)
     constraints = []
     cone_types = type_selectors.keys()
     if '0' in cone_types:
         tss = type_selectors['0']
         constraints.append(A[tss, :] @ x + b[tss] == 0)
     if 'e' in cone_types:
         rows = np.where(type_selectors['e'])[0][::3]
         expr1 = A[rows, :] @ x + b[rows]
         rows += 1
         expr2 = A[rows, :] @ x + b[rows]
         rows += 1
         expr3 = A[rows, :] @ x + b[rows]
         constraints.append(cp.constraints.ExpCone(expr1, expr3, expr2))
     if '+' in cone_types:
         tss = type_selectors['+']
         constraints.append(A[tss, :] @ x + b[tss] >= 0)
     if 'S' in cone_types or 'pow' in cone_types:
         idx = 0
         for co in K:
             if co.type == 'S':
                 # first component is epigraph variable
                 upper = A[idx, :] @ x + b[idx]
                 start = idx + 1
                 lower = A[start:(idx + co.len), :] @ x + b[start:(idx +
                                                                   co.len)]
                 # upper >= norm(lower, 2)
                 constraints.append(cp.constraints.SOC(upper, lower))
             elif co.type == 'pow':
                 # final component is hypograph variable
                 stop = idx + (co.len - 1)
                 upper = A[idx:stop, :] @ x + b[idx:stop]
                 lower = A[stop, :] @ x + b[stop]  # inclusive
                 weights = co.annotations['weights']
                 # np.prod(np.power(upper, weights)) >= abs(lower); upper >= 0.
                 constraints.append(
                     cp.constraints.PowConeND(upper, lower, weights))
             idx += co.len
     prob = cp.Problem(cp.Minimize(c @ x), constraints)
     d = params.copy()
     d.pop('cache_apply_data')
     d.pop('cache_raw_output')
     prob.solve(**d)
     return x, prob