public static void main(String[] args) throws Err {

    // Chooses the Alloy4 options
    A4Options opt = new A4Options();
    opt.solver = A4Options.SatSolver.SAT4J;

    // abstract sig A {}
    PrimSig A = new PrimSig("A", Attr.ABSTRACT);

    // sig B {}
    PrimSig B = new PrimSig("B");

    // one sig A1 extends A {}
    PrimSig A1 = new PrimSig("A1", A, Attr.ONE);

    // one sig A2 extends A {}
    PrimSig A2 = new PrimSig("A2", A, Attr.ONE);

    // A { f: B lone->lone B }
    Expr f = A.addField("f", B.lone_arrow_lone(B));
    // Since (B lone->lone B) is not unary,  the default is "setOf",  meaning "f:set (B lone->lone
    // B)"

    // A { g: B }
    Expr g = A.addField("g", B);
    // The line above is the same as:   A.addField(null, "g", B.oneOf())  since B is unary.
    // If you want "setOf", you need:   A.addField(null, "g", B.setOf())

    // pred someG { some g }
    Func someG = new Func(null, "SomeG", null, null, g.some());

    // pred atMostThree[x:univ, y:univ] { #(x+y) >= 3 }
    Decl x = UNIV.oneOf("x");
    Decl y = UNIV.oneOf("y");
    Expr body = x.get().plus(y.get()).cardinality().lte(ExprConstant.makeNUMBER(3));
    Func atMost3 = new Func(null, "atMost3", Util.asList(x, y), null, body);

    List<Sig> sigs = Arrays.asList(new Sig[] {A, B, A1, A2});

    // run { some A && atMostThree[B,B] } for 3 but 3 int, 3 seq
    Expr expr1 = A.some().and(atMost3.call(B, B));
    Command cmd1 = new Command(false, 3, 3, 3, expr1);
    A4Solution sol1 = TranslateAlloyToKodkod.execute_command(NOP, sigs, cmd1, opt);
    System.out.println("[Solution1]:");
    System.out.println(sol1.toString());

    // run { some f && SomeG[] } for 3 but 2 int, 1 seq, 5 A, exactly 6 B
    Expr expr2 = f.some().and(someG.call());
    Command cmd2 = new Command(false, 3, 2, 1, expr2);
    cmd2 = cmd2.change(A, false, 5);
    cmd2 = cmd2.change(B, true, 6);
    A4Solution sol2 = TranslateAlloyToKodkod.execute_command(NOP, sigs, cmd2, opt);
    System.out.println("[Solution2]:");
    System.out.println(sol2.toString());
  }
예제 #2
0
  /**
   * Constructs a new relation to Alloy translator. Translates a relation (top or non top) to Alloy
   * in a given direction.
   *
   * @param relation the relation being translated
   * @param top whether the relation is top or not
   * @throws EchoError
   */
  Relation2Alloy(
      EAlloyTransformation transformation_translator,
      Boolean top,
      Relation2Alloy parent_translator,
      EDependency dependency,
      ERelation relation)
      throws EchoError {
    this.relation = relation;
    this.dependency = dependency;
    this.top = top;
    this.transformation_translator = transformation_translator;
    this.parent_translator = top ? this : parent_translator;

    for (EModelParameter mdl : relation.getTransformation().getModels()) {
      Decl d;
      String metamodelID = mdl.getMetamodel().ID;
      try {
        d =
            AlloyEchoTranslator.getInstance()
                .getMetamodel(metamodelID)
                .sig_metamodel
                .oneOf(mdl.getName());
      } catch (Err a) {
        throw new ErrorAlloy(
            ErrorAlloy.FAIL_CREATE_VAR,
            "Failed to create transformation model variable: " + mdl.getName(),
            a,
            Task.TRANSLATE_TRANSFORMATION);
      }
      model_params_decls.add(d);
      modelparam2var.put(mdl.getName(), d.get());
      var2model.put(d.get().label, null);
      var2var.put(d.get().label, d.get());
    }

    initVariableLists();

    Field field = null;
    if (!top) field = addRelationField();

    Expr fact = calculateFact();
    AlloyOptimizations opt = new AlloyOptimizations();
    if (EchoOptionsSetup.getInstance().isOptimize() && true) {
      fact = opt.trading(fact);
      fact = opt.onePoint(fact);
    }
    EchoReporter.getInstance().debug("Post-opt: " + fact);

    if (top) addRelationPred(fact);
    else addRelationDef(fact, field);
  }