题目描述
- 说取倒数第k个,最简单的想法就是用头插法变成正数第k个
#include <stdio.h>
#include <stdlib.h>
typedef struct Node
{
int data;
struct Node *next;
}Lnode,*LinkList;
int main()
{
int n=0;
int k;
scanf("%d",&k);
LinkList L=NULL;
Lnode *s;
int x;
scanf("%d",&x);
while(x!=-1)
{
n++;
s=(Lnode *)malloc(sizeof(Lnode));
s->data=x;
s->next=L;
L=s;
scanf("%d",&x);
}
if(k>n) printf("NULL");
for(int i=1;i<k;i++) L=L->next;
printf("%d",L->data);
return 0;
}
但是有一个点一直超时。。。
2. 最近看那些个快慢指针,找倒数第k个就是找到结尾的固定距离的结点,用快慢指针试一下
先用一个指针来输入,同时计数。当输入到第k个结点时,慢指针同步移动,这样保持固定距离,快指针到结尾时慢指针所指的结点就是要找的结点
一开始想一边录入数据一边计数确定慢指针,但是这样存在问题就是非法输入可能不好确定(毕竟当下不知道链表长度)
#include<iostream>
using namespace std;
typedef struct Node* LinkList;
struct Node{
int data;
struct Node *next;
Node():data(0),next(nullptr){};
Node(int x):data(x),next(nullptr){};
};
int main()
{
ios::sync_with_stdio(false);
cin.tie(0),cout.tie(0);
int k,x,i=0;
cin >> k;
cin >> x;
LinkList ptr=new Node();
LinkList s=ptr;
while(x>=0)
{
i++;
if(i>=k) s=s->next;
Node *p=new Node(x);
ptr->next=p;
ptr=ptr->next;
cin >> x;
}
if(k<=0||i<k) cout << "NULL";
else cout << s->data;
return 0;
}
还有一个段错误没解决,估计是哪边界没卡好
--------------------------这是一条分割线-------------------------
上面是条分割线(用黄色看不清……主要是因为没啥内容哈哈😄)
毕竟要月考了,所以拿出来又看了一遍一交不对呀咋没通过……才想起来还有个bug没改……
上面的问题就在于,在快指针处插入数据前先移动了慢指针
这就导致极端数据情况下,原链表还没有数据就已经开始移动慢指针了……
所以慢指针调个位置即可
(抑郁一开始居然没看出来……)
#include<bits/stdc++.h>
using namespace std;
typedef struct Node* LinkList;
struct Node{
int data;
struct Node *next;
Node():data(0),next(nullptr){};
Node(int x):data(x),next(nullptr){};
};
int main()
{
ios::sync_with_stdio(false);
cin.tie(0),cout.tie(0);
LinkList head=new Node();
LinkList ptr=head;
LinkList s=head;
int k,x,i=0;
cin >> k >> x;
while(x>=0)
{
i++;
Node *p=new Node(x);
ptr->next=p;
ptr=ptr->next;
cin >> x;
if(i>=k) s=s->next; //像这种二层移动的东西还是放在最后比较好……
}
if(k<=0 || i<k) cout << "NULL";
else cout << s->data;
}
所以以后要注意慢指针的移动一定不要着急😢……放最后保险点……