def impose_reweighted_variance(v, samples, weights=None, solver=None): """impose a variance on a list of points by reweighting weights""" ndim = len(samples) if weights is None: weights = [1.0/ndim] * ndim if solver is None or solver == 'fmin': from mystic.solvers import fmin as solver elif solver == 'fmin_powell': from mystic.solvers import fmin_powell as solver elif solver == 'diffev': from mystic.solvers import diffev as solver elif solver == 'diffev2': from mystic.solvers import diffev2 as solver norm = sum(weights) m = mean(samples, weights) inequality = "" equality = ""; equality2 = ""; equality3 = "" for i in range(ndim): inequality += "x%s >= 0.0\n" % (i) # positive equality += "x%s + " % (i) # normalized equality2 += "%s * x%s + " % (float(samples[i]),(i)) # mean equality3 += "x%s*(%s-%s)**2 + " % ((i),float(samples[i]),m) # var equality += "0.0 = %s\n" % float(norm) equality += equality2 + "0.0 = %s*%s\n" % (float(norm),m) equality += equality3 + "0.0 = %s*%s\n" % (float(norm),v) penalties = generate_penalty(generate_conditions(inequality)) constrain = generate_constraint(generate_solvers(solve(equality))) def cost(x): return sum(x) results = solver(cost, weights, constraints=constrain, \ penalty=penalties, disp=False, full_output=True) wts = list(results[0]) _norm = results[1] # should have _norm == norm warn = results[4] # nonzero if didn't converge #XXX: better to fail immediately if xlo < m < xhi... or the below? if warn or not almostEqual(_norm, norm): print "Warning: could not impose mean through reweighting" return None #impose_variance(v, samples, weights), weights return wts #samples, wts # "mean-preserving"
return -(sin(2*pi*x0)**3 * sin(2*pi*x1)) / (x0**3 * (x0 + x1)) bounds = [(0,10)]*2 # with penalty='penalty' applied, solution is: xs = [1.22797136, 4.24537337] ys = -0.09582504 from mystic.symbolic import generate_constraint, generate_solvers, solve from mystic.symbolic import generate_penalty, generate_conditions equations = """ x0**2 - x1 + 1.0 <= 0.0 1.0 - x0 + (x1 - 4)**2 <= 0.0 """ #cf = generate_constraint(generate_solvers(solve(equations))) #XXX: inequalities pf = generate_penalty(generate_conditions(equations), k=1e12) from mystic.constraints import as_constraint cf = as_constraint(pf) if __name__ == '__main__': from mystic.solvers import buckshot from mystic.math import almostEqual result = buckshot(objective, 2, 40, bounds=bounds, penalty=pf, disp=False, full_output=True) assert almostEqual(result[0], xs, tol=1e-2)
from mystic.symbolic import generate_constraint, generate_solvers, simplify from mystic.symbolic import generate_penalty, generate_conditions equations = """ 2.0*x0 + 2.0*x1 + x9 + x10 - 10.0 <= 0.0 2.0*x0 + 2.0*x2 + x9 + x11 - 10.0 <= 0.0 2.0*x1 + 2.0*x2 + x10 + x11 - 10.0 <= 0.0 -8.0*x0 + x9 <= 0.0 -8.0*x1 + x10 <= 0.0 -8.0*x2 + x11 <= 0.0 -2.0*x3 - x4 + x9 <= 0.0 -2.0*x5 - x6 + x10 <= 0.0 -2.0*x7 - x8 + x11 <= 0.0 """ cf = generate_constraint(generate_solvers(simplify(equations))) pf = generate_penalty(generate_conditions(equations)) if __name__ == '__main__': x = [0] * len(xs) from mystic.solvers import fmin_powell from mystic.math import almostEqual result = fmin_powell(objective, x0=x, bounds=bounds, constraints=cf, disp=False, full_output=True) assert almostEqual(result[0], xs, tol=1e-2)
-x[0] + 2*x[1] <= 4 where: 0 <= x[0] <= inf 0 <= x[1] <= 4 """ import numpy as np import mystic.symbolic as ms import mystic.solvers as my import mystic.math as mm # generate constraints and penalty for a linear system of equations A = np.array([[1, 1], [-1, 2]]) b = np.array([7, 4]) eqns = ms.linear_symbolic(G=A, h=b) cons = ms.generate_constraint(ms.generate_solvers(ms.simplify(eqns))) pens = ms.generate_penalty(ms.generate_conditions(eqns), k=1e3) bounds = [(0., None), (0., 4.)] # get the objective def objective(x): x = np.asarray(x) return x[0]**2 + 4 * x[1]**2 - 32 * x[1] + 64 x0 = np.random.rand(2) # compare against the exact minimum xs = np.array([2., 3.]) ys = objective(xs)
def pf(len=3): return generate_penalty(generate_conditions(equations(len)))
T + H + E + M + E - 72 == 0 V + I + O + L + I + N - 100 == 0 W + A + L + T + Z - 34 == 0 """ var = list('ABCDEFGHIJKLMNOPQRSTUVWXYZ') #NOTE: FOR A MORE DIFFICULT PROBLEM, COMMENT OUT THE FOLLOWING 5 LINES bounds[0] = (5, 5) # A bounds[4] = (20, 20) # E bounds[8] = (25, 25) # I bounds[14] = (10, 10) # O bounds[20] = (1, 1) # U from mystic.constraints import unique, near_integers, has_unique from mystic.symbolic import generate_penalty, generate_conditions pf = generate_penalty(generate_conditions(equations, var), k=1) from mystic.constraints import as_constraint cf = as_constraint(pf) from mystic.penalty import quadratic_equality @quadratic_equality(near_integers) @quadratic_equality(has_unique) def penalty(x): return pf(x) from numpy import round, hstack, clip def constraint(x):
-x[0] + 2*x[1] <= 4 where: 0 <= x[0] <= inf 0 <= x[1] <= 4 """ import numpy as np import mystic.symbolic as ms import mystic.solvers as my import mystic.math as mm # generate constraints and penalty for a linear system of equations A = np.array([[1, 1],[-1, 2]]) b = np.array([7,4]) eqns = ms.linear_symbolic(G=A, h=b) cons = ms.generate_constraint(ms.generate_solvers(ms.simplify(eqns))) pens = ms.generate_penalty(ms.generate_conditions(eqns), k=1e3) bounds = [(0., None), (0., 4.)] # get the objective def objective(x): x = np.asarray(x) return x[0]**2 + 4*x[1]**2 - 32*x[1] + 64 x0 = np.random.rand(2) # compare against the exact minimum xs = np.array([2., 3.]) ys = objective(xs) sol = my.fmin_powell(objective, x0, constraint=cons, penalty=pens, disp=False,
T + H + E + M + E - 72 == 0 V + I + O + L + I + N - 100 == 0 W + A + L + T + Z - 34 == 0 """ var = list('ABCDEFGHIJKLMNOPQRSTUVWXYZ') #NOTE: FOR A MORE DIFFICULT PROBLEM, COMMENT OUT THE FOLLOWING 5 LINES bounds[0] = (5,5) # A bounds[4] = (20,20) # E bounds[8] = (25,25) # I bounds[14] = (10,10) # O bounds[20] = (1,1) # U from mystic.constraints import unique, near_integers, has_unique from mystic.symbolic import generate_penalty, generate_conditions pf = generate_penalty(generate_conditions(equations,var),k=1) from mystic.constraints import as_constraint cf = as_constraint(pf) from mystic.penalty import quadratic_equality @quadratic_equality(near_integers) @quadratic_equality(has_unique) def penalty(x): return pf(x) from numpy import round, hstack, clip def constraint(x): x = round(x).astype(int) # force round and convert type to int x = clip(x, 1,nletters) #XXX: hack to impose bounds x = unique(x, list(range(1,nletters+1))) return x
constraints = ms.linear_symbolic(G=[load, invest], h=[max_load, max_spend]) # bounds (on x) bounds = [(0, i.limit) for i in items] # bounds constraints lo = 'x%s >= %s' lo = '\n'.join(lo % (i, str(float(j[0])).lstrip('0')) for (i, j) in enumerate(bounds)) hi = 'x%s <= %s' hi = '\n'.join(hi % (i, str(float(j[1])).lstrip('0')) for (i, j) in enumerate(bounds)) constraints = '\n'.join([lo, hi]).strip() + '\n' + constraints cf = ms.generate_constraint(ms.generate_solvers(ms.simplify(constraints)), join=mc.and_) pf = ms.generate_penalty(ms.generate_conditions(ms.simplify(constraints))) # integer constraints #constrain = mc.and_(mc.integers(float)(lambda x:x), cf) constrain = mc.integers(float)(lambda x: x) # solve mon = my.monitors.VerboseMonitor(10) result = my.solvers.diffev2(lambda x: -profit(x), bounds, npop=400, bounds=bounds, ftol=1e-6, gtol=100, itermon=mon, disp=True,
_join = join_ = None print(eqns) else: _join, join_ = _or, or_ for eqn in eqns: print(eqn + '\n----------------------') constrain = ms.generate_constraint(ms.generate_solvers( eqns, var, locals=dict(e_=eps)), join=_join) solution = constrain([1, -2, 1]) print('solved: %s' % dict(zip(var, solution))) penalty = ms.generate_penalty(ms.generate_conditions(eqns, var, locals=dict(e_=eps)), join=join_) print('penalty: %s' % penalty(solution)) equations = """ A*(B-C) + 2*C > 1 B + C = 2*D D < 0 """ print(equations) var = list('ABCD') eqns = ms.simplify(equations, variables=var, all=True) if isinstance(eqns, str): _join = join_ = None print(eqns)