片方向リンクリストのマージソートは、リストの中に、最終的な数のI入力より大きい任意の数字を削除しているようです

fourteen14:

私は現在、単独リンクリストのためのマージメカニズムを策定しようとしています。これらは、このような操作を行うための重要な要素であることを研究し、マージソート単独リンクリストをソートするための最良の方法である)Aについて一貫性のあるアイデアを見つけ、そしてB)を通じ、私はこの次のコードで到着しました。それはほとんど意図どおりに動作しますが、最後の入力された数よりも大きい整数のすべてを返します。例えば、7、6、5、4、3、2入力、1、1、2、3、4、5、6、7、しかし1の入力、2、3、4、5のみ5. Iを戻します戻ります「それはちょうど逆の順序で番号を入力するには、ローカライズの問題ではないですので、使用されるランダム入力注文VEのが、文字通り任意の順序。数は、最終的な数よりも小さい場合は、ソート処理のリストから削除されます。私はすべてではこの原因を見つけることができません。

任意およびすべてのアドバイスや提案は、より多くの歓迎されている、とあなたが持っている任意の入力に感謝。私は本当にここにすべての入力/建設的な批判を歓迎するように、リンクされたリストと再帰の私の知識は、最大ではありません。

    public Node mergeSort(Node head) {
    if (head == null || head.getNext() == null) return head;
    Node midpoint = findMidpoint(head);
    Node rightliststart = midpoint.getNext();                       
    midpoint.setNext(null);                                                         
    Node rightlist = mergeSort(rightliststart);
    Node sorted = sort(leftlist, rightlist);
    return sorted;
}

  public Node findMidpoint(Node head) {                             
        if (head == null) return head;
        Node slowpointer = head;
        Node fastpointer = slowpointer.getNext();
        while (fastpointer != null) {
            fastpointer = fastpointer.getNext();
            if (fastpointer != null) {
                slowpointer = slowpointer.getNext();
                fastpointer = fastpointer.getNext();
            }
        }
        return slowpointer;
    }

    public Node sort(Node one, Node two) {
        Node temp = null;
        if (one == null) return two;
        if (two == null) return one;
        if (one.getData() <= two.getData()) {
            temp = one;
            temp.setNext(sort(one.getNext(), two));
        }
        else {
            temp = two;
            temp.setNext(sort(one, two.getNext()));
        }
        return temp;
    }
rcgldr:

例のマージコード。ダミー・ノードは、コードを簡略化するために使用されるどのようにこの番組は、(最初​​のノードがマージに更新ヘッドに特殊なケースを回避します)。

    // merge two already sorted lists
    static Node merge(Node list0, Node list1) {
        if(list0 == null)
            return list1;
        if(list1 == null)
            return list0;
        Node temp = new Node();         // dummy node
        Node dest = temp;
        while(true){
            if(list0.data <= list1.data){
                dest.next = list0;
                dest = list0;
                list0 = list0.next;
                if(list0 == null){
                    dest.next = list1;
                    break;
                }
            } else {
                dest.next = list1;
                dest = list1;
                list1 = list1.next;
                if(list1 == null){
                    dest.next = list0;
                    break;
                }
            }
        }
        return temp.next;
    }

マージソートのコードダウンの例トップ。それはリストにのみ各再帰分割のN / 2個のノードを走査し、(高速、低速の)二重スキャンを避けるために、リストの大きさを得るために一回走査します。

    // return size of list
    static int size(Node head) {
    int i = 0;
        while(head != null){
            head = head.next;
            i++;
        }
        return i;
    }

    // advance to node n
    static Node advance(Node head, int n) {
        while(0 < n--)
            head = head.next;
        return head;
    }

    // top down merge sort for single link list entry function
    static Node sorttd(Node head) {
        int n = size(head);
        if(n < 2)
            return head;
        head = sorttdr(head, n);
        return head;
    }

    // top down merge sort for single link list recursive function
    static Node sorttdr(Node head, int n) {
        if(n < 2)
            return head;
        int n2 = (n/2);
        Node node = advance(head, n2-1);
        Node next = node.next;
        node.next = null;
        head = sorttdr(head, n2);
        next = sorttdr(next, n-n2);
        head = merge(head, next);
        return head;
    }

マージソートのコード例アップ底。これは、配列[i]は2 ^ Iノードとのリストであるリストの小(32)アレイを使用します。ノードが配列にマージされ、その配列は、単一のソートされたリストにマージされます。キャッシュに収まらない大きなリストでは、ランダムに散在のノードと、各ノードごとにキャッシュミスがたくさんあるだろうとは、マージソートアップケースの底が約30%速く、トップダウンよりも、アクセスします。

    // bottom up merge sort for single link list
    static Node sortbu(Node head) {
        final int NUMLIST = 32;
        Node[] alist = new Node[NUMLIST];
        Node node;
        Node next;
        int i;
        // if < 2 nodes, return
        if(head == null || head.next == null)
            return null;
        node = head;
        // merge node into array
        while(node != null){
            next = node.next;
            node.next = null;
            for(i = 0; (i < NUMLIST) && (alist[i] != null); i++){
                node = merge(alist[i], node);
                alist[i] = null;
            }
            if(i == NUMLIST)   // don't go past end of array
                i--;
            alist[i] = node;
            node = next;
        }
        // node == null
        // merge array into single list
        for(i = 0; i < NUMLIST; i++)
            node = merge(alist[i], node);
        return node;
    }

おすすめ

転載: http://43.154.161.224:23101/article/api/json?id=34736&siteId=1