list.h

#ifndef LIST_H
#define LIST_H

#include <iostream>
#include <stdio.h>
#include <malloc.h>

//定义单链表结点
typedef struct _node
{
    int data;   //数据
    struct _node *next; //指向下一结点
}node,*pNode;

//创建链表
node *create_list();

//从链表头后插入数据
int insert_listHead(pNode head,int data);

//从链表尾后插入数据
int insert_listTail(pNode head, int data);

//遍历链表,并显示每个结点的数据
int show_listData(pNode head);

//求链表中的结点个数 (不包括链表头,指真正存放数据的结点数目)
int getNodeNum(pNode head);

//根据索引查找结点,找到返回所找结点 index=0,对应头结点(不存放数据) index=1,对应第一个数据结点
pNode find_nodeByIndex(pNode head,int index);

//根据数据查找第一个符合结点(后面也可能有结点的数据为所找数据),找到返回所找结点
pNode find_nodeByData(pNode head,int data);

//指定位置插入结点数据
int insert_dataInPos(pNode head,int data,int index);

//从链表中删除第index个结点  index范围为1-nodeNum
int delete_listIndex(pNode head,int index);

//删除整个链表
int delete_listAll(node **head);

//根据索引查找结点,找到修改其值
int modify_nodeByIndex(pNode head,int index,int data);

//将链表排序 ==0,升序  ==1,降序
int sort_list(pNode head,int sortType);

#endif // LIST_H

list.c

#include "list.h"

/*************单链表测试程序************/

//创建链表
node *create_list()
{
    pNode head = (pNode)malloc(sizeof(node));
    if(!head)
    {
        printf("malloc error!\n");
//        exit(-1);   //在iostream中定义
        return NULL;
    }

    head->data = ;
    head->next = NULL;  //不用指向head,由于不是循环链表且是单链表的尾结点的next腰指向NULL

    return head;
}

//从链表头后插入结点数据
int insert_listHead(pNode head,int data)
{
    //检测链表是否存在
    if(!head)
    {
        printf("list isnot exist!\n");
        ;
    }

    pNode tmpNode = (pNode)malloc(sizeof(node));    //存放插入数据的结点
    if(!tmpNode)
    {
        printf("malloc error!\n");
        ;
    }

    //将插入数据存入要插入链表的结点
    tmpNode->data = data;
    //将tmpNode插入链表头后
    tmpNode->next = head->next;
    head->next = tmpNode;

    ;
}

//从链表尾后插入结点数据
int insert_listTail(pNode head, int data)
{
    //检测链表是否存在
    if(!head)
    {
        printf("list isnot exist!\n");
        ;
    }

    pNode tmpNode = (pNode)malloc(sizeof(node));    //存放插入数据的结点
    if(!tmpNode)
    {
        printf("malloc error!\n");
        ;
    }

    //将插入数据存入要插入链表的结点
    tmpNode->data = data;
    //将tmpNode插入链表尾后
    tmpNode->next = NULL;   //插入链表插入链表尾后,成为新的尾结点,next要指向NULL

    pNode cur = head;
    //找到链表尾结点
    while(cur->next)    //尾结点的next指向NULL,跳出时的cur即为尾结点
    {
        cur = cur->next;
    }

    cur->next = tmpNode;    //原先尾结点的next指向插入结点

    ;
}

//遍历链表,并显示每个结点的数据
int show_listData(pNode head)
{
    //检测链表是否存在
    if(!head)
    {
        printf("list isnot exist!\n");
        ;
    }

    //检测链表是否为空  (“为空”与“不存在”不同,为空说明只有一个结点,刚创建还未插入任何结点)
    if(!head->next)
    {
        printf("list isnot exist!\n");
        ;
    }

    pNode cur = head->next; //头结点数据域不保存插入数据,第二个结点才是第一个插入结点
    while(cur)
    {
        printf("%d ",cur->data);
        cur = cur->next;
    }
    printf("\n");

    ;
}

//求链表中的结点个数 (不包括链表头,指真正存放数据的结点数目)
int getNodeNum(pNode head)
{
    ;    //结点数目

    //判断链表是否存在
    if(!head)
    {
        printf("list isnot exist!\n");
        ;
    }
    //------
    //判断链表是否为空
    if(!head->next)
    {
        printf("list is NULL!\n");
        ;
    }

    pNode cur = head->next;
    while(cur)
    {
        nodeNum++;
        cur = cur->next;
    }

    return nodeNum;
}

