def run_process(f, pipe): xbar = Parameter(n, value=np.zeros(n)) u = Parameter(n, value=np.zeros(n)) f += (rho/2)*sum_squares(x - xbar + u) prox = Problem(Minimize(f)) # ADMM loop. while True: prox.solve() pipe.send(x.value) xbar.value = pipe.recv() u.value += x.value - xbar.value
def test_warm_start(self): """Test warm start. """ m = 200 n = 100 np.random.seed(1) A = np.random.randn(m, n) b = Parameter(m) # Construct the problem. x = Variable(n) prob = Problem(Minimize(sum_squares(A * x - b))) b.value = np.random.randn(m) result = prob.solve(warm_start=False) result2 = prob.solve(warm_start=True) self.assertAlmostEqual(result, result2) b.value = np.random.randn(m) result = prob.solve(warm_start=True) result2 = prob.solve(warm_start=False) self.assertAlmostEqual(result, result2) pass
def test_parametric(self): """Test solve parametric problem vs full problem""" x = Variable() a = 10 # b_vec = [-10, -2., 2., 3., 10.] b_vec = [-10, -2.] for solver in self.solvers: print(solver) # Solve from scratch with no parameters x_full = [] obj_full = [] for b in b_vec: obj = Minimize(a * (x ** 2) + b * x) constraints = [0 <= x, x <= 1] prob = Problem(obj, constraints) prob.solve(solver=solver) x_full += [x.value] obj_full += [prob.value] # Solve parametric x_param = [] obj_param = [] b = Parameter() obj = Minimize(a * (x ** 2) + b * x) constraints = [0 <= x, x <= 1] prob = Problem(obj, constraints) for b_value in b_vec: b.value = b_value prob.solve(solver=solver) x_param += [x.value] obj_param += [prob.value] print(x_full) print(x_param) for i in range(len(b_vec)): self.assertItemsAlmostEqual(x_full[i], x_param[i], places=3) self.assertAlmostEqual(obj_full[i], obj_param[i])
def test_lasso(self): # Solve the following consensus problem using ADMM: # Minimize sum_squares(A*x - b) + gamma*norm(x,1) # Problem data. m = 100 n = 75 np.random.seed(1) A = np.random.randn(m,n) b = np.random.randn(m) # Separate penalty from regularizer. x = Variable(n) gamma = Parameter(nonneg = True) funcs = [sum_squares(A*x - b), gamma*norm(x,1)] p_list = [Problem(Minimize(f)) for f in funcs] probs = Problems(p_list) # Solve via consensus. gamma.value = 1.0 probs.solve(method = "consensus", rho_init = 1.0, max_iter = 50) print("Objective:", probs.value) print("Solution:", x.value)
u[:, k] <= umax] # input interval constraint objective += quad_form(x[:, Np] - xref, QN) prob = Problem(Minimize(objective), constraints) # Simulate in closed loop len_sim = 15 # simulation length (s) nsim = int(len_sim / Ts) # simulation length(timesteps) xsim = np.zeros((nsim, nx)) usim = np.zeros((nsim, nu)) tsol = np.zeros((nsim, 1)) tsim = np.arange(0, nsim) * Ts # uminus1_val = uinit # initial previous measured input is the input at time instant -1. time_start = time.time() for i in range(nsim): x_init.value = x0 # set value to the x_init cvx parameter to x0 time_start = time.time() prob.solve(solver=OSQP, warm_start=True) tsol[i] = 1000 * (time.time() - time_start) uMPC = u[:, 0].value usim[i, :] = uMPC x0 = Ad.dot(x0) + Bd.dot(uMPC) xsim[i, :] = x0 # uminus1_val = uMPC # or a measurement if the input is affected by noise time_sim = time.time() - time_start # In[Plot time traces] fig, axes = plt.subplots(3, 1, figsize=(10, 10))
# with a (non-convex) cardinality constraint. # Generate data. np.random.seed(1) N = 50 M = 40 n = 10 data = [] for i in range(N): data += [(1, np.random.normal(1.0, 2.0, (n, 1)))] for i in range(M): data += [(-1, np.random.normal(-1.0, 2.0, (n, 1)))] # Construct problem. gamma = Parameter(nonneg=True) gamma.value = 0.1 # 'a' is a variable constrained to have at most 6 non-zero entries. a = Card(n, k=6) b = Variable() slack = [pos(1 - label*(sample.T*a - b)) for (label, sample) in data] objective = Minimize(norm(a, 2) + gamma*sum(slack)) p = Problem(objective) # Extensions can attach new solve methods to the CVXPY Problem class. p.solve(method="admm") # Count misclassifications. error = 0 for label, sample in data: if not label*(a.value.T*sample - b.value)[0] >= 0: error += 1
L = Parameter(n) U = Parameter(n) f = lambda x: sum_squares(A*x - b) prob = Problem(Minimize(f(x)), [L <= x, x <= U]) visited = 0 best_solution = numpy.inf best_x = 0 nodes = PriorityQueue() nodes.put((numpy.inf, 0, -numpy.ones(n), numpy.ones(n), 0)) while not nodes.empty(): visited += 1 # Evaluate the node with the lowest lower bound. _, _, L_val, U_val, idx = nodes.get() L.value = L_val U.value = U_val lower_bound = prob.solve() upper_bound = f(numpy.sign(x.value)).value best_solution = min(best_solution, upper_bound) if upper_bound == best_solution: best_x = numpy.sign(x.value) # Add new nodes if not at a leaf and the branch cannot be pruned. if idx < n and lower_bound < best_solution: for i in [-1, 1]: L_val[idx] = U_val[idx] = i nodes.put((lower_bound, i, L_val.copy(), U_val.copy(), idx + 1)) print("Nodes visited: %s out of %s" % (visited, 2**(n+1)-1)) print("Optimal solution:", best_solution) print(best_x)
# Simulate in closed loop nsim = int(len_sim / Ts) # simulation length(timesteps) xsim = np.zeros((nsim, nx)) ysim = np.zeros((nsim, ny)) gsim = np.zeros((nsim, ng)) tsol = np.zeros((nsim, 1)) tsim = np.arange(0, nsim) * Ts gMPC = ginit # initial previous measured input is the input at time instant -1. time_start = time.time() for i in range(nsim): yold = Cd @ x0 + Dd @ gMPC ysim[i, :] = yold x_init.value = x0 # set value to the x_init cvx parameter to x0 gminus1.value = gMPC yminus1.value = yold r.value = np.array(2 * [1.0]) # Reference output time_start = time.time() prob.solve(solver=OSQP, warm_start=True) tsol[i] = 1000 * (time.time() - time_start) gMPC = g[:, 0].value gsim[i, :] = gMPC x0 = Ad.dot(x0) + Bd.dot(gMPC) xsim[i, :] = x0 time_sim = time.time() - time_start
y_sim = np.zeros((n_sim, ny)) g_sim = np.zeros((n_sim, ng)) t_MPC = np.zeros((n_sim, 1)) t_sim = np.arange(0, n_sim) * Ts g_step_old = gm1 # initial previous measured input is the input at time instant -1. x_step = x0 y_step_old = y0 time_start = time.time() for i in range(n_sim): x_sim[i, :] = x_step # MPC Control law computation time_start = time.time() x_init.value = x_step # set value to the x_init cvx parameter to x0 gminus1.value = g_step_old yminus1.value = y_step_old r.value = np.array(2 * [1.0]) # Reference output prob.solve(solver=OSQP, warm_start=True) g_step = g[:, 0].value time_MPC = 1000 * (time.time() - time_start) t_MPC[i] = time_MPC # MPC control law computation time y_step = Cd @ x_step + Dd @ g_step y_sim[i, :] = y_step g_sim[i, :] = g_step # System update x_step = Ad @ x_step + Bd @ g_step y_step_old = y_step # like an additional state
prob = Problem(Minimize(objective), constraints) # Simulate in closed loop nsim = int(len_sim/Ts) # simulation length(timesteps) xsim = np.zeros((nsim, nx)) ysim = np.zeros((nsim, ny)) usim = np.zeros((nsim, nu)) tsol = np.zeros((nsim, 1)) tsim = np.arange(0, nsim)*Ts uMPC = ginit # initial previous measured input is the input at time instant -1. time_start = time.time() for i in range(nsim): ysim[i, :] = Cd @ x0 x_init.value = x0 # set value to the x_init cvx parameter to x0 uminus1.value = uMPC time_start = time.time() prob.solve(solver=OSQP, warm_start=True) tsol[i] = 1000*(time.time() - time_start) uMPC = u[:, 0].value usim[i, :] = uMPC x0 = Ad.dot(x0) + Bd.dot(uMPC) xsim[i, :] = x0 time_sim = time.time() - time_start # In[Plot time traces] fig, axes = plt.subplots(3, 1, figsize=(10, 10))
def calculate_portfolio(cvxtype, returns_function, long_only, exp_return, selected_solver, max_pos_size, ticker_list): assert cvxtype in ['minimize_risk','maximize_return'] """ Variables: mu is the vector of expected returns. sigma is the covariance matrix. gamma is a Parameter that trades off risk and return. x is a vector of stock holdings as fractions of total assets. """ gamma = Parameter(nonneg=True) gamma.value = 1 returns, stocks, betas = returns_function cov_mat = returns.cov() Sigma = cov_mat.values # np.asarray(cov_mat.values) w = Variable(len(cov_mat)) # #number of stocks for portfolio weights risk = quad_form(w, Sigma) #expected_variance => w.T*C*w = quad_form(w, C) # num_stocks = len(cov_mat) if cvxtype == 'minimize_risk': # Minimize portfolio risk / portfolio variance if long_only == True: prob = Problem(Minimize(risk), [sum(w) == 1, w > 0 ]) # Long only else: prob = Problem(Minimize(risk), [sum(w) == 1]) # Long / short elif cvxtype == 'maximize_return': # Maximize portfolio return given required level of risk #mu #Expected return for each instrument #expected_return = mu*x #risk = quad_form(x, sigma) #objective = Maximize(expected_return - gamma*risk) #p = Problem(objective, [sum_entries(x) == 1]) #result = p.solve() mu = np.array([exp_return]*len(cov_mat)) # mu is the vector of expected returns. expected_return = np.reshape(mu,(-1,1)).T * w # w is a vector of stock holdings as fractions of total assets. objective = Maximize(expected_return - gamma*risk) # Maximize(expected_return - expected_variance) if long_only == True: constraints = [sum(w) == 1, w > 0] else: #constraints=[sum_entries(w) == 1,w <= max_pos_size, w >= -max_pos_size] constraints=[sum(w) == 1] prob = Problem(objective, constraints) prob.solve(solver=selected_solver) weights = [] for weight in w.value: weights.append(float(weight)) if cvxtype == 'maximize_return': optimal_weights = {"Optimal expected return":expected_return.value, "Optimal portfolio weights":np.round(weights,2), "tickers": ticker_list, "Optimal risk": risk.value*100 } elif cvxtype == 'minimize_risk': optimal_weights = {"Optimal portfolio weights":np.round(weights,2), "tickers": ticker_list, "Optimal risk": risk.value*100 } return optimal_weights
def main(): class MyParser(argparse.ArgumentParser): def error(self, message): sys.stderr.write('error: %s\n' % message) self.print_help() sys.exit(2) parser = MyParser() parser.add_argument("-f", "--file", dest="filename", help="data file in CSV format", metavar="FILENAME") parser.add_argument("-o", "--output", dest="output", help="output in CSV format", metavar="OUTPUT") parser.add_argument("-ofig", "--outfigures", dest="outfigures", help="output plots in PDF format", metavar="OUTFIGURES") parser.add_argument("-t", "--threshold", dest="threshold", help="threshold distance", metavar="THRESHOLD") parser.add_argument("-r", "--regularization", dest="regularization", help="tv, tviso, divergence, tvtrace", metavar="REGULARIZATION") parser.add_argument("-n", "--nsolutions", dest="nsolutions", help="number of solutions", metavar="NSOLUTIONS") parser.add_argument("-s", "--solver", dest="solver", help="solver (cvxopt, ecos)", metavar="SOLVER") results = parser.parse_args() figure_outfile = "figureoutput.pdf" if results.outfigures is None else results.outfigures csv_outfile = "fittedout.csv" if results.output is None else results.output CUTOFF = 16 if results.threshold is None else float(results.threshold) REGULARIZATION = "tvnorm" if results.regularization is None else results.regularization N_SOLUTIONS = 10 if results.nsolutions is None else int( float(results.nsolutions)) coords, deflection, boundary = read_data(results.filename) # let's see if we have gridded data. If we do, then use the implicit data grid for all computations x_obs_positions = sorted(set(coords[:, 0])) y_obs_positions = sorted(set(coords[:, 1])) dx = abs(x_obs_positions[1] - x_obs_positions[0]) dy = abs(y_obs_positions[1] - y_obs_positions[0]) N = len(x_obs_positions) M = len(y_obs_positions) boundary2d = boundary.reshape((N, M)) mask = np.zeros(boundary2d.shape) for r in range(boundary2d.shape[1]): pts = np.where(boundary2d[:, r] == 1) if (len(pts[0]) > 0): mini = (min(min(pts))) maxi = max(max(pts)) mask[mini:maxi, r] = 1 distances2d = -ndimage.distance_transform_edt( mask) + ndimage.distance_transform_edt(1 - mask) distances2d = distances2d.flatten() condition_inside = distances2d <= 0 condition_outside = (distances2d > 0) * (distances2d <= CUTOFF) del distances2d, mask, boundary2d gc.collect() x_out = np.array(coords[condition_outside, 0] / dx, dtype=int) y_out = np.array(coords[condition_outside, 1] / dy, dtype=int) x_in = np.array(coords[condition_inside, 0] / dx, dtype=int) y_in = np.array(coords[condition_inside, 1] / dy, dtype=int) x_center = np.mean(x_in) y_center = np.mean(y_in) u_x_in = deflection[condition_inside] u_x_out = deflection[condition_outside] n_in = len(x_in) n_out = len(x_out) spacing = 1 G_in_in_xx, G_in_in_xy, G_out_in_xx, G_out_in_xy, G_in_in_yy, G_in_in_yx, G_out_in_yy, G_out_in_yx, Dx, Dy = gen_matrices( x_in, y_in, x_out, y_out, dx * spacing, dy * spacing, loworder=True) print("Size of the problem is " + str(n_in + n_out)) """ Setting up the problem ====================== We compute the coefficient matrices for the linear problem """ """ Setting up the optimization problem =================================== Define norms """ gamma = Parameter(sign="positive", value=1) sigma_xz = Variable(n_in) sigma_yz = Variable(n_in) # predicted_in = A_in_in*sigma_xz + D_in_in*sigma_yz # add higher order terms predicted_in_x = G_in_in_xx * sigma_xz + G_in_in_xy * sigma_yz predicted_out_x = G_out_in_xx * sigma_xz + G_out_in_xy * sigma_yz predicted_in_y = G_in_in_yx * sigma_xz + G_in_in_yy * sigma_yz predicted_out_y = G_out_in_yx * sigma_xz + G_out_in_yy * sigma_yz gamma_vals = np.logspace(-3, 2, N_SOLUTIONS) error = sum_squares(u_x_in - predicted_in_x) + sum_squares(u_x_out - predicted_out_x) if REGULARIZATION == "tvtrace": regularity_penalty = tvnorm_trace_2d(sigma_xz, sigma_yz, Dx, Dy) elif REGULARIZATION == "tviso": regularity_penalty = norm(Dx * sigma_xz / dx, 1) + norm( Dy * sigma_xz / dy, 1) + norm(Dx * sigma_yz / dx, 1) + norm( Dy * sigma_yz / dy, 1) elif REGULARIZATION == "tv": regularity_penalty = tvnorm2d(sigma_xz, Dx, Dy) + tvnorm2d( sigma_yz, Dx, Dy) elif REGULARIZATION == 'l2_grad': regularity_penalty = sum_squares( Dx * sigma_xz + Dx * sigma_yz) + sum_squares(Dy * sigma_xz + Dy * sigma_yz) elif REGULARIZATION == 'l1': regularity_penalty = norm(sigma_xz + sigma_yz, p=1) elif REGULARIZATION == 'l2': regularity_penalty = sum_squares(sigma_xz + sigma_yz) + sum_squares(sigma_xz + sigma_yz) elif REGULARIZATION == 'det': gamma_vals = np.logspace(-8, -5, N_SOLUTIONS) regularity_penalty = sum_entries(-log2(sigma_xz) - log2(sigma_yz)) else: print("Invalid regularization choice") sys.exit(0) forceconstraints = [ sum_entries(sigma_xz) == 0, sum_entries(sigma_yz) == 0 ] # add torque-free constraint here net_torque = sum_entries( mul_elemwise(x_in - x_center, sigma_yz) - mul_elemwise(y_in - y_center, sigma_xz)) torqueconstraints = [net_torque == 0] constraints = forceconstraints + torqueconstraints objective = Minimize(error + gamma * regularity_penalty) prob = Problem(objective, constraints) sq_penalty = [] l1_penalty = [] sigma_xz_values = [] sigma_yz_values = [] with PdfPages(figure_outfile) as pdf: for val in gamma_vals: gamma.value = val try: if results.solver is not None and results.solver == "ecos": prob.solve(verbose=True, max_iters=50, warm_start=True, solver=cvxpy.ECOS, feastol=1e-6, reltol=1e-5, abstol=1e-6) elif results.solver is not None and results.solver == "cvxopt": prob.solve(verbose=True, max_iters=50, warm_start=True, solver=cvxpy.CVXOPT, feastol=1e-6, reltol=1e-5, abstol=1e-6) else: prob.solve(verbose=True, max_iters=50, warm_start=True, feastol=1e-6, reltol=1e-5, abstol=1e-6) except cvxpy.SolverError: continue sq_penalty.append(error.value) l1_penalty.append(regularity_penalty.value) sigma_xz_values.append(sigma_xz.value) sigma_yz_values.append(sigma_yz.value) force = np.zeros_like(coords) force[condition_inside, 0] = sigma_xz.value.reshape((n_in, )) force[condition_inside, 1] = sigma_yz.value.reshape((n_in, )) u_x = np.zeros(coords.shape[0]) u_x[condition_inside] = predicted_in_x.value u_x[condition_outside] = predicted_out_x.value maxmagnitude = np.max(np.abs(force)) plt.rc('text', usetex=True) plt.rc('font', family='serif') plt.figure(figsize=(10, 10)) x_min = min(coords[boundary == 1, 0]) x_max = max(coords[boundary == 1, 0]) y_min = min(coords[boundary == 1, 1]) y_max = max(coords[boundary == 1, 1]) pdf.attach_note("$\gamma$: " + str(val)) plt.suptitle("$\gamma$: " + str(val) + "\n" + "mismatch: " + str(error.value) + " penalty: " + str(regularity_penalty.value)) plt.subplot(221) plt.xlim((x_min - 40, x_max + 40)) plt.ylim((y_min - 40, y_max + 40)) plt.pcolormesh(x_obs_positions, y_obs_positions, force[:, 0].reshape( (len(x_obs_positions), len(y_obs_positions))).transpose(), cmap='seismic_r', vmax=maxmagnitude * .75, vmin=-maxmagnitude * .8) plt.title("$\sigma_{xz}$") plt.colorbar() plt.subplot(222) plt.xlim((x_min - 40, x_max + 40)) plt.ylim((y_min - 40, y_max + 40)) plt.pcolormesh(x_obs_positions, y_obs_positions, force[:, 1].reshape( (len(x_obs_positions), len(y_obs_positions))).transpose(), cmap='seismic_r', vmax=maxmagnitude * .75, vmin=-maxmagnitude * .8) plt.title("$\sigma_{yz}$") plt.colorbar() plt.subplot(223) plt.xlim((x_min - 40, x_max + 40)) plt.ylim((y_min - 40, y_max + 40)) plt.pcolormesh(x_obs_positions, y_obs_positions, u_x.reshape((len(x_obs_positions), len(y_obs_positions))).transpose(), cmap='seismic_r') plt.title("$\hat{u}_x$") plt.colorbar() plt.subplot(224) plt.xlim((x_min - 40, x_max + 40)) plt.ylim((y_min - 40, y_max + 40)) plt.pcolormesh(x_obs_positions, y_obs_positions, (deflection - u_x).reshape( (len(x_obs_positions), len(y_obs_positions))).transpose(), cmap='seismic_r') plt.title("$u_x-\hat{u}_x$") plt.colorbar() pdf.savefig() #plt.show() plt.close() plt.plot(sq_penalty, l1_penalty) plt.xlabel("Mismatch", fontsize=16) plt.ylabel("Regularity", fontsize=16) plt.title('Trade-Off Curve', fontsize=16) l_curve_distances = np.abs((l1_penalty[-1]-l1_penalty[0])*sq_penalty - \ (sq_penalty[-1]-sq_penalty[0])*l1_penalty+sq_penalty[-1]*l1_penalty[0]-l1_penalty[-1]*sq_penalty[0]) # Choose the optimal lambda value pdf.savefig() plt.close() input("Press Enter to continue...")
constraints += [umin <= u[:, k], u[:, k] <= umax] objective += quad_form(x[:, Np] - xref, QN) prob = Problem(Minimize(objective), constraints) # Simulate in closed loop # Simulate in closed loop len_sim = 15 # simulation length (s) nsim = int(len_sim / Ts) # simulation length(timesteps) xsim = np.zeros((nsim, nx)) usim = np.zeros((nsim, nu)) tsim = np.arange(0, nsim) * Ts uminus1_val = uinit # initial previous measured input is the input at time instant -1. time_start = time.time() for i in range(nsim): x_init.value = x0 #uminus1.value = uminus1_val prob.solve(solver=OSQP, warm_start=True) uMPC = u[:, 0].value usim[i, :] = uMPC x0 = Ad.dot(x0) + Bd.dot(uMPC) xsim[i, :] = x0 uminus1_val = uMPC # or a measurement if the input is affected by noise time_sim = time.time() - time_start # In [1] import matplotlib.pyplot as plt fig, axes = plt.subplots(3, 1, figsize=(10, 10)) axes[0].plot(tsim, xsim[:, 0], "k", label='p') axes[0].plot(tsim, xref[0] * np.ones(np.shape(tsim)), "r--", label="pref")