繁体   English   中英

通过回溯算法设置Java功能

[英]Java power set through backtrack algorithm

我似乎在使用回溯实现功率设定算法方面遇到问题。 我要达到的目标很简单,生成任何给定数字的幂集: [1 2 3] => [1] [2] [3]; [1,2] [1,3] [2,3]; [1,2,3]

我的算法使用堆栈放置数字,将数字添加到堆栈中并将其发送进行计算。 代码如下:

public int calculatePowerSet(int x, LinkedList<Integer> arr)
{
    int size = 1;
    int nrOfTimes=0;
    int calculate =0;
    boolean goOn=true;
    Stack<Integer> stack = new Stack<Integer>();
    int k=0, len = arr.size();
    double temp=0.0f;
    while(size<=len)
    {
        goOn=true;
        stack.push(arr.get(0));
        k = arr.indexOf(stack.peek());
        temp = size;    //ignore these as they are for calculating time
        temp/=len;      //ignore these as they are for calculating time
        temp*=100;      //ignore these as they are for calculating time
        setPowerSetPrecentage((int)temp);
        while(goOn)
        {
            if(isStopProcess())return 0;
            if((k==len)&&(stack.size()==0)) goOn=false;
            else if(stack.size()==size) 
            {
                String sign = "";   
                if((stack.size()%2)==0) sign="+";
                else sign="-";
                calculate =calculateSets(stack.toArray(), sign, calculate, x);
                k = arr.indexOf(stack.pop())+1;
            }
            else if(k==len)
                k = arr.indexOf(stack.pop())+1;
            else
            {
                prepereStack(stack,arr.get(k));
                k++;
            }
        }
        size++;
    }
    return calculate;
}

这是计算方法:

private int calculate(int[] arr2, int x)
{
        int calc=1;

        float rez = 0;
        for(int i=0;i<arr2.length;i++)
            calc*=arr2[i];
        rez = (float)(x/calc);
        calc = (int) (rez+0.5d);
        return calc;
}

该代码对于所有20以下的数字似乎都可以正常工作,但是在那之后我似乎得到了错误的结果。 由于有数百种组合,因此无法手动检查数字。 例如,对于一个25个数字的输入,我应该得到1229的结果,而我得到1249。我不确定我丢失了什么,因为我认为该算法在理论上应该是可行的,因此,如果有人提出任何建议,那将是一个很好的建议。

我建议从计算中分离出功率集的生成。 尽管有一些非常有效的算法可用于生成功率集,但我建议保持相当简单,直到需要效率为止。

private void forEachSet(List<Integer> currentSet, List<Integer> rest) {
    if (rest.isEmpty()) {
        process(currentSet);
    } else {
        Integer nextInt = rest.remove(0);
        forEachSet(currentSet, rest);
        currentSet.add(nextInt);
        forEachSet(currentSet, rest);
        current.remove(nextInt);
        rest.add(nextInt);
    }
}

public forEachSet(List<Integer> set) {
    forEachSet(new ArrayList<>(), new ArrayList<>(set));
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM