排序—堆排序

本文借鉴与 一线码农 的博客

   

   

   

   

package com.ufida.practice.suanfa.sort;

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

public class HeapAdjust {

    public static void main(String[] args) {
        List<Integer> list = new ArrayList();
        for (int i = 0; i < 20000; i++)
            list.add(new Random().nextInt(100000));
        HeapSort(list);
        for (int j = 0; j < list.size(); j++)
            System.out.println(list.get(j));
    }

    public static void HeapAdjust(List<Integer> list, int parent, int length) {
        
        int temp = list.get(parent);// temp保存当前父节点
        int child = 2 * parent + 1;// 得到左孩子
        while (child < length) {
            // 如果parent有右孩子,则要判断左孩子是否小于右孩子
            if (child + 1 < length && list.get(child) < list.get(child + 1))
                child++;

            // 父亲节点大于子节点,就不用做交换
            if (temp >= list.get(child))
                break;

            // 将较大子节点的值赋给父亲节点
            list.set(parent, list.get(child));

            // 然后将子节点做为父亲节点,已防止是否破坏根堆时重新构造
            parent = child;

            // 找到该父亲节点较小的左孩子节点
            child = 2 * parent + 1;
        }
        // 最后将temp值赋给较大的子节点,以形成两值交换
        list.set(parent, temp);
    }

    public static void HeapSort(List<Integer> list) {
        // list.Count/2-1:就是堆中父节点的个数
        for (int i = list.size() / 2 - 1; i >= 0; i--) {
            HeapAdjust(list, i, list.size());
        }

        // 最后输出堆元素
        for (int i = list.size() - 1; i > 0; i--) {
            // 堆顶与当前堆的第i个元素进行值对调
            int temp = list.get(0);
            list.set(0, i);
            list.set(i, temp);

            // 因为两值交换,可能破坏根堆,所以必须重新构造
            HeapAdjust(list, 0, i);
        }
    }
}
posted @ 2013-01-05 15:59  爱我所艾  阅读(152)  评论(0编辑  收藏  举报