資料結構之單鏈表(C++實現)
阿新 • • 發佈:2019-02-12
很早前就想用C++來實現那些常用的資料結構。
今天就算是個開端把。還是那句話,看的再多不如自己動手寫一遍。
按照自己的思路寫。首先你得熟悉那種結構的特點,然後才能談實現。
連結串列是一種很常用的資料結構。支援在任意地方對資料進行增刪改查。
但是不支援隨機訪問。所以複雜度就有些高了。寫的時候出了個問題。
最後把記憶體查看了幾遍。並不是儲存資料的結點出問題了。而是在連結串列轉置
的時候用到的那個int *p = new int(length).出問題了。因為習慣了C的malloc,
所以就那麼寫。最後才發現這樣並沒有申請到需要的lenght個int長度的記憶體。
把()改成[]就好了。所以只有多用才能發現更多的錯誤。否則永遠停留在理論層面上,
沒有實踐,貌似就是扯淡。
Link的功能不多,就那麼些。當然你可以擴充套件。
gcc和vc6.0下通過。一個.cpp檔案對應一個.h檔案這樣的規範比較好。
.h裡面的函式如果很小就可以寫出來,如果比較大,就寫在.cpp檔案裡面。
以後會陸陸續續實現那些常用的資料結構C++版本。
你們的訪問和評論是俺前進的強大動力啊。所以,親啊,試試多花幾秒鐘在鍵盤上寫寫你的對問題
的看法。
轉載請註明出處,謝謝!
Link.h
#ifndef LINK_H #define LINK_H //結構體的定義 struct myLink{ int value; //資料域 struct myLink *next; //指標域 }; class Link{ private: struct myLink *head; //頭指標 struct myLink *cur; //當前位置的指標 int length; //link的長度 public: Link(){//default constructor head = cur =NULL; //預設link是空的 length = 0; } Link(const Link &L){//禁止copy constructor throw "not allowed"; } Link& operator=(const Link &L){//禁止assignment constructor throw "not allowed"; } void add(int data);//新增元素到連結串列,預設到尾部新增 int getData(int pos);//得到第pos位置的元素 int remove(int pos);//移除某個位置的元素 void sort();//對link進行排序 int insert(int pos, int data);//在第pos個位置data插入到link void reverse();//對link進行轉置 void display();//對link的元素進行顯示 int modify(int pos, int data);//更改第pos個位置的data int getLength(){//得到link的長度 return length; } ~Link(); //destructor }; #endif
Link.cpp
#include <iostream> #include "Link.h" void Link::add(int data){ struct myLink *u = new struct myLink; u->value = data; u->next = NULL; if (NULL == head){//頭結點也儲存資料 head = u; cur = u; }else { cur->next = u; cur = u; //當前指標改為u } length++; } int Link::getData(int pos){ if (length >= pos && length > 0){//連結串列非空並且無越界 int count = 0;//計數 while (pos != count){ count++; if (1 == count) cur = head;//頭指標成為當前指標 else cur = cur->next;//指標後移 } return cur->value; } return -1; //其它返回-1 } int Link::remove(int pos){ if (length >= pos && length > 0){//連結串列非空並且無越界 int count = 1;//計數 while (pos != count){//得到第pos位置的前一個指標 count++; if (2 == count) cur = head;//頭指標成為當前指標 else cur = cur->next;//指標後移 } struct myLink *temp; if (1 == count){ //如果remove第一個資料,就應該特殊處理下,因為頭結點也儲存了data temp = head; head = temp->next; delete temp; }else { temp = cur->next; cur->next = temp->next; delete temp; } length--; //不要忘了將length-- return 0; } return -1;//其它返回-1 } int Link::insert(int pos, int data){ if (length >= pos && length > 0){//連結串列非空並且無越界 int count = 1;//計數 while (pos != count){//找到當前位置的前一個指標 count++; if (2 == count) cur = head;//頭指標成為當前指標 else cur = cur->next;//指標後移 } struct myLink *u = new struct myLink; u->value = data; if (1 == count){ u->next = head; head = u;//當前結點成為頭結點 }else { u->next = cur->next;//新加結點的指向當前結點的下一個結點 cur->next = u; //當前結點指向新加結點 } length++; //不要忘了 return 0; } return -1;//其它返回-1 } void Link::sort(){ if (length > 1){ int count = 0; while (length - 1 != count){ int i = count + 1; struct myLink *temp = head; cur = head; //當前結點指向頭結點 while (length != i ){ if (cur->value > cur->next->value){ cur->value += cur->next->value; cur->next->value = cur->value - cur->next->value; cur->value -= cur->next->value; } cur = cur->next; i++; } temp = temp->next; count++; } } } void Link::reverse(){//通過改變指標域來轉置,效率更高點 if (length > 0){ int count = 0; int *p = new int[length];//不要寫成new int(length),最後俺找了2個多小時才找出來這裡出錯了 //new int(length)沒有申請length個int的記憶體, cur = head; //當前結點指向頭結點 while (length != count){ p[count] = (int)cur;//將指標儲存在p[i]中 count++; cur = cur->next; } count = 0; struct myLink *temp = head; //輔助指標 while (length != count){ count++; cur = (struct myLink *)p[length - count];//反轉 if (1 == count){ head = cur;//最後一個結點成為頭結點 temp = head; } else { temp->next = cur; //當前結點成為上一個結點的後繼結點 temp = temp->next; //temp後移 } } cur->next = NULL; delete []p; } } int Link::modify(int pos, int data){ if (length >= pos && length > 0){//連結串列非空並且無越界 int count = 0;//計數 while (pos != count){ count++; if (1 == count) cur = head;//頭指標成為當前指標 else cur = cur->next;//指標後移 } cur->value = data; return 0; } return -1;//其它返回-1 } void Link::display(){ if (length > 0){ std::cout<<"data in the Link is:"<<std::endl; int count = 0; cur = head; //當前結點指向頭結點 while (length != count){ count++; std::cout<<"the "<<count<<" data is "<<cur->value<<std::endl; cur = cur->next; } } } Link::~Link(){ if (NULL != head){ cur = head; //從頭結點開始delete while (0 != length){ head = cur->next; //頭結點後移 delete cur; cur = head; length--; } } }