输出单链表倒数第K个结点值

【问题描述】输入一个单向链表,输出该链表中倒数第k个结点,链表的最后一个结点是倒数第1个节点。


【输入形式】输入第一位为K值,其后接一串以空格分隔的整型值。
【输出形式】输出为倒数第K个结点的值,若无,则输出Not Found


【样例输入】3 13 45 54 32 1 4 98 2
【样例输出】4
【样例说明】K值为3,则输出链表倒数第3个结点的值,为4;数据输入间以空格隔开
【评分标准】本题要综合输出正确性及使用的数据结构。需由输入数据构建单链表。不使用链表的将不得分。

 方法:

需要注意的是 在输入的时候以回车为判断输入是否结束,使用getchar()!='\n'来判断。

1、单链表   

        第一遍遍历得到链表长度 再次循环找到 Length-k+1的位置  即为所求

2、单链表   

        以头插法方式进行数据载入,然后从头往后找第k个元素 就是要找的元素;(需要注意定义的单链表是否有头结点。)

3、循环双链表 

        向后找

4、快慢指针  

1)定义一个q变量指向链表的第一个结点,是q变量往后移动k个结点。
2)定义一个p变量指向链表的第一个结点。
3)p变量和q变量同时循环往后移动一个结点,直到q为null。

       示例:

方法2,4如下

/*
1.单链表  
*/

#include <stdio.h>
#include <stdlib.h>
#define _CRT_SECURE_NO_WARNINGS 1

//方法一:单链表
/*
typedef struct LNode
{
	int data;
	struct LNode* next;		//指向后继结点
} LinkNode;	//声明单链表结点类型

void HeadInsertLisk(LinkNode*& L, int number)
//头插法建立单链表
{
	LinkNode* s;
	s = (LinkNode*)malloc(sizeof(LinkNode));//创建新结点s
	s->data = number;
	s->next = L->next;			//将结点s插在原开始结点之前,头结点之后
	L->next = s;
	L->data++;
}

void InitList1(LinkNode*& L)
{
	L = (LinkNode*)malloc(sizeof(LinkNode));  	//创建头结点
	L->next = NULL;
	L->data = 0;
}

void GetElem1(LinkNode* L, int Location)
{
	int Length = L->data;
	LinkNode* p = L;
	if (Location < 0||Location>Length)
		printf("Not Found");
	else
	{
		int i = 0;
		//printf("%d\t%d\n", Length,Location);
		for (i = 0; i < Location; i++)
		{
			p = p->next;
		}
		printf("%d\n", (p->data));
	}
}
void Dispaly(LinkNode*& L)
{
	while (L->next != NULL)
	{
		printf("%d  ", L->data);
		L = L->next;
	}
}

int main()
{
	int Location = 0;
	scanf("%d", &Location);

	LinkNode* L;
	int num = 0;
	//char s;
	InitList1(L);
	/*
	while (1)
	{
		scanf_s("%c", &s);
		if (s != '\n')
		{
			if (s == ' ')
				continue;
			else
			{
				num = ((int)(s - 48));
				HeadInsertLisk(L, num);
			}
		}
		else
			break;
	}
	//删去112行时候,需要将112行移到此行
	do {
		scanf("%d", &num);
		HeadInsertLisk(L, num);
	} while ( (getchar() != '\n'));
	//(scanf_s("%d", &num) == 1) &&
	GetElem1(L, Location);

	//Dispaly(L);
	return 0;
}

*/

//方法二:双指针:快慢指针

 
typedef struct ListNode {
	int data;
    struct ListNode *next;
 }ListNode;

int FS_Pointer(ListNode* head, int k) 
{
	ListNode* faster = head;//前 快
	ListNode* slower = head;

	for (int i = 0; i < k; i++)
	{
		faster = faster->next;
	}

	while (faster != NULL)
	{
		faster = faster->next;
		slower = slower->next;
	}

	return slower->data;
}

void InitList(ListNode*& L)
{
	L = (ListNode*)malloc(sizeof(ListNode));
	L->next = NULL;
}

void TailInsertList(ListNode*& L, int number)//尾插法
{
	ListNode* NewNode;
	NewNode = (ListNode*)malloc(sizeof(ListNode));

	NewNode->data = number;
	L->next = NewNode;
	L = NewNode;
}

int main()
{
	int Length = scanf_s("%d", &Length);

	ListNode *L;
	InitList(L);
	int number = 0;
	do
	{
		TailInsertList(L, scanf_s("%d", &number));
	} while (getchar() != '\n');

	printf("%d",FS_Pointer(L, Length));

	return 0;
}
  • 13
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值