1 package org.simantics.scl.compiler.elaboration.query;
3 import org.simantics.scl.compiler.common.names.Names;
4 import org.simantics.scl.compiler.elaboration.contexts.ReplaceContext;
5 import org.simantics.scl.compiler.elaboration.expressions.EApply;
6 import org.simantics.scl.compiler.elaboration.expressions.QueryTransformer;
7 import org.simantics.scl.compiler.elaboration.query.compilation.ConstraintCollectionContext;
8 import org.simantics.scl.compiler.elaboration.query.compilation.DerivateException;
9 import org.simantics.scl.compiler.elaboration.query.compilation.QueryCompilationContext;
10 import org.simantics.scl.compiler.elaboration.query.compilation.QueryConstraint;
11 import org.simantics.scl.compiler.elaboration.query.compilation.UnsolvableQueryException;
12 import org.simantics.scl.compiler.elaboration.relations.LocalRelation;
13 import org.simantics.scl.compiler.types.Type;
15 import gnu.trove.map.hash.THashMap;
16 import gnu.trove.set.hash.TIntHashSet;
19 public class QNegation extends QAbstractModifier {
21 public QNegation(Query query) {
26 public void collectConstraints(ConstraintCollectionContext context) throws UnsolvableQueryException {
27 TIntHashSet vars = new TIntHashSet();
28 query.collectVars(context.getVariableMap(), vars);
30 final QueryCompilationContext innerContext = context.getQueryCompilationContext().createCheckContext();
31 query.generate(innerContext);
33 context.addConstraint(new QueryConstraint(vars.toArray()) {
36 for(int v : variables)
37 variableMask |= 1L << v;
40 public double getSolutionCost(long boundVariables) {
41 if((boundVariables & variableMask) != variableMask)
42 return Double.POSITIVE_INFINITY;
43 return innerContext.getCost();
46 public double getSolutionBranching(long boundVariables) {
47 if((boundVariables & variableMask) != variableMask)
48 return Double.POSITIVE_INFINITY;
49 return innerContext.getBranching();
52 public boolean canBeSolvedFrom(long boundVariables) {
53 return (boundVariables & variableMask) == variableMask;
57 public long getVariableMask() {
61 public void generate(QueryCompilationContext context) {
62 context.condition(new EApply(
63 context.getConstant(Names.Prelude_not, Type.EMPTY_ARRAY),
64 innerContext.getContinuation()));
70 public Query replace(ReplaceContext context) {
71 return new QNegation(query.replace(context));
75 public Diff[] derivate(THashMap<LocalRelation, Diffable> diffables) throws DerivateException {
76 Diff[] diffs = query.derivate(diffables);
80 throw new DerivateException(location);
84 public void accept(QueryVisitor visitor) {
89 public Query accept(QueryTransformer transformer) {
90 return transformer.transform(this);