def test_solver_comparison(self): """ Test that all solvers return the same and correct solution. """ # Convex functions. y = [1, 0, 0.1, 8, -6.5, 0.2, 0.004, 0.01] sol = [0.75, 0, 0, 7.75, -6.25, 0, 0, 0] w1, w2 = .8, .4 f1 = functions.norm_l2(y=y, lambda_=w1 / 2.) # Smooth. f2 = functions.norm_l1(lambda_=w2 / 2.) # Non-smooth. # Solvers. L = w1 # Lipschitz continuous gradient. step = 1. / L lambda_ = 0.5 params = {'step': step, 'lambda_': lambda_} slvs = [] slvs.append( solvers.forward_backward(accel=acceleration.dummy(), step=step)) slvs.append(solvers.douglas_rachford(**params)) slvs.append(solvers.generalized_forward_backward(**params)) # Compare solutions. params = {'rtol': 1e-14, 'verbosity': 'NONE', 'maxit': 1e4} niters = [2, 61, 26] for solver, niter in zip(slvs, niters): x0 = np.zeros(len(y)) ret = solvers.solve([f1, f2], x0, solver, **params) nptest.assert_allclose(ret['sol'], sol) self.assertEqual(ret['niter'], niter) self.assertIs(ret['sol'], x0) # The initial value was modified.
def test_solver_comparison(self): """ Test that all solvers return the same and correct solution. """ # Convex functions. y = [1, 0, 0.1, 8, -6.5, 0.2, 0.004, 0.01] sol = [0.75, 0, 0, 7.75, -6.25, 0, 0, 0] w1, w2 = .8, .4 f1 = functions.norm_l2(y=y, lambda_=w1 / 2.) # Smooth. f2 = functions.norm_l1(lambda_=w2 / 2.) # Non-smooth. # Solvers. L = w1 # Lipschitz continuous gradient. step = 1. / L lambda_ = 0.5 params = {'step': step, 'lambda_': lambda_} slvs = [] slvs.append(solvers.forward_backward(accel=acceleration.dummy(), step=step)) slvs.append(solvers.douglas_rachford(**params)) slvs.append(solvers.generalized_forward_backward(**params)) # Compare solutions. params = {'rtol': 1e-14, 'verbosity': 'NONE', 'maxit': 1e4} niters = [2, 61, 26] for solver, niter in zip(slvs, niters): x0 = np.zeros(len(y)) ret = solvers.solve([f1, f2], x0, solver, **params) nptest.assert_allclose(ret['sol'], sol) self.assertEqual(ret['niter'], niter) self.assertIs(ret['sol'], x0) # The initial value was modified.
def optGFB(D, GK0, triangles, fxy, E, maxit, x1, step, tau1, tau2, tau3, flag): #### N = len(E) f2 = functions.func() f2._eval = lambda x: 0 f2._prox = lambda x, T: np.clip(x, 0, 0.7) # ### T1 = Nodeneighbor(triangles, N) g = lambda x: Ggradient(x, T1) f3 = functions.norm_l1(A=g, At=None, dim=1, y=np.zeros(N), lambda_=tau2) #['EVAL', 'PROX'] ###### yy2 = np.ravel(fxy) #### N_cov = np.zeros((2 * N, 2 * N)) for j in np.arange(0, 2 * N, 2): N_cov[j, j] = 3 N_cov[j + 1, j + 1] = 1 gamma = GK0 @ N_cov @ GK0.T # gamma += np.eye(gamma.shape[1]) * 1e-5 gamma_inv = np.linalg.inv(gamma) f8 = functions.func(lambda_=tau1) f8._eval = lambda x: (yy2 - D @ x).T @ gamma_inv @ (yy2 - D @ x) * 1e+7 f8._grad = lambda x: -D.T @ gamma_inv @ (yy2 - D @ x) * 1e+7 ####### #step = 0.08#0.5 /tau1# (np.linalg.norm(func(x0),2)**2/np.linalg.norm(x0,2)**2) #0.5/tau#2e3/scale solver2 = solvers.generalized_forward_backward( step=step * 0.2 ) #generalized_forward_backward(step=step*0.1)#step*0.1)douglas_rachford # without f3 -->singular matrix ret2 = solvers.solve([f8, f3, f2], x1, solver2, rtol=1e-15, maxit=maxit) objective = np.array(ret2['objective']) sol = ret2['sol'] import matplotlib.pyplot as plt if flag == 1: _ = plt.figure(figsize=(10, 4)) _ = plt.subplot(121) _ = plt.plot(E, 'o', label='Original E') #-np.ones(N)*0.1 _ = plt.plot(ret2['sol'], 'xr', label='Reconstructed E') _ = plt.grid(True) _ = plt.title('Achieved reconstruction') _ = plt.legend(numpoints=1) _ = plt.xlabel('Signal dimension number') _ = plt.ylabel('Signal value') _ = plt.subplot(122) _ = plt.semilogy(objective[:, 0], '-.', label='l2-norm') # _ = plt.semilogy(np.sum(objective, axis=1), label='Global objective') _ = plt.grid(True) _ = plt.title('Convergence') _ = plt.legend(numpoints=1) _ = plt.xlabel('Iteration number') _ = plt.ylabel('Objective function value') _ = plt.show() return sol
def test_generalized_forward_backward(self): """ Test the generalized forward-backward algorithm. """ y = [4, 5, 6, 7] L = 4 # Gradient of the smooth function is Lipschitz continuous. solver = solvers.generalized_forward_backward(step=.9 / L, lambda_=.8) params = {'solver': solver, 'verbosity': 'NONE'} # Functions. f1 = functions.norm_l1(y=y, lambda_=.7) # Non-smooth. f2 = functions.norm_l2(y=y, lambda_=L / 2.) # Smooth. # Solve with 1 smooth and 1 non-smooth. ret = solvers.solve([f1, f2], np.zeros(len(y)), **params) nptest.assert_allclose(ret['sol'], y) self.assertEqual(ret['niter'], 25) # Solve with 1 smooth. ret = solvers.solve([f1], np.zeros(len(y)), **params) nptest.assert_allclose(ret['sol'], y) self.assertEqual(ret['niter'], 77) # Solve with 1 non-smooth. ret = solvers.solve([f2], np.zeros(len(y)), **params) nptest.assert_allclose(ret['sol'], y) self.assertEqual(ret['niter'], 18) # Solve with 1 smooth and 2 non-smooth. ret = solvers.solve([f1, f2, f2], np.zeros(len(y)), **params) nptest.assert_allclose(ret['sol'], y) self.assertEqual(ret['niter'], 26) # Solve with 2 smooth and 2 non-smooth. ret = solvers.solve([f2, f1, f2, f1], np.zeros(len(y)), **params) nptest.assert_allclose(ret['sol'], y) self.assertEqual(ret['niter'], 25) # Sanity checks x0 = np.zeros((4, )) solver.lambda_ = 2. self.assertRaises(ValueError, solver.pre, [f1, f2], x0) solver.lambda_ = -2. self.assertRaises(ValueError, solver.pre, [f1, f2], x0) f1 = functions.func() f2 = functions.func() f3 = functions.func() solver.lambda_ = 1. self.assertRaises(ValueError, solver.pre, [f1, f2, f3], x0)
def test_generalized_forward_backward(self): """ Test the generalized forward-backward algorithm. """ y = [4, 5, 6, 7] L = 4 # Gradient of the smooth function is Lipschitz continuous. solver = solvers.generalized_forward_backward(step=.9 / L, lambda_=.8) params = {'solver': solver, 'verbosity': 'NONE'} # Functions. f1 = functions.norm_l1(y=y, lambda_=.7) # Non-smooth. f2 = functions.norm_l2(y=y, lambda_=L / 2.) # Smooth. # Solve with 1 smooth and 1 non-smooth. ret = solvers.solve([f1, f2], np.zeros(len(y)), **params) nptest.assert_allclose(ret['sol'], y) self.assertEqual(ret['niter'], 25) # Solve with 1 smooth. ret = solvers.solve([f1], np.zeros(len(y)), **params) nptest.assert_allclose(ret['sol'], y) self.assertEqual(ret['niter'], 77) # Solve with 1 non-smooth. ret = solvers.solve([f2], np.zeros(len(y)), **params) nptest.assert_allclose(ret['sol'], y) self.assertEqual(ret['niter'], 18) # Solve with 1 smooth and 2 non-smooth. ret = solvers.solve([f1, f2, f2], np.zeros(len(y)), **params) nptest.assert_allclose(ret['sol'], y) self.assertEqual(ret['niter'], 26) # Solve with 2 smooth and 2 non-smooth. ret = solvers.solve([f2, f1, f2, f1], np.zeros(len(y)), **params) nptest.assert_allclose(ret['sol'], y) self.assertEqual(ret['niter'], 25) # Sanity checks x0 = np.zeros((4,)) solver.lambda_ = 2. self.assertRaises(ValueError, solver.pre, [f1, f2], x0) solver.lambda_ = -2. self.assertRaises(ValueError, solver.pre, [f1, f2], x0) f1 = functions.func() f2 = functions.func() f3 = functions.func() solver.lambda_ = 1. self.assertRaises(ValueError, solver.pre, [f1, f2, f3], x0)