Commit aa2d7859 authored by Marta Różańska's avatar Marta Różańska
Browse files

deleting cp_sampler and testing module which is not needed

parent 0bf219af
......@@ -101,17 +101,6 @@
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<executions>
<execution>
<id>repackage</id>
<goals>
<goal>repackage</goal>
</goals>
<configuration>
<classifier>exec</classifier>
</configuration>
</execution>
</executions>
</plugin>
<plugin>
<groupId>com.spotify</groupId>
......
......@@ -30,7 +30,6 @@ public class CPSolverController {
@RequestMapping(value = "/constraintProblemSolution", method = POST)
public void applySolution(@RequestBody ConstraintProblemSolutionRequestImpl request) {
log.info("LEDDDDSRERR");
String applicationId = request.getApplicationId();
String cdoResourcePath = request.getCdoModelsPath();
String notificationUri = request.getNotificationURI();
......@@ -44,7 +43,6 @@ public class CPSolverController {
@RequestMapping(value = "/constraintProblemSolutionFromFile", method = POST)
public void constraintProblemSolutionFromFile(@RequestBody ConstraintProblemSolutionFromFileRequestImpl request) throws Exception {
log.info("LESRERR");
String camelModelFilePath = request.getCamelModelFilePath();
String cpModelPath = request.getCpProblemFilePath();
String nodeCandidatesFilePath = request.getNodeCandidatesFilePath();
......
......@@ -84,9 +84,6 @@ public final class NodeCandidatePredicates {
Double latitude = null;
Location tempLocation = nodeCandidate.getLocation();
do {
if (tempLocation == null) {
System.out.println("O NIE");
}
final GeoLocation geoLocation = tempLocation.getGeoLocation();
if (geoLocation != null) {
latitude = geoLocation.getLatitude();
......
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>zpp-solver</artifactId>
<groupId>org.ow2.paasage</groupId>
<version>3.1.0-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<groupId>eu.melodic</groupId>
<artifactId>cp_sampler</artifactId>
<dependencies>
<dependency>
<groupId>eu.melodic</groupId>
<artifactId>cp-parser</artifactId>
<version>${melodic.version}</version>
</dependency>
<dependency>
<groupId>eu.melodic</groupId>
<artifactId>node-candidates-solver</artifactId>
<version>${melodic.version}</version>
</dependency>
</dependencies>
</project>
\ No newline at end of file
package eu.melodic.upperware.cp_sampler;
import eu.melodic.cache.NodeCandidates;
import eu.melodic.upperware.cp_sampler.constraint_problem_data.ConstraintProblemData;
import eu.melodic.upperware.cp_sampler.generator.ConstraintEvaluator;
import eu.melodic.upperware.cp_sampler.generator.ConstraintGenerator;
import eu.melodic.upperware.cp_sampler.generator.VariableGenerator;
import eu.melodic.upperware.cp_sampler.node_candidates.NodeCandidatesPool;
import eu.melodic.upperware.cp_sampler.utils.NamesProvider;
import io.github.cloudiator.rest.model.GeoLocation;
import io.github.cloudiator.rest.model.NodeCandidate;
import org.javatuples.Pair;
import java.util.*;
import java.util.stream.IntStream;
public class Sampler {
private int COMPONENTS_COUNT;
private int MAX_NUMBER_CONSTRAINTS;
private int MIN_NUMBER_CONSTRAINTS;
private final Random random = new Random();
public Sampler(int componentsCount, int minNumberConstraints, int maxNumberConstraints) {
this.COMPONENTS_COUNT = componentsCount;
this.MAX_NUMBER_CONSTRAINTS = maxNumberConstraints;
this.MIN_NUMBER_CONSTRAINTS = minNumberConstraints;
}
private int sampleNumberOfConstraints() {
return MIN_NUMBER_CONSTRAINTS + random.nextInt(MAX_NUMBER_CONSTRAINTS - MIN_NUMBER_CONSTRAINTS);
}
public Pair<ConstraintProblemData, NodeCandidates> sample(NodeCandidates nodeCandidates) {
int constraints = sampleNumberOfConstraints();
NodeCandidatesPool nodeCandidatesPool = new NodeCandidatesPool(nodeCandidates);
VariableGenerator variableGenerator = new VariableGenerator(nodeCandidatesPool, COMPONENTS_COUNT);
ConstraintEvaluator constraintEvaluator = new ConstraintEvaluator(variableGenerator, constraints);
ConstraintGenerator constraintGenerator = new ConstraintGenerator(constraintEvaluator, variableGenerator, COMPONENTS_COUNT);
ConstraintProblemData constraintProblem = new ConstraintProblemData(variableGenerator.getDomains());
IntStream.range(0, constraints).forEach(number -> constraintProblem.postConstraint(constraintGenerator.generateConstraint()));
return new Pair<>(constraintProblem, convertNodeCandidatesToSampleProblem(nodeCandidates));
}
private List<NodeCandidate> fillEmptyLocations(List<NodeCandidate> nodeCandidates) {
GeoLocation defaultGeoLocation = new GeoLocation();
defaultGeoLocation.setLongitude(1.0);
defaultGeoLocation.setLatitude(1.0);
nodeCandidates.forEach(node -> {
if(node.getLocation().getGeoLocation() == null) {
node.getLocation().setGeoLocation(defaultGeoLocation);
}
});
return nodeCandidates;
}
private NodeCandidates convertNodeCandidatesToSampleProblem(NodeCandidates nodeCandidates) {
Map<String, Map<Integer, List<NodeCandidate>>> candidates = nodeCandidates.get();
Map<String, Map<Integer, List<NodeCandidate>>> result = new HashMap<>();
IntStream.range(0, COMPONENTS_COUNT).forEach(
component -> {
result.put(NamesProvider.getComponentName(component), new HashMap<>());
candidates.forEach( (name, mapping) -> mapping.forEach(
(provider, machines) -> {
if (!result.get(NamesProvider.getComponentName(component)).containsKey(provider)) {
result.get(NamesProvider.getComponentName(component)).put(provider, new ArrayList<>());
}
result.get(NamesProvider.getComponentName(component)).get(provider).addAll(fillEmptyLocations(machines));
}));
}
);
return NodeCandidates.of(result);
}
}
\ No newline at end of file
package eu.melodic.upperware.cp_sampler.constraint_problem_data;
import eu.melodic.upperware.cp_wrapper.utils.numeric_value.NumericValueInterface;
import eu.melodic.upperware.cp_sampler.expressions.Constraint;
import eu.melodic.upperware.cp_sampler.expressions.VariableExpression;
import lombok.Getter;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
@Getter
public class ConstraintProblemData {
private Map<String, List<NumericValueInterface>> variableToDomain;
private Collection<VariableExpression> variables;
private Collection<Constraint> constraints = new ArrayList<>();
public ConstraintProblemData(Map<String, List<NumericValueInterface>> variableToDomain) {
this.variableToDomain = variableToDomain;
variables = gatherVariables();
}
public List<NumericValueInterface> getVariableDomain(String variable) {
return variableToDomain.get(variable);
}
private Collection<VariableExpression> gatherVariables() {
return variableToDomain.keySet().stream().map(VariableExpression::new).collect(Collectors.toList());
}
public void postConstraint(Constraint constraint) {
constraints.add(constraint);
}
@Override
public String toString() {
StringBuilder build = new StringBuilder();
build.append("Variables:\n");
for (VariableExpression var : variables) {
build.append(var.getVariableName());
build.append('\n');
}
build.append("Constraints:\n");
for (Constraint c : constraints) {
build.append(c.toString());
}
build.append("Domains:\n");
for (String var : variableToDomain.keySet()) {
build.append(var + " domain:\n");
build.append('\n');
}
return build.toString();
}
}
package eu.melodic.upperware.cp_sampler.expressions;
import eu.paasage.upperware.metamodel.cp.OperatorEnum;
import lombok.AllArgsConstructor;
import lombok.Getter;
@AllArgsConstructor
@Getter
public class ComposedExpression implements Expression {
private Expression leftExpr;
private Expression rightExpr;
private OperatorEnum operator;
private String operatorToString(OperatorEnum oper) {
switch(oper) {
case PLUS:
return "+";
case MINUS:
return "-";
case TIMES:
return "*";
default:
return "{}";
}
}
@Override
public String toString() {
StringBuilder builder = new StringBuilder();
builder.append('(');
builder.append(leftExpr.toString());
builder.append(") ");
builder.append(operatorToString(operator));
builder.append(" (");
builder.append(rightExpr.toString());
builder.append(')');
return builder.toString();
}
}
package eu.melodic.upperware.cp_sampler.expressions;
import eu.melodic.upperware.cp_wrapper.utils.numeric_value.NumericValueInterface;
import lombok.AllArgsConstructor;
import lombok.Getter;
import lombok.ToString;
@AllArgsConstructor
@ToString
public class ConstantExpression implements Expression {
@Getter
private NumericValueInterface value;
}
package eu.melodic.upperware.cp_sampler.expressions;
import eu.paasage.upperware.metamodel.cp.ComparatorEnum;
import lombok.AllArgsConstructor;
import lombok.Getter;
@AllArgsConstructor
@Getter
public class Constraint {
private Expression expression;
private Expression constant;
private ComparatorEnum comparator;
private String comparatorToString(ComparatorEnum comp) {
switch(comp) {
case LESS_OR_EQUAL_TO:
return "<=";
case LESS_THAN:
return "<";
case GREATER_OR_EQUAL_TO:
return ">=";
case GREATER_THAN:
return ">";
case DIFFERENT:
return "!=";
default:
return "==";
}
}
@Override
public String toString() {
StringBuilder builder = new StringBuilder();
builder.append(expression.toString());
builder.append(comparatorToString(comparator));
builder.append(((ConstantExpression)constant).getValue());
builder.append('\n');
return builder.toString();
}
}
package eu.melodic.upperware.cp_sampler.expressions;
public interface Expression {
@Override
String toString();
}
package eu.melodic.upperware.cp_sampler.expressions;
import lombok.AllArgsConstructor;
import lombok.Getter;
import lombok.ToString;
@AllArgsConstructor
@ToString
public class VariableExpression implements Expression {
@Getter
private String variableName;
}
package eu.melodic.upperware.cp_sampler.generator;
import eu.melodic.upperware.cp_wrapper.utils.expression_evaluator.ExpressionEvaluator;
import eu.melodic.upperware.cp_wrapper.utils.numeric_value.NumericValueInterface;
import eu.melodic.upperware.cp_wrapper.utils.numeric_value.implementations.DoubleValue;
import eu.melodic.upperware.cp_wrapper.utils.numeric_value.implementations.LongValue;
import eu.melodic.upperware.cp_sampler.expressions.ComposedExpression;
import eu.melodic.upperware.cp_sampler.expressions.ConstantExpression;
import eu.melodic.upperware.cp_sampler.expressions.Expression;
import eu.melodic.upperware.cp_sampler.expressions.VariableExpression;
import eu.melodic.upperware.cp_sampler.utils.NamesProvider;
import eu.melodic.upperware.nc_solver.nc_solver.node_candidate.node_candidate_element.GeographicCoordinate;
import eu.melodic.upperware.nc_solver.nc_solver.node_candidate.node_candidate_element.VMConfiguration;
import eu.melodic.upperware.nc_solver.nc_solver.variable_orderer.VariableTypeOrderer;
import eu.paasage.upperware.metamodel.cp.ComparatorEnum;
import eu.paasage.upperware.metamodel.cp.VariableType;
import org.javatuples.Pair;
import java.util.*;
import java.util.stream.Collectors;
import java.util.stream.IntStream;
import static eu.melodic.upperware.cp_wrapper.utils.expression_evaluator.ExpressionEvaluator.evaluateComparator;
/*
Each constraint is of a form Expression operator constant;
Process of constraint sampling proceeds as follows:
1) sample Expression (task of ConstraintGenerator)
2) sample operator
3) Choose constant value
Point 3) is this class responsibility;
A sample of size @sampleSize is taken from the state space -
median of Expression value on this sample is taken to be equal to the constant
(we try to avoid equality constraints);
*/
public class ConstraintEvaluator {
private Random random = new Random();
private VariableGenerator variableGenerator;
private int numberOfConstraints;
private List<Map<Integer, Pair<VMConfiguration, GeographicCoordinate>>> samples;
private final int SAMPLE_SIZE = 1000;
private final int MIN_SAMPLE_SIZE = 10;
public ConstraintEvaluator(VariableGenerator variableGenerator, int numberOfConstraints) {
this.variableGenerator = variableGenerator;
this.numberOfConstraints = numberOfConstraints;
this.samples = getSample(SAMPLE_SIZE);
}
private List<Map<Integer, Pair<VMConfiguration, GeographicCoordinate>>> getSample(int sampleSize) {
return IntStream.range(0, sampleSize).mapToObj(sampleNumber -> sample()).collect(Collectors.toList());
}
ConstantExpression getConstant(Expression expression, ComparatorEnum comparatorEnum) {
if (samples.size() <= MIN_SAMPLE_SIZE) samples = getSample(SAMPLE_SIZE);
List<Double> evaluatedResults = samples.stream().map(sample -> evaluateExpression(expression, mapSampleToList(sample))).sorted().collect(Collectors.toList());
/*
At this point evaluated results have been sorted, hence SAMPLE_SIZE/2 -th element
will be the median. We choose samples median as a constraint constant because this guarantees us
approximately half of state space elements will not violate the constraint.
*/
double constant = getConstant(evaluatedResults, comparatorEnum);
samples = samples.stream().filter(sample -> evaluateComparator(comparatorEnum, evaluateExpression(expression, mapSampleToList(sample)), constant)).collect(Collectors.toList());
return new ConstantExpression(new DoubleValue(constant));
}
private double getConstant(List<Double> evaluatedSamples, ComparatorEnum comparatorEnum) {
int middle = evaluatedSamples.size() /2;
int constantIndex = middle;
if (comparatorEnum == ComparatorEnum.GREATER_OR_EQUAL_TO || comparatorEnum == ComparatorEnum.GREATER_THAN) {
constantIndex -= random.nextInt(middle);
} else {
constantIndex += random.nextInt(middle);
}
return evaluatedSamples.get(constantIndex);
}
private Pair<VMConfiguration, GeographicCoordinate> sampleComponentData(int component) {
List<VMConfiguration> configurations = variableGenerator.getComponentToConfiguration().get(component);
List<GeographicCoordinate> locations = variableGenerator.getComponentToLocation().get(component);
return new Pair<>(
configurations.get(random.nextInt(configurations.size())),
locations.get(random.nextInt(locations.size()))
);
}
private Map<Integer, Pair<VMConfiguration, GeographicCoordinate>> sample() {
Map<Integer, Pair<VMConfiguration, GeographicCoordinate>> sample = new HashMap<>();
IntStream.range(0, variableGenerator.getComponentsCount())
.forEach( component -> sample.put(component, sampleComponentData(component)));
return sample;
}
private Map<String, NumericValueInterface> mapSampleToList(Map<Integer, Pair<VMConfiguration, GeographicCoordinate>> sample) {
Map<String, NumericValueInterface> result = new HashMap<>();
Map<Integer, List<NumericValueInterface>> domains = variableGenerator.getVariableDomains();
sample.keySet().forEach(
component -> {
result.put(NamesProvider.getVariableName(component* NamesProvider.VARIABLES_PER_COMPONENT + VariableTypeOrderer.mapTypeToIndex(VariableType.CORES)),
new LongValue(sample.get(component).getValue0().getCores()));
result.put(NamesProvider.getVariableName(component* NamesProvider.VARIABLES_PER_COMPONENT + VariableTypeOrderer.mapTypeToIndex(VariableType.STORAGE)),
new LongValue(sample.get(component).getValue0().getDisk()));
result.put(NamesProvider.getVariableName(component* NamesProvider.VARIABLES_PER_COMPONENT + VariableTypeOrderer.mapTypeToIndex(VariableType.RAM)),
new LongValue(sample.get(component).getValue0().getRam()));
result.put(NamesProvider.getVariableName(component* NamesProvider.VARIABLES_PER_COMPONENT + VariableTypeOrderer.mapTypeToIndex(VariableType.LATITUDE)),
new LongValue(sample.get(component).getValue1().getLatitude()));
result.put(NamesProvider.getVariableName(component* NamesProvider.VARIABLES_PER_COMPONENT + VariableTypeOrderer.mapTypeToIndex(VariableType.LONGITUDE)),
new LongValue(sample.get(component).getValue1().getLongitude()));
List<NumericValueInterface> cardinalityDomain = domains
.get(component* NamesProvider.VARIABLES_PER_COMPONENT + VariableTypeOrderer.mapTypeToIndex(VariableType.CARDINALITY));
result.put(NamesProvider.getVariableName(component* NamesProvider.VARIABLES_PER_COMPONENT + VariableTypeOrderer.mapTypeToIndex(VariableType.CARDINALITY)),
cardinalityDomain.get(random.nextInt(cardinalityDomain.size())));
List<NumericValueInterface> providerDomain = domains
.get(component* NamesProvider.VARIABLES_PER_COMPONENT + VariableTypeOrderer.mapTypeToIndex(VariableType.PROVIDER));
result.put(NamesProvider.getVariableName(component* NamesProvider.VARIABLES_PER_COMPONENT + VariableTypeOrderer.mapTypeToIndex(VariableType.PROVIDER)),
providerDomain.get(random.nextInt(providerDomain.size())));
}
);
return result;
}
private double evaluateExpression(Expression expression, Map<String, NumericValueInterface> vars) {
if (expression instanceof ConstantExpression) {
return ((ConstantExpression) expression).getValue().getDoubleValue();
} else if (expression instanceof VariableExpression) {
return vars.get(((VariableExpression) expression).getVariableName()).getDoubleValue();
} else if (expression instanceof ComposedExpression) {
Expression exp1 = ((ComposedExpression) expression).getLeftExpr();
Expression exp2 = ((ComposedExpression) expression).getRightExpr();
return ExpressionEvaluator.evaluateOnOperator(
((ComposedExpression) expression).getOperator(),
Arrays.asList(
evaluateExpression(exp1, vars),
evaluateExpression(exp2, vars)
)
);
}
throw new RuntimeException("Unrecognized expression type!");
}
}
package eu.melodic.upperware.cp_sampler.generator;
import eu.melodic.upperware.cp_wrapper.utils.numeric_value.implementations.DoubleValue;
import eu.melodic.upperware.cp_sampler.expressions.*;
import eu.melodic.upperware.cp_sampler.utils.priors.Priors;
import eu.paasage.upperware.metamodel.cp.ComparatorEnum;
import eu.paasage.upperware.metamodel.cp.OperatorEnum;
import org.javatuples.Pair;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Random;
public class ConstraintGenerator {
private enum ExpressionSampleType {
PRODUCT,
SUM,
MIXED
}
private Map<Integer, ComparatorEnum> comparatorIndex = new HashMap<Integer, ComparatorEnum>(){{
put(0, ComparatorEnum.GREATER_OR_EQUAL_TO);
put(1, ComparatorEnum.GREATER_THAN);
put(2, ComparatorEnum.LESS_OR_EQUAL_TO);
put(3, ComparatorEnum.LESS_THAN);
put(4, ComparatorEnum.DIFFERENT);
put(5, ComparatorEnum.EQUAL_TO);
}};
private Random random = new Random();
private ConstraintEvaluator constraintEvaluator;
private VariableGenerator variableGenerator;
private int componentsCount;
public ConstraintGenerator(ConstraintEvaluator constraintEvaluator, VariableGenerator variableGenerator, int componentsCount) {
this.variableGenerator = variableGenerator;
this.constraintEvaluator = constraintEvaluator;
this.componentsCount = componentsCount;
}
public Constraint generateConstraint() {
Pair<Expression, ExpressionSampleType> exp = sampleExpression();
ComparatorEnum comparator = sampleComparator(exp.getValue1());
Expression constant = constraintEvaluator.getConstant(exp.getValue0(), comparator);
return new Constraint(exp.getValue0(), constant, comparator);
}
private OperatorEnum sampleOperator() {
double unif = random.nextDouble();
if (unif <= 0.3) {
return OperatorEnum.PLUS;
} else if (unif <= 0.6) {
return OperatorEnum.MINUS;
} else {
return OperatorEnum.TIMES;
}
}
private Expression sampleLongSumOrLongProduct(OperatorEnum operator) {
List<VariableExpression> vars = variableGenerator.sampleVariablesForLongExpression();
variableGenerator.removeRandomElementsFromList(vars, 3);
ComposedExpression exp = new ComposedExpression(vars.get(0), vars.get(1), operator);
for (int i = 2; i < vars.size(); i++) {
exp = new ComposedExpression(exp, vars.get(i), operator);
}
return exp;
}
private ConstantExpression sampleConstant() {
return new ConstantExpression(new DoubleValue(100*random.nextDouble()));
}
private Expression sampleTwoArgExpression() {
OperatorEnum operator = sampleOperator();
Pair<VariableExpression, VariableExpression> vars = variableGenerator.samplePairOfVariables();
if (random.nextDouble() > Priors.CONSTANT_IN_TWO_ARGS_PROB) {
return new ComposedExpression(vars.getValue0(), vars.getValue1(), operator);
} else {
return new ComposedExpression(vars.getValue0(), sampleConstant(), operator);
}
}
private Expression sampleVariableExpression() {