C++面试笔记--单链表
1、编程实现单链表删除节点。
解析:如果删除的是头节点,如下图:

则把head指针指向头节点的下一个节点。同时free p1,如下图所示:

如果删除的是中间节点,如下图所示:

则用p2的next指向p1的next同时,free p1 ,如下图所示:

2、编写程序实现单链表的插入。
解析:单链表的插入,如下图所示:

如果插入在头结点以前,则p0的next指向p1,头节点指向p0,如下图所示:

如果插入中间节点,如下图所示:

则先让p2的next指向p0,再让p0指向p1,如下图所示:

如果插入尾节点,如下图所示:

则先让p1的next指向p0,再让p0指向空,如下图所示:

3、编写实现单链表的逆置。
解析:单链表模型如下图所示:
进行单链表逆置,首先要让p2的next指向p1,如下图所示:

再由p1指向p2,p2指向p3,如下图所示:

让后重复p2的next指向p1,p1指向p2,p2指向p3。

#include<iostream>
using namespace std;
typedef struct Student{
int data;
struct student *next;//结构体重如果没有用typedef定义结构体,那么想要声明一个结构体的变量,就需要加上struct }node; node *creat(){
/*① 建立头结点
② 循环输入节点值,0停止输入,其他则继续输入
③ 插入一个值,新建一个节点存储该值,赋值操作,指针修改操作
上一个节点的next指向新建立的节点,临时指针指向当前节点方便递增操作
④ 返回一个头结点,该节点不为空
*/
node *head,*p,*s;//头结点,p临时头节点,s为新建立的节点
int x,cycye=;//输入停止变量
head=(node*)malloc(sizeof(node));//建立头结点
p=head;
while(cycle){
cout<<"请输入链表数据:"<<endl;
cin>>x;
if(x!=){//当输入不为0,继续输入
s=(node*)malloc(sizeof(node));//S为新建立的节点
s->data=x;
cout<<s->data<<endl;
p->next=s;
p=s;//临时指针递增
}
else{
cycle=;//停止输入
}
p->next=NULL;//指针指向链表尾端
cout<<" yyy"<<head->next->data<<endl;
head=head->next;
return (head);
}
}
//打印链表
void print(node *head){
/* ① 该链表为空,不输出。
② 该链表不为空且不止一个节点:头结点没有值,则从头结点的下一个节点开始输出
*/
node *tem_node;//临时节点
tem_node=head;
//这里还要输出链表长度
int length=length(head);
cout<<"该链表长度为:"<<length<<endl; if(head!=NULL){
tem_node=tem_node->next;//因为该头结点没有值,所以要指向下一个
}
while(tem_node!=NULL){
cout<<"节点值:"<<tem_node->data<<endl;
tem_node=tem_node->next;
}
}
//删除节点
node *remove(node *head,int num){
/*① 删除头结点:把头结点的指针指向下一个节点,再把头结点移除
② 删除中间节点:前驱节点的next指向删除节点的next
*/
node *p1,*p2;
p1=head;
//找到删除位置
while(num!=p1->data &&p1->next!=NULL){//删除的值不为头结点值,并且头结点不为空
p2=p1;//删除节点的上一个节点
p1=p1->next;//找到删除节点
}
if(num==p1->data){//如果存在p1节点,删除
if(p1==head){//删除头结点
head=p1->next;
free(p1);
}
else{
p2->next=p1->next;
}
}
else{
cout<<"不存在值为"<<num<<"的节点!"<<endl;
}
return (head);
}
node *insert(node *head,int num){
/*① 从头部插入:头指针指向插入节点,新插入节点next指向原头结点
② 从中间插入:插入位置的前一个节点next指向新插入节点,新插入节点nex指向后一个节点
③ 从尾部插入:和2类似,只是最后是新插入节点next指向NULL
*/
node *p1,*p2,*p3;
p2=head;
p1=(node*)malloc(sizeof(node));//新增节点
p1->data=num;
while(p1->data > p2->data && p2->next!=NULL){//找插入点
p3=p2;
p2=p2->next;
//p2是后一个,P3是前一个
}
//判断这个插入的位置
if(p1->data<=p2->data){
if(head==p2){//从头结点插入
p1->next=p2;
head=p1;
}
else {//从中间节点插入
p3->next=p1;
p1->next=p2;
}
}
else{//没有比他大的数,从尾部插入
p2->next=p1;
p1->next=NULL;
}
return (head);
}
//链表排序
node *sort(node *head){
/*冒泡排序法解决*/
node *p,*p2,*p3;
int n;
int temp;
n=length(head);
if(head==NULL ||head->next==NULL)//如果只有一个或者没有节点
return head;
p=head;
for(int j=;j<n;++j) {
p=head;
for(int i=;i<n-j;++i) {
if(p->data > p->next->data){
temp=p->data;
p->data=p->next->data;
p->next->data=temp;
}
p=p->next;
}
}
return (head); }
//链表的转置
node *reverse(node *head){
/**/
node *p1,*p2,*p3;
if(head==NULL || head->next==NULL){
return head;
}
p1=head;
p2=p1->next;
while(p2){
p3=p2->next;
p2->next=p1;
p1=p2;
p2=p3;
}
head->nex=NULL;
head=p1;
return head;
}
//链表测长
int length(node *head){
node *tem_node;
tem_node=head;
int n=;
while(tem_node!=NULL){
n++;
tem_node=tem_node->next;
}
return n;
} int main(){ }
4、编程实现删除单链表的头元素。
答案:
#include<iostream>
using namespace std; void Removehead(node *head){
node * p=head;
head=head->next;
free(p);
}
5、给出一个单链表,不知道节点N的值,怎么只遍历一次就可以求出中间节点,写出算法。
解析:设立两个指针,比如*p和*q。p每次移动两个位置,即p=p->next->next,q每次移动一个位置,即q=q->next。当p达到最后一个节点时,q就是中间节点了。
答案:
#include<iostream>
using namespace std;
//给出一个单链表,不知道节点N的值,怎么遍历一次就可以求出中间节点
void searchMid(node *head,node *mid){
node *p,*q;
p=head;
q=head;
while(p->next->next!=NULL){
p=p->next->next;//p移动两个位置
q=q->next;//q移动一个位置,这样相当于p走了两倍,q走了一倍就到达了中点
mid=q;
}
}
6、给定一个单向链表,设计一个时间优化并且空间优化的算法,找出该链表的倒数第m个元素。实现您的算法,注意处理相关的出错情况。m定义为当m=0时,返回链表最后一个元素。
解析:这是一个难题,我们需要的是倒数第m个元素,所以如果我们从某个元素开始,遍历了m个元素之后刚好到达链表末尾,那么这个元素就是要找的元素。也许从链表的尾部倒推回去不是最好的办法,那么我们可以从链表头开始计数。
思路一:我们可以先一次遍历求出链表的总长度n,然后顺序变量求出第n-m个元素,那么这个就是我们要找的元素了。
思路二:我们用两个指针,一个当前位置指针p和一个指向第m个元素的指针q,需要确保两个指针之间相差m个元素,然后以同样的速度移动它们,如果当q到达链表末尾时,那么p指针就是指向倒数第m个元素了。
答案:
#include<iostream>
using namespace std;
//思路二
node* search_last_m_num(node *head,int m){
if(head==NULL)
return NULL;
node *p1,*p2;
p1=head;
p2=head;
while(m){//这样p1和p2相差M个单位长度,当p2走到尽头的时候,p1指向的元素就是倒数第m个元素
if(p2->next!=NULL){
p2=p2->next;
m--;
}
else
return NULL;
}
while(p2->next!=NULL){
p1=p1->next;
p2=p2->next;
}
return p1;
}
C++面试笔记--单链表的更多相关文章
- c++学习笔记—单链表基本操作的实现
用c++语言实现的单链表基本操作,包括单链表的创建(包括头插法和尾插法建表).结点的查找.删除.排序.打印输出.逆置.链表销毁等基本操作. IDE:vs2013 具体实现代码如下: #include ...
- python经典面试算法题1.3:如何计算两个单链表所代表的数之和
本题目摘自<Python程序员面试算法宝典>,我会每天做一道这本书上的题目,并分享出来,统一放在我博客内,收集在一个分类中. 1.2 如何实现链表的逆序 [华为笔试题] 难度系数:⭐⭐⭐ ...
- LeetCode 笔记系列六 Reverse Nodes in k-Group [学习如何逆转一个单链表]
题目:Given a linked list, reverse the nodes of a linked list k at a time and return its modified list. ...
- 面试之路(10)-BAT面试之java实现单链表的插入和删除
链表的结构: 链表在空间是不连续的,包括: 数据域(用于存储数据) 指针域(用于存储下一个node的指针) 单项链表的代码实现: 节点类 构造函数 数据域的get,set方法 指针域的get,set方 ...
- 数据结构(java版)学习笔记(三)——线性表之单链表
单链表的优点: 长度不固定,可以任意增删. 单链表的缺点: 存储密度小,因为每个数据元素,都需要额外存储一个指向下一元素的指针(双链表则需要两个指针). 要访问特定元素,只能从链表头开始,遍历到该元素 ...
- 《程序员代码面试指南》第二章 链表问题 将单链表每K个节点之间逆序
样例 链表1-2-3-4-5-6-7-8-9-10 K=3 ,结果 3-2-1-6-5-4-9-8-7-10 java代码 /** * @Description:将单链表每K个节点之间逆序 * @Au ...
- 《程序员代码面试指南》第二章 链表问题 在单链表和双链表中删除倒数第K个节点
题目 在单链表和双链表中删除倒数第K个节点 java代码 /** * @Description:在单链表和双链表中删除倒数第K个节点 * @Author: lizhouwei * @CreateDat ...
- 左神算法书籍《程序员代码面试指南》——2_11将单链表的每K个节点之间逆序
[题目]给定一个单链表的头节点head,实现一个调整单链表的函数,使得每K个节点之间逆序,如果最后不够K个节点一组,则不调整最后几个节点.例如:链表:1->2->3->4->5 ...
- 左神算法书籍《程序员代码面试指南》——2_02在单链表和双链表中删除倒数第k个字节
[题目]分别实现两个函数,一个可以删除单链表中倒数第K个节点,另一个可以删除双链表中倒数第K个节点.[要求]如果链表长度为N,时间复杂度达到O(N),额外空间复杂度达到O(1).[题解]从头遍历链表, ...
随机推荐
- leetcode_sql_1,176,177
1.176题目,Second Highest Salary,https://leetcode.com/problems/second-highest-salary/#/description Writ ...
- 【LeetCode】075. Sort Colors
Given an array with n objects colored red, white or blue, sort them so that objects of the same colo ...
- C++语言对C的增强(1)——实用性、变量检测、struct类型、C++中所有变量和函数都必须有类型、bool类型、三目运算符
1.“实用性”增强 C语言中的变量都必须在作用域开始的位置定义,C++中更强调语言的“实用性”,所有的变量都可以在需要使用时再定义. 2.变量检测加强 在C语言中,重复定义多个同名的全局变量是合法的: ...
- Python函数 __import__()
功能: __import__() 函数用于动态加载类和函数 .返回元组列表. 如果一个模块经常变化就可以使用 __import__() 来动态载入. __import__ 语法: __import__ ...
- hihoCoder#1139(二分+bfs)
时间限制:10000ms 单点时限:1000ms 内存限制:256MB 描述 在上一回和上上回里我们知道Nettle在玩<艦これ>,Nettle在整理好舰队之后终于准备出海捞船和敌军交战了 ...
- Python内置函数:strip()
文章转载于:http://www.cnblogs.com/itdyb/p/5046472.html(博主:波比12) 在python API中这样解释strip()函数:
- JeeSite入门介绍(一)
JeeSite特点:高效.高性能.强安全性属于开源.JavaEE快速开发平台:接私活的最佳助手: JeeSite是在Spring Framework基础上搭建的一个Java基础开发平台,以Spring ...
- Flash 零日漏洞复现(CVE-2018-4878)
项目地址:https://github.com/Sch01ar/CVE-2018-4878.git 影响版本为:Adobe Flash Player <= 28.0.0.137 攻击机器IP:1 ...
- sql语句优化方案
1. 为查询缓存优化你的查询 NOW() 和 RAND() 或是其它的诸如此类的SQL函数都不会开启查询缓存,因为这些函数的返回是会不定的易变的. 所以,你所需要的就是用一个变量来代替MySQL的函数 ...
- myeclipse实用快捷键
笔者这里总结的是个人在使用myeclipse时常用的快捷操作,总结如下: 1.Ctrl + / :为选中的一段代码加上或去掉注释符 Ctrl + Shift + / :( ...