All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.chocosolver.solver.expression.discrete.arithmetic.NaArExpression Maven / Gradle / Ivy

There is a newer version: 4.10.17
Show newest version
/*
 * This file is part of choco-solver, http://choco-solver.org/
 *
 * Copyright (c) 2023, IMT Atlantique. All rights reserved.
 *
 * Licensed under the BSD 4-clause license.
 *
 * See LICENSE file in the project root for full license information.
 */
package org.chocosolver.solver.expression.discrete.arithmetic;

import org.chocosolver.solver.Model;
import org.chocosolver.solver.variables.IntVar;
import org.chocosolver.util.tools.ArrayUtils;
import org.chocosolver.util.tools.VariableUtils;

import java.util.Arrays;
import java.util.Map;

/**
 * Binary arithmetic expression
 * 

* Project: choco-solver. * * @author Charles Prud'homme * @since 28/04/2016. */ public class NaArExpression implements ArExpression { /** * The model in which the expression is declared */ Model model; /** * Lazy creation of the underlying variable */ IntVar me = null; /** * Operator of the arithmetic expression */ Operator op; /** * The expressions this expression relies on */ private final ArExpression[] es; /** * Builds a n-ary expression * * @param op an operator * @param es some expressions */ public NaArExpression(Operator op, ArExpression e, ArExpression... es) { this(op, ArrayUtils.append(new ArExpression[]{e}, es)); } /** * Builds a n-ary expression * * @param op an operator * @param es some expressions */ public NaArExpression(Operator op, ArExpression... es) { this.op = op; this.es = es; this.model = es[0].getModel(); } @Override public Model getModel() { return model; } public Operator getOp() { return op; } @Override public IntVar intVar() { if (me == null) { IntVar[] vs = Arrays.stream(es).map(ArExpression::intVar).toArray(IntVar[]::new); int[] bounds; switch (op) { case ADD: bounds = VariableUtils.boundsForAddition(vs); me = model.intVar(model.generateName("sum_exp_"), bounds[0], bounds[1]); model.sum(vs, "=", me).post(); break; case MUL: bounds = VariableUtils.boundsForMultiplication(vs[0], vs[1]); me = model.intVar(model.generateName("mul_exp_0_"), bounds[0], bounds[1]); model.times(vs[0], vs[1], me).post(); for (int i = 2; i < vs.length; i++) { IntVar pre = me; bounds = VariableUtils.boundsForMultiplication(pre, vs[i]); me = model.intVar(model.generateName("mul_exp_0_"), bounds[0], bounds[1]); model.times(pre, vs[i], me).post(); } break; case MIN: bounds = VariableUtils.boundsForMinimum(vs); me = model.intVar(model.generateName("min_exp_"), bounds[0], bounds[1]); model.min(me, vs).post(); break; case MAX: bounds = VariableUtils.boundsForMaximum(vs); me = model.intVar(model.generateName("max_exp_"), bounds[0], bounds[1]); model.max(me, vs).post(); break; default: throw new UnsupportedOperationException("Binary arithmetic expressions does not support " + op.name()); } } return me; } @Override public int ieval(int[] values, Map map) { // int r = es[0].eval(values, map); return Arrays.stream(es) .mapToInt(e -> e.ieval(values, map)) .reduce(op.identity(), (e1, e2) -> op.eval(e1, e2)); } @Override public int getNoChild() { return es.length; } @Override public ArExpression[] getExpressionChild() { return es; } @Override public String toString() { return op.name() + "(" + es[0].toString() + ",... ," + es[es.length - 1].toString() + ")"; } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy