單向鏈表節點的奇偶性排序

更詳細的講解和代碼調試演示過程,請參看視頻
如何進入google,算法面試技能全面提高指南vue

給定一個單項鍊表,要求實現一個算法,把鏈表分紅兩部分,前一部分全是下標爲偶數的節點,後一部分全是下標爲奇數的節點,例如給定鏈表爲下圖的第一個隊列,要求編寫一個算法,將鏈表轉換爲第二個隊列:node

要求算法不能分配多餘的內存,同時,在操做鏈表是,不能更改節點內部的內容,只能更改節點的next 指針。面試

若是容許分配新內存,那麼咱們能夠先把奇數下標的節點存成一個隊列,把偶數下標的節點存成另外一個隊列,而後把兩隊列收尾鏈接便可。但限制條件是不能分配新內存,所以問題的解決須要一點小技巧。算法

咱們能夠這麼作,用一個指針evenHead,專門指向偶下標節點,用另外一個指針,oddHead指向奇下標節點。咱們注意到,偶下標節點的下一個節點正好是奇下標節點,同時奇下標節點的下一個節點正好是偶下標節點。所以,若是咱們把 evenHead.nex 指向 oddHead.next, oddHead.next 指向evenHead.next ,那麼,咱們就能實現偶下標節點連在一塊兒,奇下標節點連在一塊兒的效果,例如:微信

evenHead 指向節點0,oddHead指向節點1, oddHead.next 指向節點2,若是把evenHead的next指針設置成oddHead的next, 那至關於把節點0和2連在一塊兒,而後把evenHead挪到它的next指針指向的節點:markdown

此時evenHead的next指向的是節點3,正好是一個奇下標節點,此時把oddHead的next指向evenHead.next那麼就能夠實現奇數節點連成一體了:app


將上面操做循環下去,直到遍歷完整個隊列,那麼咱們的目標就達到了。這個算法沒有分配新內存,同時只需對整個鏈表遍歷一次足夠,所以算法複雜度是O(n),空間複雜度是O(1).函數

實現代碼以下:ui

public class EvenOddListSorter {
    private Node listHead;
    private Node evenHead, oddHead;

    public EvenOddListSorter(Node head) {
        this.listHead = head;
    }


    public Node sort() {
        if (listHead == null || listHead.next == null) {
            return listHead;
        }

        evenHead = listHead;
        oddHead = listHead.next;
        Node node = oddHead;

        while (evenHead.next != null && oddHead.next != null) {
            if (oddHead.next != null) {
                evenHead.next = oddHead.next;
                evenHead = evenHead.next;
            }

            if (evenHead.next != null) {
                oddHead.next  = evenHead.next;
                oddHead = oddHead.next;
            }
        }

        evenHead.next = node;
        return listHead;
    }
}

sort函數所實現的正好是咱們前面所描述的邏輯。主函數實現以下:this

public class LinkList {
    public static void main(String[] args) {
        ListUtility util1 = new ListUtility();
        Node head = util1.createList(10);
        EvenOddListSorter sorter = new EvenOddListSorter(head);
        head = sorter.sort();
        util1.printList(head);
    }
}

咱們先構造一個長度爲10的隊列,而後對其進行節點的奇偶排序,最後打印出的結果以下:

0 -> 2 -> 4 -> 6 -> 8 -> 1 -> 3 -> 5 -> 7 -> 9 -> null

因而可知,咱們算法的實現是正確的。更詳細的代碼講解和調試,請參看視頻。


本文分享自微信公衆號 - Coding迪斯尼(gh_c9f933e7765d)。
若有侵權,請聯繫 support@oschina.cn 刪除。
本文參與「OSC源創計劃」,歡迎正在閱讀的你也加入,一塊兒分享。

相關文章
相關標籤/搜索