数据结构与算法
Posted 子羽丿
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了数据结构与算法相关的知识,希望对你有一定的参考价值。
数据结构与算法
统一声明:
博客转载 声 明 : 本博客部分内容来源于网络、书籍、及各类手册。
内容宗旨为方便查询、总结备份、开源分享。
部分转载内容均有注明出处,如有侵权请联系博客告知并删除,谢谢!
百度云盘提取码:统一提取码:ziyu
一、基本概念
1.1、数据结构起源
由于最初涉及的运算对象是简单的整型、实型或布尔型数据,所以程序设计者的主要精力集中于程序设计的技巧上,而无需重视数据结构。随着计算机应用领域的扩大和软硬件的发展,非数值计算问题显得越来越重要。
据统计,当今处理非数值计算问题占用了90%以上的机器时间。
这类问题涉及的数据结构更为复杂,数据元素之间的相互关系一般无法用数学方程式加以描述。因此,解决这类问题的关键不再是数学分析和计算方法,而是要设计出合适的数据结构。
所以,数据结构是一门研究非数值计算的程序设计问题中的操作对象,以及它们之间的关系和操作等相关问题的学科。
1968年,美国DonaldEKnuth教授在其所写的《计算机程序艺术》第一卷《基本算法》中,较系统地阐述了数据的逻辑结构和存储结构以及操作,开创了“数据结构”的课程体系。同年,数据结构作为一门独立课程,在计算机科学学位课程中开始出现。
数据结构是介于数学、计算机硬件、计算机软件、逻辑学等学科之间的综合学科,是计算机学科的一门核心课程,是设计实现编译系统、操作系统、数据库等其他课程和大型应用程序的基础。
进入70年代,出现了大型计算机程序,软件开始相对独立,结构程序设计成为程序设计方法学的主要内容。
程序设计的实质是对实际问题设计/选择好的数据结构和好的算法,
而好的算法在很大程度上取决于描述实际问题的数据结构。
著名的瑞士计算机科学家沃思(N.Wirth)教授曾提出:
程序设计 = 数据结构 + 算法
1.2、数据结构
1.3、数据结构基本概念
正所谓“巧妇难为无米之炊”,数据结构是针对数据进行研究的学科,那么这里的“米”就是数据。
数据不仅仅包含整型、字符型、浮点型等数值类型,还包括字符、图像、声音、视频等非数值类型。
数据元素:例如,若我们要对家畜类进行调查,则牛、羊、马、狗、猪等都是家畜类的数据元素。
数据项: 例如,人这样的数据元素,可以有眼、耳、鼻、口、手等数据项,也可以有姓名、年龄、性别、出生日期、出生地址、联系电话等数据项。具体使用哪些数据项,要视你做的程序决定。
- 数据:描述客观事实的符号,能被计算机所识别、操作,并输入到计算机中的一些符号的集合,信息的载体
- 数据项:一个数据元素可由若干数据项组成,构成数据元素的最小单位
- 数据元素:数据基本单位,通常作为一个整体考虑和处理
- 数据结构:相互之间存在一种或多种特定关系的数据元素的结合
1.4、数据结构三要素
1.4.1. 逻辑结构: 线性、树形、图状
1.4.2. 存储结构:顺序存储、链式存储
1.4.3. 数据的运算:增删改查
1.5、数据结构三个方面
二、线性表(逻辑结构)
2.1、线性表的概念
线性表的顺序存储结构,指的是用一段地址连续的存储单元依次存储线性表的数据元素。
线性结构:一对一
假设有n个数据元素,满足线性结构;
特点:1.n = 0, 该表为空
2.a0为表头,没有直接前驱, a(n-1),表尾,没有直接后继
3.其他有且仅有一个直接前驱和一个直接后继
顺序存储结构存放线性表:顺序表
链式存储结构存放线性表:链表
2.2、顺序表
2.2.1、顺序表运算:
顺序表初始化:
typedef struct list{
int data[size];
int last;
}seqlist;
2.2.2、静态分配:
如果“数组”放满怎么办?
如果刚开始就声明一个内存空间呢?
2.2.3、动态分配:
int *p = (int *)malloc(3 * sizeof(int));
2.2.4、顺序表的基本运算:
初始化
判空
判满
求表长
插入
删除
查找
修改
清空
销毁
输出
2.2.5、顺序表的实现
(1)seqlist_malooc.c
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <strings.h>
#define SIZE 100
typedef int data_t; //重命名int 类型
//顺序表
typedef struct list{
data_t data[SIZE]; //数组,用来存放数据元素
int last; //最后一个元素下标
}seqlist; //重命名,struct list == seqlist,结构体的数据类型
//初始化
seqlist *creatSeqlist()
{
//动态分配
seqlist *seq = (seqlist *)malloc(sizeof(seqlist));//结构体指针
if(seq == NULL)
{
printf("malloc failed!\\n");
return NULL;
}
memset(seq->data, 0, sizeof(seq->data));//把结构体的成员data数组清零
seq->last = -1; //如果下标为-1,说明顺序表中没有元素存在
return seq;
}
//判空
int seqlist_is_empty(seqlist *seq)
{
if(seq == NULL)
return -1;
return ((seq->last == -1)?1:0);
}
//判满
int seqlist_is_full(seqlist *seq)
{
if(seq == NULL)
return -1;
return ((seq->last+1 == SIZE)?1:0);
}
//求表长
int seqlist_length(seqlist *seq)
{
if(seq == NULL)
return -1;
return (seq->last+1);
}
//插入:按位置插入数据元素
int inserSeqlistByPos(seqlist *seq, int pos, data_t data)
{
if(NULL == seq) //malloc是否成功
return -1;
if(seqlist_is_full(seq) == 1) //判满
return -1;
int len = seqlist_length(seq); //插入的位置
if(pos < 0 || pos > len)
return -1;
int i = 0;
for(i= seq->last; i>=pos; i--)
{
seq->data[i+1] = seq->data[i];
}
seq->data[pos] = data;
seq->last++;
}
//删除:按位置删除数据元素
int deleteSeqlistByPos(seqlist *seq, int pos)
{
if(NULL == seq)
return -1;
if(seqlist_is_empty(seq) == 1) //判空
return -1;
int len = seqlist_length(seq);
if(pos < 0 || pos > seq->last)
return -1;
int i = 0;
for(i=pos; i<seq->last; i++)
{
seq->data[i] = seq->data[i+1];
}
seq->last--;
}
//查找:按位置来查找数据元素
data_t findSeqlistByPos(seqlist * seq, int pos)
{
if(NULL == seq)
return -1;
if(seqlist_is_empty(seq) == 1)
return -1;
int len = seqlist_length(seq);
if(pos < 0 || pos > seq->last)
return -1;
return seq->data[pos];
}
//修改:按位置来修改数据元素
int changSeqlisByPos(seqlist *seq, int pos, data_t data)
{
if(NULL == seq)
return -1;
if(seqlist_is_empty(seq) == 1)
return -1;
int len = seqlist_length(seq);
if(pos < 0 || pos > seq->last)
return -1;
seq->data[pos] = data; //按位置来修改数据元素
}
//查找:按值来查找数据元素,返回那个值的下标
int findSeqlistByData(seqlist *seq, data_t data)
{
if(NULL == seq)
return -1;
if(seqlist_is_empty(seq) == 1)
return -1;
int i = 0;
for(i=0; i<=seq->last; i++)
{
if(seq->data[i] == data)
{
return i;
}
}
}
//删除:按值来删除数据元素
int deleteSeqlistByData(seqlist *seq, data_t data)
{
int pos = findSeqlistByData(seq, data);
deleteSeqlistByPos(seq, pos);
}
//修改:按值来修改数据元素
int changeSeqlistByData(seqlist *seq, data_t old_data, data_t new_data)
{
int pos = findSeqlistByData(seq, old_data);
changSeqlisByPos(seq, pos, new_data);
}
//清空
void clearSeqlist(seqlist *seq)
{
if(NULL == seq)
return;
seq->last = -1;
}
//销毁:把地址的地址回收掉
void destroySeqlist(seqlist **seq)
{
free(*seq);
*seq = NULL;
}
//输出
void displaySeqlist(seqlist *seq)
{
if(NULL == seq)
return;
if(seqlist_is_empty(seq) == 1)
return ;
int i = 0;
for(i=0; i<=seq->last; i++)
{
printf("%d ", seq->data[i]);
}
puts(" ");
}
int main(int argc, const char *argv[])
{
seqlist *seq = creatSeqlist();
if(seq == NULL)
{
printf("malloc failed!\\n");
return -1;
}
int n = seqlist_is_empty(seq);
printf("line:%d, n:%d\\n",__LINE__, n); //:line:221, n:1
int m = seqlist_is_full(seq);
printf("line:%d, m:%d\\n",__LINE__, m); //:line:224, n:0
int len = seqlist_length(seq);
printf("line:%d, n:%d\\n",__LINE__, len); //:line:227, n:0
//按位置插入数据元素
int i = 0;
while(i<10)
{
inserSeqlistByPos(seq, i, i+1);
i++;
}
len = seqlist_length(seq);
printf("line:%d, n:%d\\n",__LINE__, len); //: 10
//打印输出
displaySeqlist(seq); //:1 2 3 4 5 6 7 8 9 10
//按位置删除
deleteSeqlistByPos(seq, 2);
//打印输出
displaySeqlist(seq); //:1 2 4 5 6 7 8 9 10
//按位置来查找数据元素
data_t data = findSeqlistByPos(seq, 5);
printf("data = %d\\n", data); //:data = 7
//按位置来修改数据元素
changSeqlisByPos(seq, 1, 250);
//打印yy输出
displaySeqlist(seq); //:1 250 4 5 6 7 8 9 10
//查找:按值来查找数据元素,返回那个值的下标
int pos = findSeqlistByData(seq, 250);
printf("line:%d, pos = %d\\n", __LINE__, pos); //:line:257, pos = 1
//删除:按值来删除数据元素
deleteSeqlistByData(seq, 7);
displaySeqlist(seq); //:1 250 4 5 6 8 9 10
//修改:按值来修改数据元素
changeSeqlistByData(seq, 10, 100);
displaySeqlist(seq); //:1 250 4 5 6 8 9 100
//清空
clearSeqlist(seq);
displaySeqlist(seq); //:
len = seqlist_length(seq);
printf("line:%d, n:%d\\n",__LINE__, len); //:line:271, n:0
//销毁
destroySeqlist(&seq);
printf("seq = %p\\n", seq); //:seq = (nil)
return 0;
}
(2)seqlist_static.c
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <strings.h>
#define SIZE 100
typedef int data_t; //重命名int 类型
//顺序表
typedef struct list{
data_t data[SIZE]; //数组,用来存放数据元素
int last; //最后一个元素下标
}seqlist; //重命名,struct list == seqlist,结构体的数据类型
//判空
int seqlist_is_empty(seqlist *seq)
{
if(seq == NULL)
return -1;
return ((seq->last == -1)?1:0);
}
//判满
int seqlist_is_full(seqlist *seq)
{
if(seq == NULL)
return -1;
return ((seq->last+1 == SIZE)?1:0);
}
//求表长
int seqlist_length(seqlist *seq)
{
if(seq == NULL)
return -1;
return (seq->last+1);
}
//插入:按位置插入数据元素
int inserSeqlistByPos(seqlist *seq, int pos, data_t data)
{
if(NULL == seq) //malloc是否成功
return -1;
if(seqlist_is_full(seq) == 1) //判满
return -1;
int len = seqlist_length(seq); //插入的位置
if(pos < 0 || pos > len)
return -1;
int i = 0;
for(i= seq->last; i>=pos; i--)
{
seq->data[i+1] = seq->data[i];
}
seq->data[pos] = data;
seq->last++;
}
//插入:按位置插入数据元素
int deleteSeqlistByPos(seqlist *seq, int pos)
{
if(NULL == seq)
return -1;
if(seqlist_is_empty(seq) == 1) //判空
return -1;
int len = seqlist_length(seq);
if(pos < 0 || pos > seq->last)
return -1;
int i = 0;
for(i=pos; i<seq->last; i++)
{
seq->data[i] = seq->data[i+1];
}
seq->last--;
}
//查找:按位置来查找数据元素
data_t findSeqlistByPos(seqlist * seq, int pos)
{
if(NULL == seq)
return -1;
if(seqlist_is_empty(seq) == 1)
return -1;
int len = seqlist_length(seq);
if(pos < 0 || pos 以上是关于数据结构与算法的主要内容,如果未能解决你的问题,请参考以下文章