Проблема с кувшином воды java.lang.OutOfMemoryError: пространство кучи Java - PullRequest
0 голосов
/ 11 декабря 2018

Написание фрагмента кода для моего класса ИИ, который предназначен для перечисления всех возможных состояний с учетом трех кувшинов для решения проблемы с кувшином с водой (вы можете заполнить любой кувшин или вылить столько, сколько будет соответствовать из одного в другой, или опустошить любойкувшин столько раз, сколько вы хотите и в любом порядке) начиная с пустых кувшинов.

По какой-то причине, после записи 88, казалось бы, различных состояний, 89-й совпадает с первым, и я заканчиваюпространства, потому что он зацикливается.

Я думаю, что это как-то связано с тем, как я проверяю, что состояния различны, но не могу понять это.Любая помощь будет принята с благодарностью.

import java.util.ArrayList;
    import java.util.List;

public class AI {
    private static final int[] start=new int[]{0,0,0};
    private static int[] jugs;
    public static void main(String[] args){
        jugs=new int[]{Integer.parseInt(args[0]), Integer.parseInt(args[1]),Integer.parseInt(args[2])};

    String out="";
    out=out.concat("{");
    for (int[] state:addStates(start,new ArrayList<>())) {
        out=out.concat("{"+state[0]+","+state[1]+","+state[2]+"}");
    }
    out=out.substring(0,out.length()-2).concat("}");
    System.out.println(out);

}

private static List<int[]> addStates(int[] start, List<int[]> states) {


    states.add(start);

    int[][] newStates={
            fillA(start),
            fillB(start),
            fillC(start),
            emptyA(start),
            emptyB(start),
            emptyC(start),
            pour(start,0,1),
            pour(start,0,2),
            pour(start,1,0),
            pour(start,1,2),
            pour(start,2,0),
            pour(start,2,1)
    };

    for (int[] child:newStates) {
        if (!has(states,child)) {
            states.addAll(addStates(child,states));
        }
    }
    System.out.println("close");
    return states;
}
private static boolean has(List<int[]> list, int[] e) { //finds out if list contains something with the same values as e
    for (int[] el:list) {
        boolean is=true;
        for(int i=0;i<e.length;i++){
            if (el[i]!=e[i]){
                is=false;
            }
        }
        if(is){
            return true;
        }
    }
    return false;
}

private static int[] fillA(int[] state) {
    return new int[]{jugs[0],state[1],state[2]};
} //fills A
private static int[] fillB(int[] state) {
    return new int[]{state[0],jugs[1],state[2]};
} //fills B
private static int[] fillC(int[] state) {
    return new int[]{state[0],state[1],jugs[2]};
} //fills C
private static int[] emptyA(int[] state) {
    return new int[]{0,state[1],state[2]};
} //empties A
private static int[] emptyB(int[] state) {
    return new int[]{state[0],0,state[2]};
} //empties B
private static int[] emptyC(int[] state) {
    return new int[]{state[0],state[1],0};
} //empties C
private static int[] pour(int[] state, int from, int into) {
    int currentInto=state[into];
    int currentfrom=state[from];
    if (currentInto+currentfrom>jugs[into]){
        currentfrom-=(jugs[into]-currentInto);
        currentInto=jugs[into];
    } else {
        currentInto+=currentfrom;
        currentfrom=0;
    }

    int[] newState= new int[3];
    newState[from]=currentfrom;
    newState[into]=currentInto;
    newState[3-from-into]=state[3-from-into];

    return newState;
} //moves as much water from "from" into "into"

}

1 Ответ

0 голосов
/ 31 января 2019

Проблема заключалась в том, что я использовал states.add(start) и states.addAll(addStates(child,states)), что означало, что я добавлял каждый элемент огромное количество раз.После исправления этого код работал отлично.

...