/*
 * Copyright 2002, 2003, 2004, 2005 - <A href="http://www.koalog.com">Koalog</A>
 */
package com.koalog.jcs.examples;

import org.apache.log4j.PropertyConfigurator;
import com.koalog.jcs.variable.IntegerVariable;
import com.koalog.jcs.solver.DefaultFFSolver;
import com.koalog.jcs.constraint.BaseProblem;
import com.koalog.jcs.constraint.arithmetic.ConstantSum;
import com.koalog.jcs.constraint.arithmetic.Hyperplan;
import com.koalog.jcs.constraint.arithmetic.AllDifferent;

/**
 * This problem comes from the newsgroup rec.puzzle.  
 * The numbers from 1 to 26 are assigned to the letters of the alphabet.
 * The numbers beside each word are the total of the values assigned to the 
 * letters in the word (e.g for LYRE: L,Y,R,E might be to equal 5,9,20 and 13 
 * or any other combination that add up to 47).
 *
 * Find the value of each letter under the equations:                      
 <PRE>                                                                 
 *    BALLET  45     GLEE  66     POLKA      59     SONG     61            
 *    CELLO   43     JAZZ  58     QUARTET    50     SOPRANO  82            
 *    CONCERT 74     LYRE  47     SAXOPHONE 134     THEME    72            
 *    FLUTE   30     OBOE  53     SCALE      51     VIOLIN  100            
 *    FUGUE   50     OPERA 65     SOLO       37     WALTZ    34   
 </PRE>
 *
 @author Daniel Diaz
 @author Yan Georget
 */
public class AlphaProblem extends BaseProblem {
    //------------------------------------------------------------------------
    // CONSTRUCTORS
    //------------------------------------------------------------------------
    /**
     * Sole constructor.
     */
    public AlphaProblem() {
        super();
        IntegerVariable a = new IntegerVariable("a",1,26);
        IntegerVariable b = new IntegerVariable("b",1,26);
        IntegerVariable c = new IntegerVariable("c",1,26);
        IntegerVariable d = new IntegerVariable("d",1,26);
        IntegerVariable e = new IntegerVariable("e",1,26);
        IntegerVariable f = new IntegerVariable("f",1,26);
        IntegerVariable g = new IntegerVariable("g",1,26);
        IntegerVariable h = new IntegerVariable("h",1,26);
        IntegerVariable i = new IntegerVariable("i",1,26);
        IntegerVariable j = new IntegerVariable("j",1,26);
        IntegerVariable k = new IntegerVariable("k",1,26);
        IntegerVariable l = new IntegerVariable("l",1,26);
        IntegerVariable m = new IntegerVariable("m",1,26);
        IntegerVariable n = new IntegerVariable("n",1,26);
        IntegerVariable o = new IntegerVariable("o",1,26);
        IntegerVariable p = new IntegerVariable("p",1,26);
        IntegerVariable q = new IntegerVariable("q",1,26);
        IntegerVariable r = new IntegerVariable("r",1,26);
        IntegerVariable s = new IntegerVariable("s",1,26);
        IntegerVariable t = new IntegerVariable("t",1,26);
        IntegerVariable u = new IntegerVariable("u",1,26);
        IntegerVariable v = new IntegerVariable("v",1,26);
        IntegerVariable w = new IntegerVariable("w",1,26);
        IntegerVariable x = new IntegerVariable("x",1,26);
        IntegerVariable y = new IntegerVariable("y",1,26);
        IntegerVariable z = new IntegerVariable("z",1,26);
        IntegerVariable[] vars = new IntegerVariable[] 
            {a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,p,q,r,s,t,u,v,w,x,y,z};
        add(new AllDifferent(vars));
        add(new Hyperplan(new int[]{11121}
                                  new IntegerVariable[] {a, b, e, l, t}
                                  45));
        add(new Hyperplan(new int[]{1121}
                                  new IntegerVariable[] {c, e, l, o}
                                  43));
        add(new Hyperplan(new int[]{211111}
                                  new IntegerVariable[] {c, e, o, n, r, t}
                                  74));
        add(new ConstantSum(new IntegerVariable[] {e, f, l, u, t}
                                    30));
        add(new Hyperplan(new int[]{1112}
                                  new IntegerVariable[] {e, f, g, u}
                                  50));
        add(new Hyperplan(new int[]{211}
                                  new IntegerVariable[] {e, g, l}
                                  66));
        add(new Hyperplan(new int[]{112}
                                  new IntegerVariable[] {a, j, z}
                                  58));
        add(new ConstantSum(new IntegerVariable[] {e, l, r, y}
                                    47));
        add(new Hyperplan(new int[]{112}
                                  new IntegerVariable[] {b, e, o}
                                  53));
        add(new ConstantSum(new IntegerVariable[] {a, e, o, p, r}
                                    65));
        add(new ConstantSum(new IntegerVariable[] {a, k, l, o, p}
                                    59));
        add(new Hyperplan(new int[]{111121}
                                  new IntegerVariable[] {a, e, q, r, t, u}
                                  50));
        add(new Hyperplan(new int[]{11121111}
                                  new IntegerVariable[]{a, e, h, o, n, p, s, x},
                                  134));
        add(new ConstantSum(new IntegerVariable[] {a, c, e, l, s}
                                    51));
        add(new Hyperplan(new int[]{121}
                                  new IntegerVariable[] {l, o, s}
                                  37));
        add(new ConstantSum(new IntegerVariable[] {g, n, o, s}
                                    61));
        add(new Hyperplan(new int[]{112111}
                                  new IntegerVariable[] {a, n, o, p, r, s}
                                  82));
        add(new Hyperplan(new int[]{2111}
                                  new IntegerVariable[] {e, h, m, t}
                                  72));
        add(new Hyperplan(new int[]{21111}
                                  new IntegerVariable[] {i, l, n, o, v}
                                  100));
        add(new ConstantSum(new IntegerVariable[] {a, l, t, w, z}
                                    34));
        setVariables(vars);
    }

    //------------------------------------------------------------------------
    // STATIC METHODS
    //------------------------------------------------------------------------
    /**
     * Runs the problem.
     @param args the command line arguments
     * args[0] must contain a log4j properties file location
     */
    public static void main(String[] args) {
        PropertyConfigurator.configure(args[0]);
        new DefaultFFSolver(new AlphaProblem()).solve(1);
    }
}