合併兩個有序的單鏈表,合併後依然有序
阿新 • • 發佈:2018-11-07
分析過程:
首先我要合併有序的連結串列,合併後依然有序。我就要有兩個指標,分別指向兩個連結串列,觀察所給的兩個連結串列是升序還是降序的來確定合併後的連結串列是否有序。(這裡預設的認為連結串列時升序的)
用指標分別指向兩個連結串列的第一個節點,比較大小,那個大,將元素尾插進入我所要返回的新連結串列中去。一次比較迴圈往復,直至某一個連結串列為空為止。但有可能會出現一個連結串列為空,另一個連結串列不為空。我們就要在最後檢測,將不為空連結串列的全部掛在我要返回元素的後面。因為要不停的給新連結串列尾插。所以我用一個指標,將新連結串列的尾部標記。
程式碼如下所示
//合併兩個有序連結串列,合併後依然有序的測試
SLinkList* MergeLinkList(SLinkList* pHead1, SLinkList* pHead2)
{
SLinkList* New = NULL;//合併後的連結串列
SLinkList* tail = NULL;//標記合併後連結串列的尾部,方便尾插
SLinkList* cur1 = pHead1;
SLinkList* cur2 = pHead2;
SLinkList* nxt = NULL;//用來儲存連結串列的後續節點
while (cur1 != NULL && cur2 != NULL)
{
if (cur1->_data <= cur2->_data)
{
nxt = cur1->_pNext;//儲存cur1後面的節點
//應取連結串列1的結點:將cur1指向的結點從連結串列1上取下來,掛在新連結串列上,後序的連結串列應該儲存下來,否則程式會奔潰
if (New == NULL)
{ //合併的連結串列為空
New = cur1;//將cur1指向的結點掛在新連結串列上
}
else
{ //合併連結串列不為空
tail->_pNext = cur1;
}
cur1->_pNext = NULL;//尾插,連結串列的最後一個元素應為空
//儲存新連結串列的最後一個節點
tail = cur1;
cur1 = nxt;
}
else
{
nxt = cur2->_pNext;//儲存cur1後面的節點
//應取連結串列1的結點:將cur1指向的結點從連結串列1上取下來,掛在新連結串列上,後序的連結串列應該儲存下來,否則程式會奔潰
if (New == NULL)
{ //合併的連結串列為空
New = cur2;//將cur1指向的結點掛在新連結串列上
}
else
{ //合併連結串列不為空
tail->_pNext = cur2;
}
cur2->_pNext = NULL;//尾插,連結串列的最後一個元素應為空
//儲存新連結串列的最後一個節點
tail = cur2;
cur2 = nxt;
}
}
//一個連結串列空了,但要判斷裡另一個連結串列為不為空
if (cur1 == NULL)
{
tail->_pNext = cur2;
}
if (cur2 == NULL)
{
tail->_pNext = cur1;
}
return New;
}
由於這個程式碼有許多重複的步驟,優化可得
這裡寫程式碼片
連結串列結構、測試程式碼、執行結果
typedef int DataType;
typedef struct ListNode
{
DataType _data; //當前節點中所儲存的元素
struct ListNode* _pNext; //指向連結串列中下一個結點
}SLinkList, SListNode;
void Test_MergeLinkList()
{
SLinkList* pHead1 = NULL;
SLinkList* pHead2 = NULL;
PushBack(&pHead1, 2);
PushBack(&pHead1, 4);
PushBack(&pHead1, 5);
PushBack(&pHead1, 7);
PushBack(&pHead2, 1);
PushBack(&pHead2, 3);
PushBack(&pHead2, 5);
PushBack(&pHead2, 6);
printf("連結串列1:");
PrintSLinkList(pHead1);
printf("連結串列2:");
PrintSLinkList(pHead2);
SLinkList* pHead3 = MergeLinkList(pHead1, pHead2);
printf("新連結串列:");
PrintSLinkList(pHead3);
SLinkList* pHead3OP = MergeLinkListOP(pHead1, pHead2);
printf("優化後的新連結串列:");
PrintSLinkList(pHead3);
}