Created
June 11, 2012 14:26
-
-
Save josejuan/2910322 to your computer and use it in GitHub Desktop.
Maximize bits using lpi.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Una forma de acceder al solver, es usando el contexto siempre disponible: | |
var c = SolverContext.GetContext(); | |
// Creamos un modelo vacío, podríamos haberlo leído de disco, ... | |
var m = c.CreateModel(); | |
// Enumeramos los bits: 0, 1, 2, ..., n-1 | |
var b = new Set(0, Math.Ceiling(Math.Log(X) / Math.Log(2)), 1); | |
// Las incógnitas son los bits que tomarán los números Y y Z | |
var y = new Decision(Domain.Boolean, "y", b); | |
var z = new Decision(Domain.Boolean, "z", b); | |
m.AddDecisions(y, z); | |
// Como restricción, Y + Z = X, esta expresión es equivalente a: | |
// X = 2^0 (y0 + z0) + 2^1 (y1 + z1) + ... | |
m.AddConstraint("sum", Model.Sum(Model.ForEach(b, | |
i => Model.Power(2, i) * ( y [ i ] + z [ i ] ))) == X); | |
// Vamos a maximizar la suma del número de bits de Y y Z | |
// X = Y + Z | |
m.AddGoal("maxbits", GoalKind.Maximize, | |
Model.Sum(Model.ForEach(b, i => y [ i ] + z [ i ]))); | |
// Resolvemos el problema | |
var s = c.Solve(); | |
// Obtenemos soluciones, Y o Z se calcula como | |
// 2^0 b0 + 2^1 b1 + ... + 2^(n-1) b(n-1) | |
Func<object [] [], int> result = v => | |
Enumerable.Range(0, v.Length).Zip(v, | |
( n, x ) => (bool) x.First() ? 1 << n : 0).Sum(); | |
result(y.GetValues().ToArray()); // la solución para Y | |
result(z.GetValues().ToArray()); // la solución para Z |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment