D堆没有产生正确的顺序

时间:2017-04-25 00:34:39

标签: java heap

我的程序运行,但它总是给出错误的答案。以下是一些示例运行:

输入堆元素:15 1 14 2 13 3 12 4 11 5 10 6 9 7 8

输入d:3

输出:堆(d = 3):1 2 3 4 5 6 7 15 11 13 10 14 9 12 8

应该是:

输入堆元素:15 1 14 2 13 3 12 4 11 5 10 6 9 7 8

输入d:3

输出:堆(d = 3):1 3 4 2 7 15 12 14 11 5 10 6 9 13 8

import java.util.Scanner;
import java.util.Arrays;

public class D_heap<AnyType extends Comparable<? super AnyType>>
{
    private int d;

    private final static int DEFAULT_CAPACITY = 10;

    private int currentSize;      
    private AnyType [ ] array; // 
    /**
     * Construct the binary heap.
     */
    public D_heap( )
    {
         this(2, DEFAULT_CAPACITY );
    }

    /**
     * Construct the binary heap.
     * @param capacity the capacity of the binary heap.
     */

    public D_heap(int numChild )
    {
        this(numChild, DEFAULT_CAPACITY);
    }

    public D_heap(int numChild, int cap )
    {
        currentSize = 0;
        d = numChild;
        array = (AnyType[]) new Comparable[ cap + 1 ];
    }

    /**
     * Construct the binary heap given an array of items.
     */
    //public D_heap( AnyType [ ] items )
    //{
     //   currentSize = items.length;
      //  array = (AnyType[]) new Comparable[ ( currentSize + 2 ) * 11 / 10 ];

     //   int i = 1;
     //   for( AnyType item : items )
      //      array[ i++ ] = item;
      //  buildHeap( );
    //}

    /**
     * Insert into the priority queue, maintaining heap order.
     * Duplicates are allowed.
     * @param x the item to insert.
     */
    public void insert( AnyType x )
    {
        if( currentSize == array.length - 1 )
            enlargeArray( array.length * 2 + 1 );

            // Percolate up
        int hole = ++currentSize;
        for( ; hole > 1 && x.compareTo( array[ getParent(hole)] ) < 0; hole = getParent(hole) ) 
            array[ hole ] = array[getParent(hole)];

        array[ hole ] = x;
    }


    private void enlargeArray( int newSize )
    {
        AnyType [] old = array;
        array = (AnyType []) new Comparable[ newSize ];
        for( int i = 0; i < old.length; i++ )
            array[ i ] = old[ i ];        
    }

    /**
     * Find the smallest item in the priority queue.
     * @return the smallest item, or throw an UnderflowException if empty.
     */
    public AnyType findMin( )
    {
        if( isEmpty( ) )
            throw new UnderflowException(" ");
        return array[ 1 ];
    }

    /**
     * Remove the smallest item from the priority queue.
     * @return the smallest item, or throw an UnderflowException if empty.
     */
    public AnyType deleteMin( )
    {
        if( isEmpty( ) )
            throw new UnderflowException(" ");

        AnyType minItem = findMin( );
        array[ 1 ] = array[ currentSize-- ];
        percolateDown( 1 );

        return minItem;
    }

    /**
     * Establish heap order property from an arbitrary
     * arrangement of items. Runs in linear time.
     */
    private void buildHeap( )
    {
        for( int i = currentSize / 2; i > 0; i-- )
            percolateDown( i );
    }

    /**
     * Test if the priority queue is logically empty.
     * @return true if empty, false otherwise.
     */
    public boolean isEmpty( )
    {
        return currentSize == 0;
    }

    /**
     * Make the priority queue logically empty.
     */
    public void makeEmpty( )
    {
        currentSize = 0;
    }

    public void print( )
    {
        for( int i = 0; i < currentSize; i++ )
            System.out.printf("%d ",  array[i+1]);
        System.out.println();
    }

    /**
     * Internal method to percolate down in the heap.
     * @param hole the index at which the percolate begins.
     */
    private void percolateDown( int hole )
    {
        int child = getChild(hole);
        int tempChild = getChild (hole);
        AnyType tmp = array[ hole ];

        for( ; getChild(hole) <= currentSize; hole = child) {
            child = getChild(hole);
            tempChild = getChild(hole);

            for(int i = 0; i < d && tempChild != currentSize; i++, tempChild++){
                if(array[tempChild + 1].compareTo(array[child]) < 0){
                child = tempChild + 1;
                }
            }

        if (array[child].compareTo(tmp) < 0)
            array[hole] = array[child];
        else
            break;

        }

        array[ hole ] = tmp;
    }

        // Test program
    public static void main( String [ ] args )
    {
        Scanner in = new Scanner(System.in);


        D_heap<Integer> h = new D_heap<Integer>();


        System.out.print ("How many numeric values do you want to enter? ");
        int num = in.nextInt();
        System.out.print ("Enter heap elements: ");

        for (int i = 1; i <= num; i++){
            h.insert (in.nextInt());
        }


        System.out.print ("Enter d: ");
        int d = in.nextInt();

        System.out.printf ("Output: Heap (d= %d): ", d); 
        h.buildHeap();
        h.print();

        // Create the array of Strings containing the main menu options (Quit - option 0)
        // Create the mainMenu object
        String opts[] = {"Exit program", "Insert", "deleteMin", "Pick new d value", };
        Menu mainMenu = new Menu(opts);


        int opt = 0;
        do {
            opt = mainMenu.runMenu();
            switch (opt) {
                case 1: 

                    System.out.print ("Enter element to insert: ");
                    int x = in.nextInt();
                    h.insert(x);
                    h.print();
                    break;

                case 2: 
                    h.deleteMin();  
                    h.print();
                    break;
                case 3:  
                    System.out.print ("Enter new d: ");
                    d = in.nextInt();
                    h.buildHeap();
                    h.print();
                    break;


               default:
                    System.out.println ("Thank you - Have a nice day!");
            }
        } while (opt != 0);
    }

    public int getChild( int p){
        return d * (p - 1) + 2;
    }

    public int getParent (int c){
        return (c - 2)/d + 1;
    }
}

0 个答案:

没有答案