簡體   English   中英

不復制C鏈表拆分

[英]Splitting C linked list without making a copy

我有這個結構:

typedef struct node {
    struct node *m_Next;
    int id;
} NODE;

我需要將鏈表分成兩半。 如果它不能分成兩個相同的部分,我想從更大的列表中刪除最后一個。

示例:整個列表: {1,2,3,4,5} ; 我需要什么: A:{1,2} B:{3,4} (最后一個被丟棄)

我有這個 function 來分隔列表:

void split(NODE *src, NODE **p1, NODE **p2) {
    int len = get_length(src);
    if (len < 2) {
        *p1 = NULL;
        *p2 = NULL;
        return;
    }
    struct node *current = src;
    int c = (len - 1) / 2;
    for (int i = 0; i < c; i++) {
        current = current->m_Next;
    }
    *p1 = src;
    *p2 = current->m_Next;
    current->m_Next = NULL;
}

它適用於偶數列表,但是當我嘗試用 7 個結構分隔某些東西時,我有兩個問題:

a)最后一個不指向NULL b)它以某種方式對數據進行洗牌(我期望: A:{1,2,3} B:{4,5,6} | 我得到: A:{1,2,3} B:{5,4,7}例如)

誰能幫我正確拆分列表並添加偶數/奇數條件?

我已經有了 function 來刪除最后一個結構:

deleteNode(struct TSoldier *firstNode)

我只是目前不使用它,因為拆分 function 被竊聽。

謝謝:)

首先,值得注意的是,以下代碼可能會導致memory 泄漏

if (len < 2) {
    *p1 = NULL;
    *p2 = NULL;
    return;
}

如果節點數等於 1,那么除非您保留對該節點的其他引用,否則 memory 將被泄露。 您可能在 function 之外有這樣的引用,但您可能會丟棄此引用,只保留寫入p1p2的值,這意味着 memory 已泄露。

因此,假設您使用malloc分配節點,您可能需要添加該行

free( src );

為了防止 memory 泄漏,或使用您的 function deleteNode

正如在另一個答案中已經指出的那樣,這條線

int c = (len - 1) / 2;

是錯的。 它應該是:

int c = len / 2 - 1;

在 function split的末尾,如果節點數是奇數,則必須添加代碼以丟棄最終節點,例如:

if ( len % 2 == 1 )
{
    current = *p2;
    for (int i = 0; i < c; i++) {
        current = current->m_Next;
    }
    free( current->m_Next );
    current->m_Next = NULL;
}

確定前半部分的最后一個節點,而不是int c = (len - 1) / 2; 您應該使用適用於偶數和奇數長度的公式:

int c = len / 2 - 1;

同樣,如果長度為奇數且大於 1,則刪除最后一個節點:

if (len & 1) {
    NODE *node = src;
    for (int i = 2; i < len; i++) {
        node = node->m_Next;
    }
    deleteNode(node->m_Next);
    node->m_Next = NULL;
}

這是使用快速和慢速掃描技巧的另一種方法:

void split(NODE *src, NODE **p1, NODE **p2) {
    NODE *last = src;
    *p1 = *p2 = NULL;
    if (src && src->m_Next) {
        NODE *slow = src;
        NODE *fast = src;
        while (fast->m_Next && fast->m_Next->m_Next) {
            slow = slow->m_Next;
            fast = fast->m_Next->m_Next;
        }
        *p1 = src;
        *p2 = slow->m_Next;
        slow->m_Next = NULL;
        last = fast->m_Next;  // last will be non NULL if length is odd
        fast->m_Next = NULL;
    }
    if (last) {
        deleteNode(last);  // drop the last node if required
    }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM