コード例 #1
0
ファイル: Main.java プロジェクト: eric7237cire/CodeJam
  /**
   * For the small solution, an example of Integer Linear Programming
   *
   * @param in
   * @return
   */
  public String handleCase2(InputData in) {

    List<Double> zeroCoef = Collections.nCopies(in.N, 0d);

    // 8 0 1 2 0
    // assigned.put(2, 1);
    // assigned.put(3, 2);
    Stack<Simplex> assignementsToTry = new Stack<>();
    Simplex s2 = new Simplex(in.N);
    addConstraints(s2, new HashMap<Integer, Integer>(), in);

    assignementsToTry.add(s2);
    Map<Integer, Integer> assigned = new HashMap<Integer, Integer>();

    int tries = 0;

    while (!assignementsToTry.isEmpty()) {
      ++tries;

      Simplex simplex = assignementsToTry.pop();

      log.info("Tries {}", tries);
      List<Double> solution = Lists.newArrayList();
      boolean f = false; // simplex.doPhase1(solution);

      if (!f) {
        // return String.format("Case #%d: Impossible", in.testCase, solution.subList(0, in.N));
        continue;
      }

      int smallestNonIntIndex = -1;
      double smallest = Double.MAX_VALUE;
      List<Integer> solInt = Lists.newArrayList();

      for (int solIndex = 0; solIndex < in.N; ++solIndex) {

        double sol = solution.get(solIndex);
        double solAsInt = Math.rint(sol);
        if (Math.abs(solAsInt - sol) > 1e-5 && sol < smallest) {
          smallestNonIntIndex = solIndex;
          smallest = solution.get(solIndex);
        }

        if (assigned.containsKey(solIndex)) {
          solInt.add(assigned.get(solIndex));
        } else {
          solInt.add((int) Math.rint(solution.get(solIndex)));
        }
      }

      if (smallestNonIntIndex == -1) {
        return String.format("Case #%d: %s", in.testCase, Joiner.on(' ').join(solInt));
      } else {
        Simplex try1 = new Simplex(simplex);
        Simplex try2 = new Simplex(simplex);

        double nonIntSolution = solution.get(smallestNonIntIndex);

        Preconditions.checkState(nonIntSolution >= 0d);
        double intSolutionLB = Math.ceil(nonIntSolution);
        double intSolutionUP = Math.floor(nonIntSolution);

        List<Double> coeffsTry1 = Lists.newArrayList(zeroCoef);
        List<Double> coeffsTry2 = Lists.newArrayList(zeroCoef);
        coeffsTry1.set(smallestNonIntIndex, 1d);
        coeffsTry2.set(smallestNonIntIndex, 1d);

        try2.addConstraintLTE(coeffsTry2, intSolutionUP);
        try1.addConstraintGTE(coeffsTry1, intSolutionLB);

        assignementsToTry.add(try1);
        assignementsToTry.add(try2);
      }
    }

    return String.format("Case #%d: Impossible", in.testCase);

    /*if (1==1)
    return String.format("Case #%d: Impossible", in.testCase);

    List<Double> solution = Lists.newArrayList();
    List<Double> solutions = solution.subList(0, in.N);

    log.info("Solutions {}", solutions);

    List<Fraction> solutionFra = Lists.transform(solutions, new Function<Double,Fraction>(){
       public Fraction apply(Double arg) {
           return new Fraction(arg);
       }
    });

    long lcm = 1;

    for(Fraction fr : solutionFra) {
        if (fr.getNumerator() == 0)
            continue;

        lcm = LongMath.checkedMultiply(lcm, fr.getDenominator() / LongMath.gcd(lcm, fr.getDenominator()));
    }

    List<Integer> solInt = Lists.newArrayList();
    for(Fraction fr : solutionFra) {
        solInt.add( Ints.checkedCast(LongMath.checkedMultiply(lcm, fr.getNumerator()) / fr.getDenominator()));
    }

    return String.format("Case #%d: %s", in.testCase, Joiner.on(' ').join(solInt));*/
  }
コード例 #2
0
ファイル: Main.java プロジェクト: eric7237cire/CodeJam
  private boolean addConstraints(Simplex s, Map<Integer, Integer> assigned, InputData in) {
    List<Double> zeroCoef = Collections.nCopies(in.N, 0d);

    for (int i = 0; i < in.N - 1; ++i) {
      int max = in.highest[i] - 1;

      for (int j = i + 1; j < max; ++j) {
        List<Double> coeffs = Lists.newArrayList(zeroCoef);

        coeffs.set(max, (double) j - i);
        coeffs.set(i, (double) max - j);
        coeffs.set(j, (double) i - max);

        double rhs = 1;

        int cof = 0;
        for (int all = 0; all < in.N; ++all) {
          if (coeffs.get(all) != 0 && assigned.containsKey(all)) {
            rhs -= coeffs.get(all) * assigned.get(all);
            coeffs.set(all, 0d);
            ++cof;
          }
        }

        if (cof == 3) {
          Preconditions.checkState(rhs >= 0);
        }

        s.addConstraintGTE(coeffs, rhs);

        log.debug("Eq : {}Y{} + {}Y{} + {}Y{} >= 1", j - i, max, max - j, i, i - max, j);
      }

      for (int j = max + 1; j < in.N; ++j) {
        List<Double> coeffs = Lists.newArrayList(zeroCoef);

        coeffs.set(max, (double) j - i);
        coeffs.set(i, (double) max - j);
        coeffs.set(j, (double) i - max);

        double rhs = 0;

        int cof = 0;
        for (int all = 0; all < in.N; ++all) {
          if (coeffs.get(all) != 0 && assigned.containsKey(all)) {
            rhs -= coeffs.get(all) * assigned.get(all);
            coeffs.set(all, 0d);
            ++cof;
          }
        }

        if (cof == 3 && rhs < 0) {
          return false;
        }

        s.addConstraintGTE(coeffs, rhs);

        log.debug("Eq : {}Y{} + {}Y{} + {}Y{} >= 0", j - i, max, max - j, i, i - max, j);
      }
    }

    return true;
  }