問題描述:
輸入一個鏈表,從尾到頭打印鏈表每個節點的值。
輸入描述:
輸入為鏈表的表頭
輸出描述:
輸出為需要打印的“新鏈表”的表頭
方法一:通過借助容器vector和棧stack共同完成
解決這個問題肯定要遍歷鏈表。遍歷的順序是從頭到尾的順序,可輸出的順序卻是從尾到頭。也就是說第一個遍歷到的結點最后一個輸出,而最后一個遍歷到得結點第一個輸出。這就是典型的“后進先出”,可以用棧實現這種順序。每經過一個結點的時候,把該結點放到一個棧中。當遍歷完整個鏈表后,再從棧頂開始逐個取出節點的值,放入vector容器中。
1 //鏈表結構體定義 2 struct ListNode { 3 int val; 4 struct ListNode *next; 5 ListNode(int x) : 6 val(x), next(NULL) { 7 } 8 }; 9 10 class Solution { 11 public: 12 vector<int> printListFromTailToHead(struct ListNode* head) { 13 14 vector<int> result;//存儲輸出的節點的值 15 stack<struct ListNode*> nodes;//用棧來存儲每個節點 16 17 struct ListNode* pNode = head;//從鏈表頭開始 18 while (pNode != NULL){ //鏈表的所有節點全部入棧 19 nodes.push(pNode); 20 pNode = pNode->next; 21 } 22 23 while (!nodes.empty()){ //出棧:后進先出 24 pNode = nodes.top(); 25 result.push_back(pNode->val); 26 nodes.pop(); 27 } 28 return result; 29 } 30 };
方法二: 不使用容器vector,直接用print結合遞歸方式實現鏈表的反向打印
遞歸在本質上就是一個棧結構,於是很自然地想到用遞歸來實現 要實現反過來輸出鏈表每訪問到一個結點的時候, 先遞歸輸出它后面的結點,再輸出該結點自身,這樣鏈表的輸出結構就反過來了。
1 struct ListNode { 2 int val; 3 struct ListNode *next; 4 ListNode(int x) : 5 val(x), next(NULL) { 6 } 7 }; 8 9 void printListFromTailToHead(ListNode* pListHead){ 10 if(pListHead!=NULL){ 11 12 //print the next node first 13 if(pListHead->next!=NULL){ 14 printListFromTailToHead(pListHead->next); 15 } 16 17 // And then print the current node 18 print("%d",pListHead->val); 19 } 20 }
方法三: 不使用棧結構stack,直接利用翻轉函數reverse()函數和容器vector
每訪問到一個結點的時候,取出節點的值放入容器中,最后使用翻轉函數reverse()將容器翻轉。
1 struct ListNode { 2 int val; 3 struct ListNode *next; 4 ListNode(int x) : 5 val(x), next(NULL) { 6 } 7 }; 8 9 class Solution{ 10 public: 11 vector<int> printListFromTailToHead(struct ListNode* head){ 12 vector<int> result; 13 struct ListNode* pNode=head; 14 15 while(pNode!=NULL){ 16 result.push_back(pNode->val); 17 pNode=pNode->next; 18 } 19 20 reverse(result.begin(),result.end());//applying reverse() 21 return result; 22 } 23 };
