Hundred-million-level sorting-garbage notebook 78ms to achieve 100-million-level sorting (Part 2)

Not much to say: the first results attract attention

tip: For larger data volumes or other more demanding environments, consider divide and conquer

Test Results

The time-consuming
Insert picture description here
memory consumption: minimal (Without vmvare, comes up with the idea 4M)
computer configuration
Insert picture description here

demand

How to extract the largest 100 numbers in the 1E level of data.
Idea:
Use a custom ordered singly linked list to filter (here in ascending order)

  1. For values ​​smaller than the leftmost value, discard directly without any processing
  2. For values ​​greater than the rightmost (maximum) value, the linked list is shifted to the right (that is, the leftmost is deleted, and the rightmost is added)
  3. For values ​​larger than the leftmost value and smaller than the maximum value, the subscript is shifted to the right until a value larger than him is encountered,
  4. For only greater than the leftmost value, change the value directly to the leftmost value
  5. For the middle value (larger than the leftmost value and smaller than the rightmost value), we assign the leftmost node to this value, and extract the
    idea of inserting the middle (position at 2 has been obtained) +
    for a larger order of magnitude data, we The idea of ​​divide and conquer can be adopted, so the idea can theoretically handle unlimited orders of data
package practice;

import java.util.*;

public class Main {
    
    
    class ListNode {
    
    
        int val;
        ListNode next;
        public ListNode() {
    
    
        }

        public ListNode(int val) {
    
    
            this.val = val;
        }
    }
    public ListNode createNode(int val){
    
    
        return new ListNode(val);
    }
    public static void main(String[] args) {
    
    
        Main main = new Main();
        int ti=0;
        //赋予1E个随机数字,用于排序
        int[] arr=new int[10000*10000];
        Random random=new Random();
        for (int i = 0; i < arr.length; i++) {
    
    
            arr[i]=random.nextInt();
        }
        //开始计时
        long start = System.currentTimeMillis();
        //抽取数组前100位并排序,用于初始化链表
        int[] ints = Arrays.copyOfRange(arr, 0, 100);
        Arrays.sort(ints);
        ListNode root=main.createNode(0);
        root.next=main.createNode(Integer.MIN_VALUE);
        ListNode curr=root.next;
        //记录最后一个
        ListNode last=curr;
        //初始化长度100的链表
        for (int i = 0; i < ints.length; i++) {
    
    
            curr.next=main.createNode(ints[i]);
            last=curr;
            curr=curr.next;
        }

        //筛除最大100个
        for (int i = 0; i < arr.length; i++) {
    
    
            curr=root.next;
            //比最左大才判断,否则直接舍弃
            if (arr[i]>curr.val) {
    
    
                //首先跟最右比较,比最右大
                if (arr[i] >= last.val) {
    
    
                    //是最大,删除最左,添加最右
                    root.next = root.next.next;
                    last.next = main.createNode(arr[i]);
                    last = last.next;
                } else {
    
    
                    //比最左边大,下标右移,直至右边比其大
                    while (curr.next != null && arr[i] > curr.next.val) {
    
    
                        curr = curr.next;
                    }
                    //右移完成
                    //处于最左边,最左边直接复制
                    if (curr.val==root.next.val) {
    
    
                        curr.val=arr[i];
                    }
                    //处于中间
                    else {
    
    
                        //增加新中间节点,废物利用,减少新对象的创建
                        ListNode node=root.next;
                        node.val=arr[i];
                        //删除最左节点
                        root.next = root.next.next;
                        //串联新增节点
                        node.next=curr.next;
                        curr.next=node;
                    }
                }
            }
        }
        //计时结束
        System.out.println("总计用时");
        System.out.println(System.currentTimeMillis()-start);
        //遍历,校验结果
        curr=root.next;
        while (curr!=null)
        {
    
    
            System.out.println(curr.val);
            curr=curr.next;
        }
    }
}



Guess you like

Origin blog.csdn.net/weixin_43158695/article/details/113199734