【再思考】1025. 反转链表 (25)

来源:互联网 发布:哈奇森效应 知乎 编辑:程序博客网 时间:2024/06/06 00:50

给定一个常数K以及一个单链表L,请编写程序将L中每K个结点反转。例如:给定L为1→2→3→4→5→6,K为3,则输出应该为3→2→1→6→5→4;如果K为4,则输出应该为4→3→2→1→5→6,即最后不到K个元素不反转。

输入格式:

每个输入包含1个测试用例。每个测试用例第1行给出第1个结点的地址、结点总个数正整数N(<= 105)、以及正整数K(<=N),即要求反转的子链结点的个数。结点的地址是5位非负整数,NULL地址用-1表示。

接下来有N行,每行格式为:

Address Data Next

其中Address是结点地址,Data是该结点保存的整数数据,Next是下一结点的地址。

输出格式:

对每个测试用例,顺序输出反转后的链表,其上每个结点占一行,格式与输入相同。

输入样例:
00100 6 400000 4 9999900100 1 1230968237 6 -133218 3 0000099999 5 6823712309 2 33218
输出样例:
00000 4 3321833218 3 1230912309 2 0010000100 1 9999999999 5 68237

68237 6 -1

先上一版正确答案,但是里面的关键算法用的C++里面SIL中的reverse,考试做题是一种快速解决问题的好方法,但是对于面试来说,还是要仔细斟酌,好好想想怎么反转;第二版是我自己原先写的,题意都理解错了,居然还能得19分,题目是每K个反转一次,不是前K个反转。回头自己再好好想想

正确代码:

#include<vector>#include <sstream>#include<cmath>#include<iomanip>#include<iostream>#include <ctype.h>#include <stdlib.h>#include <algorithm>#include <map>#include <utility>using namespace std;//1025. 反转链表 (25)struct List{int addr;int value;int next;};int main(){int head,n,k;cin >> head >> n >> k;int index[100005] = {-1};vector<List> lists;int cnt = 0;for (int i = 0; i < n; i++){List list;cin >> list.addr >> list.value >> list.next;lists.push_back(list);index[list.addr] = cnt++;//数组下标表示结点的地址,对应的值表示第几个存入容器中的。以空间换取时间}vector<List> linklists;for (int i = 0; i < n; i++){List list = lists[index[head]];linklists.push_back(list);if (list.next == -1){break;}head = list.next;}//到此处,linklists中存放的是有序的链表,待反转int time = (int)linklists.size() / k;//注意题意说的是每K个结点反转一次for (int i = 0; i < time; i++){reverse(linklists.begin() + i*k, linklists.begin() + (i+1)*k);}int size = (int)linklists.size();for (int i = 0; i < size; i++){if (i == size - 1) {printf("%05d %d -1\n", linklists[i].addr, linklists[i].value);}else{printf("%05d %d %05d\n", linklists[i].addr, linklists[i].value, linklists[i + 1].addr);}}return 0;}

第二版自己写的,待修改的代码,核心反转部分,最开始理解题意有误,再想想每K个结点反转一次应该怎么做

#include<vector>#include <sstream>#include<cmath>#include<iomanip>#include<iostream>#include <ctype.h>#include <stdlib.h>#include <algorithm>#include <map>#include <utility>using namespace std;//1025. 反转链表 (25)struct List{int addr;int value;int next;};void StdOutP(int addr, int value, int next);int IntBit(int n)//计算一个整数n的位数{int cnt = 0;int shang = n;while (shang != 0){shang = shang / 10;cnt++;}return cnt;}int main(){int head,n,k;cin >> head >> n >> k;int index[100005] = {-1};vector<List> lists;int cnt = 0;for (int i = 0; i < n; i++){List list;cin >> list.addr >> list.value >> list.next;lists.push_back(list);index[list.addr] = cnt++;//数组下标表示结点的地址,对应的值表示第几个存入容器中的。以空间换取时间}vector<List> linklists;for (int i = 0; i < n; i++){List list = lists[index[head]];linklists.push_back(list);if (list.next == -1){break;}head = list.next;}//到此处,linklists中存放的是有序的链表,待反转//以下部分,反转核心代码还需要再思考一下,重写if (k == 0){//原样输出for (int i = 0; i < linklists.size(); i++){int addr = linklists[i].addr;int value = linklists[i].value;int next = linklists[i].next;StdOutP(addr, value, next);}}else if (k < linklists.size()){int head2 = linklists[k].addr;int head1 = linklists[k - 1].addr;for (int i = k - 1; i>0; i--){linklists[i].next = linklists[i - 1].addr;int addr = linklists[i].addr;int value = linklists[i].value;int next = linklists[i].next;StdOutP(addr, value, next);}linklists[0].next = head2;int addr0 = linklists[0].addr;int value0 = linklists[0].value;int next0 = linklists[0].next;StdOutP(addr0, value0, next0);for (int i = k; i < linklists.size(); i++){int addr = linklists[i].addr;int value = linklists[i].value;int next = linklists[i].next;StdOutP(addr, value, next);}}else if (k>=linklists.size()){//链表全部反转int head = linklists[linklists.size() - 1].addr;for (int i = linklists.size()-1; i>0; i--){linklists[i].next = linklists[i - 1].addr;int addr = linklists[i].addr;int value = linklists[i].value;int next = linklists[i].next;StdOutP(addr, value, next);}linklists[0].next = -1;int addr0 = linklists[0].addr;int value0 = linklists[0].value;int next0 = linklists[0].next;StdOutP(addr0, value0, next0);}return 0;}void StdOutP(int addr, int value, int next)//输出标准的五位{if ((addr != -1) && (IntBit(addr) != 0)){for (int m = 5 - IntBit(addr); m>0; m--){cout << 0;}}else if (IntBit(addr) == 0){cout << "0000";}cout << addr << " " << value << " ";if ((next != -1) && (IntBit(next) != 0)){for (int m = 5 - IntBit(next); m>0; m--){cout << 0;}}else if (IntBit(next) == 0){cout << "0000";}cout << next << endl;}


0 0