//根据索引查找结点,找到返回所找结点 index=0,对应头结点(不存放数据) index=1,对应第一个数据结点
pNode find_nodeByIndex(pNode head,int index)
{
    //判断链表是否存在
    if(!head)
    {
        printf("list isnot exist!\n");
        return NULL;
    }
    //------
    //判断链表是否为空
    if(!head->next)
    {
        printf("list is NULL!\n");
        return NULL;
    }
    //------
    int nodeNum = getNodeNum(head);
     || index > nodeNum)   //索引必须在允许范围 (1-nodeNum)
    {
        printf("pos out of range!\n");
        return NULL;
    }

    ;
    pNode cur =  head;
    while(cur)
    {
        i++;
        cur = cur->next;
        if(i==index)
            return cur;
    }

    return NULL;    //不返回,有警告
}

//根据数据查找第一个符合结点(后面也可能有结点的数据为所找数据),找到返回所找结点
pNode find_nodeByData(pNode head,int data)
{
    //判断链表是否存在
    if(!head)
    {
        printf("list isnot exist!\n");
        return NULL;
    }
    //------
    //判断链表是否为空
    if(!head->next)
    {
        printf("list is NULL!\n");
        return NULL;
    }

    pNode cur =  head->next;
    while(cur)
    {
        if(cur->data == data)
            return cur;
        cur = cur->next;
    }

    return NULL;
}

//指定位置插入结点数据
int insert_dataInPos(pNode head,int data,int index)
{
    //判断链表是否存在
    if(!head)
    {
        printf("list isnot exist!\n");
        ;
    }
    //------
    //判断链表是否为空
    if(!head->next)
    {
        printf("list is NULL!\n");
        ;
    }
    //------
    int nodeNum = getNodeNum(head);
     || index > nodeNum)   //指定插入位置必须在允许范围
    {
        printf("pos out of range!\n");
        ;
    }

    //由于find_nodeByIndex的参数2范围限制为1-nodeNum,所以index在那里不能为1,要>=2
    )    //插入到位置1,相当于插入头结点后面
    {
        insert_listHead(head,data);
    }
    else    //index范围为2-nodeNum
    {
        pNode tmpNode = (pNode)malloc(sizeof(node));
        if(!tmpNode)
        {
            printf("malloc error!\n");
            ;
        }
        tmpNode->data = data;

        //获得插入位置的前一个结点-insertFrontNode(新数据结点插入到该结点后面)
        pNode insertFrontNode = find_nodeByIndex(head,index-);
        if(!insertFrontNode)   //未找到要被插入的结点
        {
            printf("no find insertFrontNode!\n");
            ;
        }

        //若index=2,相当于新数据结点插入到原数据结点1后面,所以需要找到原数据结点1
        tmpNode->next = insertFrontNode->next;
        insertFrontNode->next = tmpNode;
    }

    ;
}

//从链表中删除第index个结点  index范围为2-nodeNum
int delete_listIndex(pNode head,int index)
{
    //判断链表是否存在
    if(!head)
    {
        printf("list isnot exist!\n");
        ;
    }
    //------
    //判断链表是否为空
    if(!head->next)
    {
        printf("list is NULL!\n");
        ;
    }
    //------
    int nodeNum = getNodeNum(head);
     || index > nodeNum)   //index必须在允许范围
    {
        printf("pos out of range!\n");
        ;
    }

    pNode front =  find_nodeByIndex(head,index-);    //找到要删除结点的前一个结点
    if(!front)
    {
        printf("no find!\n");
        ;
    }
    //---------
    pNode cur =  find_nodeByIndex(head,index);    //找到要删除结点
    if(!cur)
    {
        printf("no find!\n");
        ;
    }

    //删除该结点
    front->next = cur->next;
    free(cur);
    cur = NULL;

    ;
}

//删除整个链表
int delete_listAll(node **head)
{
    if(*head == NULL)
    {
        printf("list isnot exist!\n");
        ;
    }

    node *cur = (*head)->next;

    while(cur)
    {
        node *tmp = cur;

        //在free(tmp);后面,那时cur==tmp已经被释放,cur = cur->next不能正常执行了
        cur = cur->next;

        free(tmp);
        tmp = NULL;
    }

    free(*head);
    (*head) = NULL;

    ;
}

