在数据库中存储大量的排列

时间:2014-09-26 04:10:48

标签: java

我需要计算并获得大量的所有排列。就像一个包含13个数字的数组。但是,虽然我从互联网上找到的代码工作了10个值,但对于13个数字,它没有工作,因为我得到了一个例外。它说内存不足以显示总排列。我不需要打印排列。对我来说,将它们存储在数据库中将是完美的oki。如果我直接将它们存储在数据库中,我仍然无法进行计算。我无法通过互联网找到合适的答案。

这是我用来计算排列的代码。

public class PermutationCalc {

    /**
     * @param args the command line arguments
     */


    static <E> String arrayToString( E[] arr ) {
        final StringBuffer str = new StringBuffer();
        for ( E e : arr ){
            str.append( e.toString() );
        }
        return str.toString();
    }

    static <E> ArrayList<E[]> permutations(E[] arr) {



        final ArrayList<E[]> resultList = new ArrayList<E[]>();
        final int l = arr.length;
        if ( l == 0 ) return resultList;
        if ( l == 1 )
        {
            resultList.add( arr );
            return resultList;
        }

        E[] subClone = Arrays.copyOf( arr, l - 1);
        System.arraycopy( arr, 1, subClone, 0, l - 1 );

        for ( int i = 0; i < l; ++i ){
            E e = arr[i];
            if ( i > 0 ) subClone[i-1] = arr[0];
            final ArrayList<E[]> subPermutations = permutations( subClone );
            for ( E[] sc : subPermutations )
            {
                E[] clone = Arrays.copyOf( arr, l );
                clone[0] = e;
                System.arraycopy( sc, 0, clone, 1, l - 1 );
                resultList.add( clone );
            }
            if ( i > 0 ) subClone[i-1] = e;
        }
        return resultList;
    }

    static ArrayList<String> permutations(String arr) {
        final Character[] c = new Character[arr.length()];
        for ( int i = 0; i < arr.length(); ++i )
            c[i] = arr.charAt( i );

        final ArrayList<Character[]> perms = permutations(c);
        final ArrayList<String> resultList = new ArrayList<String>( perms.size() );

        for ( Character[] p : perms )
        {
            resultList.add( arrayToString( p ) );
        }
        return resultList;
    }

    public static void main(String[] args) {
        //ArrayList<String> str_perms = permutations( "abc" );
        //for ( String p : str_perms ) System.out.println( p );

       ArrayList<Integer[]> int_perms = permutations( new Integer[]{ 1, 2, 3,4,5,6,7,8,9,10} );
       System.gc();
       for ( Integer[] p : int_perms ) System.out.println( arrayToString( p ) );


    }
    }

有人可以告诉我,如果我将它们存储在数据库中并进行计算,我是否能够解决它。

PS:有没有其他有效的代码我可以用来找到13!排列值。

5 个答案:

答案 0 :(得分:1)

