[寫文目的]
為了更深入的了解鍊錶,於是在這裡寫出單向鍊錶的公升級版雙向迴圈鍊錶!
[鍊錶介紹]
1.建立鍊錶
首先需要定義乙個結構,一般雙向迴圈鍊錶的結構用於存放儲存在該節點的值,乙個prev指標指向前乙個節點,乙個rnext指標指向下乙個節點,對用結構**如下:
typedef struct node* node;
struct node;
建立乙個
雙向迴圈鍊錶的**如下
node creatlist()
2.插入元素
示意圖為
**為:
void insertitem(node l,int n)
3.刪除元素
示意圖為:
**為:
void deleteitem(node l,int n)//這裡預設n值在鍊錶中存在
//找到儲存n的節點後
node p=l;
l->next->prev=l->prev;
l->prev->next=l->next;
free(p);
l=head;
}
[總結]
對於雙向迴圈鍊錶,我使用的測試**為
#include#includetypedef struct node* node;
struct node;
node creatlist()
void insertitem(node l,int n)
void deleteitem(node l,int n)//這裡預設n值在鍊錶中存在
//找到儲存n的節點後
node p=l;
l->next->prev=l->prev;
l->prev->next=l->next;
free(p);
l=head;
}int main()
return 0;
}
[問題提出]
對於該資料結構,我
引入乙個題目,便於更好的掌握雙向迴圈鍊錶!
題目描述:
編號為 1 - n 的 n 個人按順時針方向圍坐一圈,從第乙個人開始按順時針方向自 1 開
始報數,報到 m 時停止,在報到 m 的那個人的左右的兩個人出列,從他在順時針方向下一
個人開始重新從 1 報數,如此下去。如果還在遊戲的人數少於 3 個,則遊戲終止。在一行
內輸出最後留下來的人編號
★資料輸入
輸入第一行為 t ,代表接下去有 t 組測試, 0 < t < =10
接下去 t行,每行兩個數代表 n 和m,0 < n,m < =1000
★資料輸出
對於每個輸入,在一行內輸出最後留下來的人編號,如果有兩個人留下來,則用空格隔
開,並按從小到大排序。
輸入示例 輸出示例
3
1 2 1
3 1 1
4 2 2 4
[解題思路]
首先我們需要建立雙迴圈鍊錶,節點儲存編號n,以及left跟right(也就相當於prev跟next)用於指向左右節點
typedef struct linkedlist* list;
struct linkedlist
;
建立迴圈鍊錶,由於是1-n的順序,所以我們是在鍊錶尾部,對應**為:
list creatlist(int peoplenum)//傳入參與遊戲的人數
else
} mainlist->left=headlist; //這兩段**用於首尾相連,構成迴圈鍊錶
headlist->right=mainlist;
return headlist; //返回第乙個節點
}
查詢並依次刪除符合點檢的節點的左右節點
void searchlist(list mainlist,int n,int m)
list p,q;//待刪節點,為mainlist的左節點和右節點
p=mainlist->right;
q=mainlist->left;
mainlist->right=p->right;
p->right->left=mainlist;
mainlist->left=q->left;
q->left->right=mainlist;
free(p);
free(q);
n-=2;//刪除操作完成後人數減去兩個人
} if(n==1) printf("%d\n",mainlist->n);
else printf("%d %d\n",(mainlist->n)>(mainlist->left->n)?(mainlist->left->n):(mainlist->n),\
(mainlist->n)left->n)?(mainlist->left->n):(mainlist->n));
}
這個題目的難點就是以上的建立鍊錶乙個刪除符合條件的節點兩個,對應的完整**如下:
#include#includetypedef struct linkedlist* list;
struct linkedlist
;list creatlist(int peoplenum)//傳入參與遊戲的人數
else
} mainlist->left=headlist; //這兩段**用於首尾相連,構成迴圈鍊錶
headlist->right=mainlist;
return headlist; //返回第乙個節點
}void searchlist(list mainlist,int n,int m)
list p,q;//待刪節點,為mainlist的左節點和右節點
p=mainlist->right;
q=mainlist->left;
mainlist->right=p->right;
p->right->left=mainlist;
mainlist->left=q->left;
q->left->right=mainlist;
free(p);
free(q);
n-=2;//刪除操作完成後人數減去兩個人
} if(n==1) printf("%d\n",mainlist->n);
else printf("%d %d\n",(mainlist->n)>(mainlist->left->n)?(mainlist->left->n):(mainlist->n),\
(mainlist->n)left->n)?(mainlist->left->n):(mainlist->n));
}int main()
}
資料結構 雙向迴圈鍊錶
近期我在學習資料結構,於是我自己整理了單鏈表 迴圈單鏈表 雙向鍊錶 雙向迴圈鍊錶的相關 以鞏固這段時間的學習,也希望能夠幫助初學者,希望大家在閱讀以下 時發現問題糾正於我,一起 cycdoublelist.h ifndef cycdoublelish h define cycdoublelish h...
資料結構 雙向迴圈鍊錶
typedef struct node node,pnode pnode init dc list void 雙向迴圈鍊錶的初始化 pnode new node int dat 新建乙個節點 把位址為pnew的節點插入到雙向迴圈鍊錶的尾部 頭節點的前面 bool list add tail pnod...
資料結構之迴圈鍊錶和雙向鍊錶
迴圈鍊錶是另一種形式的鏈式儲存結構,其特點是單鏈表的最後乙個結點的指標不為空,而是指向頭結點 帶頭結點的鍊錶 或第乙個結點 不帶頭結點的鍊錶 整個鍊錶形成乙個環。這樣從鍊錶任何乙個位置出發,均可以找到表中的其他結點。迴圈鍊錶根據指標域是乙個還是多個,可以分為單迴圈鍊錶和多重迴圈鍊錶。對於單迴圈鍊錶而...