1. 程式人生 > 其它 >02 設計連結串列(leecode 707)

02 設計連結串列(leecode 707)

技術標籤:# 資料結構與演算法02-連結串列資料結構leetcode

1 問題

在連結串列類中實現這些功能:

get(index):獲取連結串列中第 index 個節點的值。如果索引無效,則返回-1。
addAtHead(val):在連結串列的第一個元素之前新增一個值為 val 的節點。插入後,新節點將成為連結串列的第一個節點。
addAtTail(val):將值為 val 的節點追加到連結串列的最後一個元素。
addAtIndex(index,val):在連結串列中的第 index 個節點之前新增值為 val  的節點。如果 index 等於連結串列的長度,則該節點將附加到連結串列的末尾。如果 index 大於連結串列長度,則不會插入節點。如果index小於0,則在頭部插入節點。
deleteAtIndex(index):如果索引 index 有效,則刪除連結串列中的第 index 個節點。

示例:

MyLinkedList linkedList = new MyLinkedList();
linkedList.addAtHead(1);
linkedList.addAtTail(3);
linkedList.addAtIndex(1,2);   //連結串列變為1-> 2-> 3
linkedList.get(1);            //返回2
linkedList.deleteAtIndex(1);  //現在連結串列是1-> 3
linkedList.get(1);            //返回3

2 解法

class MyLinkedList {
public
: /** Initialize your data structure here. */ //定義連結串列結構體 struct LinkedNode{ LinkedNode *next; int val; //建構函式,初始化列表初始化val、next LinkedNode(int val) : val(val), next(nullptr){} }; //成員變數定義 private: //連結串列長度 int m_size; //虛擬頭節點 LinkedNode *m_dummyHead;
public: //類建構函式 MyLinkedList() { m_size = 0; m_dummyHead = new LinkedNode(0); } //獲取連結串列中第 index 個節點的值。如果索引無效,則返回-1。 int get(int index) { //1.索引無效 if(index < 0 || index > m_size - 1) return -1; //2.索引有效 //定義遍歷連結串列的指標cur,其指向頭節點 LinkedNode *cur = m_dummyHead->next; //向後遍歷cur,直至index=0 while(index--) { cur = cur->next; } return cur->val; } //在連結串列的第一個元素之前新增一個值為 val 的節點。 void addAtHead(int val) { //需要新增的新節點 LinkedNode *newNode = new LinkedNode(val); //新節點的下個節點為表頭節點 newNode->next = m_dummyHead->next; //虛擬節點的下個節點是新節點 m_dummyHead->next = newNode; //連結串列長度加1 m_size++; } //在連結串列的最後一個元素後新增一個值為 val 的節點。 void addAtTail(int val) { //需要新增的新節點 LinkedNode *newNode = new LinkedNode(val); //定義遍歷連結串列的節點,初始指向虛擬節點,可以處理頭節點為null的情況 LinkedNode *cur = m_dummyHead; //使cur遍歷到末尾節點 while(cur->next != nullptr) { cur = cur->next; } // 末尾節點的下個節點為新節點 cur->next = newNode; //連結串列長度加1 m_size++; } //在連結串列中的第 index 個節點之前新增值為 val 的節點。如果 index 等於連結串列的長度,則該節點將附加到連結串列的末尾。如果 index 大於連結串列長度,則不會插入節點。如果index小於0,則在頭部插入節點。 void addAtIndex(int index, int val) { //1.不插入節點直接返回的情況(index > m_size) if(index > m_size) return; //2.index //需要插入的新節點 LinkedNode *newNode = new LinkedNode(val); //定義遍歷連結串列的節點cur,初始指向虛擬節點 LinkedNode *cur = m_dummyHead; //將cur遍歷到index的前一個節點 //包含index小於0的情況與index=m_size情況 while(index--) { cur = cur->next; } //新節點的下個節點是index節點 newNode->next = cur->next; //index前一個節點(cur)的下個節點是新節點 cur->next = newNode; //連結串列長度加1 m_size++; } //如果索引 index 有效,則刪除連結串列中的第 index 個節點。 void deleteAtIndex(int index) { //1.index無效情況,直接返回 if(index < 0 || index > m_size - 1) return; //2.index有效 //定義遍歷連結串列的指標cur LinkedNode *cur = m_dummyHead; //遍歷cur至index前一個節點 while(index--) { cur = cur->next; } //中間節點變數暫存index節點 LinkedNode *tmp = new LinkedNode(0); tmp = cur->next; //index前一個節點(cur)的下一個節點變為index的下一個節點 cur->next = cur->next->next; //釋放index節點的記憶體 delete tmp; //連結串列長度減1 m_size--; } //列印連結串列 void printLinkedList(){ //定義遍歷連結串列的指標cur LinkedNode *cur = m_dummyHead; //遍歷到末尾節點,若初始節點為null則不列印 while(cur->next != nullptr) { cout << cur->next->val << " "; cur = cur->next; } } }; /** * Your MyLinkedList object will be instantiated and called as such: * MyLinkedList* obj = new MyLinkedList(); * int param_1 = obj->get(index); * obj->addAtHead(val); * obj->addAtTail(val); * obj->addAtIndex(index,val); * obj->deleteAtIndex(index); */