只是添加一些简单的想法:这似乎是需要聪明的问题之一 - 我的意思是对于N位数字,当然有N!不同的排列,但只有我们假设所有N个数字都是唯一的!考虑数字:11111 - 只有1个排列!对于11112,只有5个排列,或者5个选择1(想想它,因为有5个位置,我们选择其中5个中的哪个进入。而不是盲目地计算所有可能的排列,你应该首先考虑存在多少唯一排列。

这是一项学校任务,所以我不会多说。

答案 1 :(得分:0)

在此代码中,您似乎首先尝试获取所有排列,然后将它们存储到数据库中,

由于缺少内存以将整个结果存储在数组列表中而发生OutOfMemoryError异常,

所以尝试将结果逐个部分存储在数据库中,而不是等待整个结果。让我们一次考虑100个排列。

方法static <E> ArrayList<E[]> permutations(E[] arr)中的

尝试此更改,

    for ( E[] sc : subPermutations )
        {
            E[] clone = Arrays.copyOf( arr, l );
            clone[0] = e;
            System.arraycopy( sc, 0, clone, 1, l - 1 );
            resultList.add( clone );
            if(resultList.size() == 100) {
                //your code to store current result in the database here.
                resultList.clear(); //clear the ArrayList.
            }
        }
    if(!resultList.isEmpty()) {
       //your code to store current result in the database here.
       resultList.clear(); //clear the ArrayList.
    }

或类似的事情。

答案 2 :(得分:0)

实际存储所有排列很愚蠢。存储数据一次,然后存储 任何需要排列数据的排列数。 提示:十三件物品有13件!排列。您需要超过6千兆字节 即使您的数组项目各为1个字节。

答案 3 :(得分:0)

你得到一个OutOfMemoryError exception,因为你没有基本案例来削减递归函数。它只会调用自己,直到你得到错误。这大约是base case

for word permutation

private static void permutation(String prefix, String str) {
    int n = str.length();
    if (n == 0) System.out.println(prefix);//or add to arraylist
    else {
        for (int i = 0; i < n; i++)
            permutation(prefix + str.charAt(i), str.substring(0, i) + str.substring(i+1, n));
    }
}

如果数字

//remember that permutation can have a repeating value or not. size is the size of the number or simply the number itself numberDraw is how many times you need to draw numbers from the pool 

private static void computePermutation(boolean isRepeting, int size,
            int numberDraw) {

        int result = 1;
        int currentsize = size;
        for (int i = 0; i < numberDraw; i++) {
            System.out.println(currentsize);
            result *= currentsize;
            if (!isRepeting) {
                currentsize -= 1;
            }
        }
        System.out.println("premute number: " + result);
    }

参考:recursion permutation

答案 4 :(得分:0)

这是获得特定长度的所有排列的一般解决方案 - 按字典顺序排列。关于是否应该将这些数据输入数据库的问题必须在其他地方得到解答。

/**
 * Generates the permutations in lexicographic order.
 */
public class LexicographicPermutationsIterator extends PermutationsIterator implements Iterator<List<Integer>> {

    public LexicographicPermutationsIterator(int length) {
        super(length);
    }

    @Override
    protected boolean nextPerm() {
        boolean got = false;
        // Find the largest index k such that a[k] < a[k + 1]. If no such index exists, the permutation is the last permutation.
        int k = -1;
        for (int i = 0; i < length - 1; i++) {
            if (indexes.get(i) < indexes.get(i + 1)) {
                k = i;
            }
        }
        if (k >= 0) {
            int ak = indexes.get(k);
            // Find the largest index l such that a[k] < a[l].
            int l = k + 1;
            for (int i = 0; i < length; i++) {
                if (ak < indexes.get(i)) {
                    l = i;
                }
            }
            // Swap the value of a[k] with that of a[l].
            Collections.swap(indexes, k, l);
            // Reverse the sequence from a[k + 1] up to and including the final element a[n].
            Collections.reverse(indexes.subList(k + 1, indexes.size()));
            // We got one.
            got = true;
        }
        return got;
    }

}

/**
 * Iterates over permutations.
 *
 * Actually - it manages a list of Integers that are used as indexes into permutation.
 *
 * The indexes can then be used to permute the objects.
 */
public abstract class PermutationsIterator extends SequenceIterator<List<Integer>> {

    // Length of the lists required.
    protected final int length;
    // The working list.
    protected final List<Integer> indexes;

    public PermutationsIterator(int length) {
        this.length = length;
        // Build my initial indexes as 0..length
        indexes = new ArrayList<>(length);
        for (int i = 0; i < length; i++) {
            indexes.add(i);
        }
        // Start with the initial position.
        next = Collections.<Integer>unmodifiableList(indexes);
    }

    protected abstract boolean nextPerm();

    @Override
    protected List<Integer> getNext() {
        // Mutate the indexes into the next permutation.
        if (nextPerm()) {
            // That's next!
            return Collections.<Integer>unmodifiableList(indexes);
        }
        return null;
    }

}

/**
 * Implements a sequence as an iterator - leaving a getNext() method for the sequence.
 *
 * @param <T> The type that will be iterated over.
 */
public abstract class SequenceIterator<T> implements Iterator<T> {

    // The next to deliver.
    protected T next = null;

    // Return a new next if one is available.
    protected abstract T getNext();

    @Override
    public boolean hasNext() {
        if (next == null) {
            // Is there one?
            next = getNext();
        }
        return next != null;
    }

    @Override
    public T next() {
        T n = hasNext() ? next : null;
        next = null;
        return n;
    }

    @Override
    public void remove() {
        throw new UnsupportedOperationException("Cannot remove from sequence");
    }

}

public void test() {
    try {
        for (int l = 0; l < 5; l++) {
            System.out.println("l = " + l);
            LexicographicPermutationsIterator lit = new LexicographicPermutationsIterator(l);
            while (lit.hasNext()) {
                System.out.println(lit.next());
            }
        }
    } catch (Throwable t) {
        t.printStackTrace(System.err);
    }
}
相关问题