//根据索引查找结点,找到修改其值
int modify_nodeByIndex(pNode head,int index,int data)
{
    pNode modifyNode =  find_nodeByIndex(head,index); //找到要修改的结点
    modifyNode->data = data;

    ;    //不返回,有警告
}

//将链表排序 ==0,升序  ==1,降序
int sort_list(pNode head,int sortType)
{
    //判断链表是否存在
    if(!head)
    {
        printf("list isnot exist!\n");
        ;
    }
    //------
    //判断链表是否为空
    if(!head->next)
    {
        printf("list is NULL!\n");
        ;
    }

    int nodeNum = getNodeNum(head);

    int i,j;
    ; i < nodeNum - ; i++) //冒泡排序法
    {
        ; j < nodeNum -  - i; j++)
        {
            //第一次获取0,1结点 第二次获取1,0结点
            node *t_first = find_nodeByIndex(head,j+);
            node *t_second = find_nodeByIndex(head,j+);

            )   //升序
            {
                if(t_first->data > t_second->data)
                {
                    //交换2个结点的值
                    int tmp = t_first->data;
                    t_first->data = t_second->data;
                    t_second->data = tmp;
                }
            }
            )  //降序
            {
                if(t_first->data < t_second->data)
                {
                    int tmp = t_first->data;
                    t_first->data = t_second->data;
                    t_second->data = tmp;
                }
            }
            else
            {
                printf("parame error!\n");
                ;
            }

        }
    }

    ;
}

main.c

#include <iostream>
#include <stdio.h>
#include <malloc.h>
#include "list.h"

using namespace std;

pNode tmpNode;
int main(void)
{
    //创建链表
    tmpNode = create_list();
    if(!tmpNode)
    {
        printf("malloc error!\n");
        ;
    }

    //插入1,3,5,7,9到链表中
    ;i<;i++)
    {
        insert_listHead(tmpNode,++i);
    }

    //插入结点数据
    insert_dataInPos(tmpNode,,);

    //获取结点数目
    printf("nodeNum=%d\n",getNodeNum(tmpNode));

    //遍历显示结点数据
    printf("showList: ");
    show_listData(tmpNode);

    //根据索引,返回第3个数据结点 index范围为1-nodeNum
    pNode t_node = find_nodeByIndex(tmpNode,);
    if(!t_node)    //有可能未找到,则返回NULL,那执行t_node->data会造成程序崩溃
        printf("no find!\n");
    else
        printf("t_data:data=%d\n",t_node->data);
    //返回数据为1的结点
    pNode t_node1 = find_nodeByData(tmpNode,);
    if(!t_node1)
        printf("no find!\n");
    else
        printf("t_data:data=%d\n",t_node1->data);

    //从链表中删除第1个结点  index范围为2-nodeNum
    delete_listIndex(tmpNode,);
    printf("showList: ");
    show_listData(tmpNode);

    //升序后显示结点数据
    sort_list(tmpNode,);
    printf("sortUp showList: ");
    show_listData(tmpNode);

    //降序后显示结点数据
    sort_list(tmpNode,);
    printf("sortUp showList: ");
    show_listData(tmpNode);

    //删除所有结点
    delete_listAll(&tmpNode);
    printf("showList: ");
    show_listData(tmpNode);

}

结果运行图:

数据结构之单链表(C实现)的更多相关文章

  1. Python数据结构之单链表

    Python数据结构之单链表 单链表有后继结点,无前继结点. 以下实现: 创建单链表 打印单链表 获取单链表的长度 判断单链表是否为空 在单链表后插入数据 获取单链表指定位置的数据 获取单链表指定元素 ...

  2. javascript数据结构之单链表

    下面是用javascript实现的单链表,但是在输出的时候insert方法中存在问题,chrome的console报错说不能读取空的属性,调试了很久都没有通过,先在这里存着,以后再来修改一下. //数 ...

  3. 数据结构之单链表的实现-java

    一.单链表基本概念 单链表是一种链式存取的数据结构,用一组地址任意的存储单元(一般是非连续存储单元)存放线性表中的数据元素.链表中的数据是以结点来表示的,每个结点的构成:元素data + 指针next ...

  4. python 数据结构之单链表的实现

    链表的定义: 链表(linked list)是由一组被称为结点的数据元素组成的数据结构,每个结点都包含结点本身的信息和指向下一个结点的地址.由于每个结点都包含了可以链接起来的地址信息,所以用一个变量就 ...

  5. 数据结构(一) 单链表的实现-JAVA

    数据结构还是很重要的,就算不是那种很牛逼的,但起码得知道基础的东西,这一系列就算是复习一下以前学过的数据结构和填补自己在这一块的知识的空缺.加油.珍惜校园中自由学习的时光.按照链表.栈.队列.排序.数 ...

  6. 数据结构 - 静态单链表的实行(C语言)

    静态单链表的实现 1 静态链表定义 静态链表存储结构的定义如下: /* 线性表的静态链表存储结构 */ #define MAXSIZE 1000 /* 假设链表的最大长度是1000 */ typede ...

  7. 数据结构 - 动态单链表的实行(C语言)

    动态单链表的实现 1 单链表存储结构代码描述 若链表没有头结点,则头指针是指向第一个结点的指针. 若链表有头结点,则头指针是指向头结点的指针. 空链表的示意图: 带有头结点的单链表: 不带头结点的单链 ...

  8. 【数据结构】单链表介绍及leetcode206题反转单链表python实现

    题目传送门:https://leetcode-cn.com/problems/reverse-linked-list/ 文章目录 单链表介绍 链表 概念 种类 优缺点 单链表(slist) leetc ...

  9. 数据结构(2):单链表学习使用java实现

    单链表是单向链表,它指向一个位置: 单链表常用使用场景:根据序号排序,然后存储起来. 代码Demo: package com.Exercise.DataStructure_Algorithm.Sing ...

  10. 数据结构:单链表结构字符串(python版)添加了三个新功能

    #!/urs/bin/env python # -*- coding:utf-8 -*- #异常类 class stringTypeError(TypeError): pass #节点类 class ...

随机推荐

  1. python用模块zlib压缩与解压字符串和文件的方法

    摘自:http://www.jb51.net/article/100218.htm Python标准模块中,有多个模块用于数据的压缩与解压缩,如zipfile,gzip, bz2等等. python中 ...

  2. hdu 4435 bfs+贪心

    /* 题意:给定每个点在平面内的坐标,要求选出一些点,在这些点建立加油站,使得总花费最少(1号点必须建立加油站).在i点建立加油站需要花费2^i. 建立加油站要求能使得汽车从1点开始走遍全图所有的点并 ...

  3. [NOIP2004] 提高组 洛谷P1090 合并果子

    题目描述 在一个果园里,多多已经将所有的果子打了下来,而且按果子的不同种类分成了不同的堆.多多决定把所有的果子合成一堆. 每一次合并,多多可以把两堆果子合并到一起,消耗的体力等于两堆果子的重量之和.可 ...

  4. Jquery判断某个字符串是否在数组中

    使用$.inArray方法判断,如果存在则返回0,不存在返回-1,结果如下: 另外也可以将数组转为字符串,并使用正则表达式处理

  5. HDU.P1100 Trees Made to Order 解题报告

    http://www.cnblogs.com/keam37/p/3637717.html  keam所有 转载请注明出处 Problem Description We can number binar ...

  6. java反射-使用反射来操纵方法

    一个类的主要成员时方法,辣么我们通过反射获取到一个类的所有方法信息后,总的寻找一种方式去操作调用这些方法,这样反射才有意义有意思. Method对象有一个方法invoke.      public O ...

  7. u盘--软驱

    https://item.taobao.com/item.htm?spm=a230r.1.14.26.XUgxcR&id=12352589458&ns=1&abbucket=5 ...

  8. openstack(2) -------RabbitMQ集群部署

    一.RabbitMQ简介 RabbitMQ属于一个流行的开源消息队列系统.属于AMQP( 高级消息队列协议 ) 标准的一个 实现.是应用层协议的一个开放标准,为面向消息的中间件设计.用于在分布式系统中 ...

  9. C - The C Answer (2nd Edition) - Exercise 1-5

    /* Modify the temperature conversion program to print the table in reverse order, that is, from 300 ...

  10. MySQL系列:innodb源代码分析之内存管理

    在innodb中实现了自己的内存池系统和内存堆分配系统,在innodb的内存管理系统中,大致分为三个部分:基础的内存块分配管理.内存伙伴分配器和内存堆分配器.innodb定义和实现内存池的主要目的是提 ...