学习视频

  • 一、串的定义和基本运算
    • 1、串的定义
    • 2、串的基本操作
  • 二、串的存储结构
    • 1、定长顺序串存储
    • 2、链式存储
    • 3、串的堆分配存储结构
  • 串的基本运算的实现

串是字符串的简称,它的每个数据元素都由一个字符组成。串是一种特殊的线性表。

一、串的定义和基本运算

字符串简称为串,是一种特殊的线性表,它的数据元素仅由字符组成。

1、串的定义

(1)串的定义
串(string)是由零个或任意多个字符组成的有限序列,一般记为:

S="a1a2a3....an"(n>=0)

其中,S为串名,在本书中用双引号作为串的定界符,引号括起来的字符序列为串值,ai(1<=i<=n)可以是字母、数字或其他字符,n为串的长度。
(2)串的相关术语

  • 空串。不含任何字符的串称为空串,即串的长度n=0时的串为空串。
  • 空格串。由一个或多个称为空格的特殊字符组成的串称为空格串,它的长度是串中空格字符的个数。
  • 子串。串中任意个连续的字符组成的子序列称为该串的子串。另外,空串是任意串的子串,任意是自身的子串。
  • 主串。包含子串的串称为该子串的主串。
  • 模式匹配。子串的定位运算又称为串的模式匹配,是一种求子串的主串中第几位出现的第一个字符的位置。
  • 两个串相等。两个串的长度相等且各个位置上对应的字符也都相同。

2、串的基本操作

(1)串的赋值StrAsign(S,chars)
初始条件:chars是字符串常量
操作结果:生成一个值等于chars的串S.
(2)串的复制StrCopy(S,T)
初始条件:串S存在。
操作结果:由串T复制得串S。
(3)求串的长度StrLength(S)
初始条件:串S存在
操作结果:返回串S的长度,即串中的元素个数。
(4)串的连接StrCat(S,T)
初始条件:串S和T存在。
操作结果:将串T的值连接在串S的后面
(5)求子串SubString(Sub,S,pos,len)
初始条件:串S存在,1<=pos<=StrLength(S)且1<=len<=StrLength(S)-pos+1
操作结果:用Sub返回串S的第pos个字符起长度为len的子串。
(6)串的定位(模式匹配)StrIndex(S,pos,T)
初始条件:S串与T串存在,T非空
操作结果:若串S中存在与T串相同的子串,则返回它在串S中第一次出现的位置;否则返回-1
(7)串的插入StrInsert(S,pos,T)
初始条件:串S和T存在,1<=pos<=StrLength(S)+1
操作结果:在串S的第pos个字符插入串T。
(8)串的删除StrDelete(S,pos,len)
初始条件:串S存在,1<=pos<=StrLength(S)且1<=len<=StrLength(S)-pos+1
操作结果:从串S中删除第pos个字符起长度为len的子串
(9)串的替换StrReplace(S,T,V)
初始条件:串S,T和V存在,且T是非空串
操作结果:用V替换串S中出现的所有与T相等的不重叠子串。
(10)判断串空StrEmpty(S)
初始条件:串S存在
操作结果:若串S为空串,返回0
(11)串的比较StrCompare(S,T)
初始条件:串S和T串存在
操作结果:若S>T,则返回值>0;若S=T,则返回值等于0;若S<T,则返回值<0
(12)串的清空StrClear(S)
初始条件:串S存在
操作结果:将S串清空
(13)输出串DispStr(S)
初始条件:串S存在
操作结果:显示串S的所有字符。

二、串的存储结构

1、定长顺序串存储

(1)顺序存储的类型定义
顺序串的类型定义与顺序表的定义相似,可以用一个字符数组和一个整型变量表示其中字符数组存储串,整型变量表示串的长度。
(2)存储方式

  • 非紧凑存储。设S=“Hello boy”,计算机字长为32位(4个Byte),用非紧凑格式一个地址只能存一个字符。其优点是运算处理简单,但缺点存储空间浪费。
  • 紧凑存储,用紧凑格式一个地址能存4个字符。紧凑存储的优点是空间利用率高,缺点是对串中字符处理的效率低。

2、链式存储

(1)链接存储的描述
用链表存储字符串,每个结点有两个域:一个数据域(Data)和一个指针域(next),在串的链式存储结构中,如下:
数据域(Data)——存放串中的字符。
指针域(next)——存放后继节点的地址

  • 链接存储的优点——插入、删除运算方便
  • 链接存储的缺点——存储、检索效率低
    (2)串的存储密度
    存储密度=串值所占的存储位/实际分配的存储位
    串链接存储的存储密度小,存储量比较浪费,但运算处理,特别是对串的连接等操作的实现比较方便。

3、串的堆分配存储结构

(1)堆分配存储的方法

  • 开辟一块地址连续的存储空间,用于存储各串的值,该存储空间称为“堆”(即自由存储区)
  • 另外建立一个索引表,用来存储串的名字、长度和该串在“堆”中存储的起始地址
  • 程序执行过程中,每产生一个串,系统就从“堆”中分配一块大小与串的长度相同的连续空间,用于存储该串的值,并且在索引表中增加一个索引项,用于登记该串的信息。
    (2)带长度的索引表的C语言描述
typedef struct{char name[MAXLEN];int length;char *start;
}LNode;

(3)“堆”的管理
C中利用动态分配函数,malloc和free来管理“堆”。利用malloc为每一个新串分配一块实际串长所需要的存储空间,分配成功返回一个指向起始地址的指针,作为串的基址,同时,约定的串长也作为存储结构的一部分。函数free则用来释放用malloc分配的存储空间。

串的基本运算的实现

(1)顺序串结构定义

typedef struct{char Data[100];//定义字符串的总大小int len;//记录字符串长度
}String;

(2)求串的长度操作

int Long(String *s){//求字符串长度int i=0;while(s->Data[i]!='\0'){i++;}s->len=i;return(s->len);//返回串长
}

(3)建立串操作

void Establish(String *s){//建立字符串printf("输入元素:");gets(s->Data);//输入元素s->len=Long(s); //求长度if(s->len>0){//判断创建是否成功printf("String创建成功!"); }else{printf("String创建失败!!!"); }
}

(4)求子串操作

void SubString(String *s,String *Sud){//求子串函数,String *Sud定义存放子表元素 int pod;//定义变量pod表示位置int i,len;//定义len子串长度printf("输入开始求子串的位置:");scanf("%d",&pod);printf("\n输入子串长度:");scanf("%d",&len);if(pod<1||pod>s->len||len<1||len>s->len-pod+1){//判断所开始查找的位置是否在主串上,如果在就执行else里的语句,如果不在吧Sud置空输出错误信息结束。 Sud->len=0;printf("\n参数错误!!");}else{for(i=0;i<len;i++){Sud->Data[i]=s->Data[pod+i-1];//把pod位置上的元素赋值给Sud串上的第一个位置 }Sud->Data[i]='\0';//Sud尾部加上结束标志 Sud->len=len;//把len输入的长度赋值给Sud串的len,表示子串长度 if(Sud->len<len){//如果Sud的长度小于输入len 在输出错误 结束程序 ,反之输出子表元素 printf("发生错误!!");exit(1); }else{printf("\n子串元素为:");for(i=0;i<len;i++){printf("%5c",Sud->Data[i]);}}}
}

(5)删除子串的操作

void StrDelete(String *s){int j,k,l,x,i,y;printf("输入子串删除的位置:");scanf("%d",&j);printf("\n输入删除子串的长度:");scanf("%d",&l);x=s->len;//把串长赋值给X变量 if(j+l-1>s->len){//删除的位置加上删除子串的长度如果大于主串则报错退出程序 printf("\n子串越界!!"); exit(1);}else{y=s->len;for(k=j+l-1;k<y;k++,j++){//从第j个位置开始删除长度l的子串 s->Data[j-1]=s->Data[k];s->len--;} s->Data[s->len]='\0';//尾部结束标志 }if(s->len>x){//如果串长大于删除之前的串长则报错,退出程序 printf("\n删除错误!!");exit(1);}else{printf("\n删除成功。");//删除成功,输出删除后的串 printf("\n删除后的串:"); for(i=0;i<s->len;i++){printf("%5c",s->Data[i]);}}
}

(6)插入子串操作

void StrInsert(String *s ,String *s1){//插入子串的操作 printf("创建子串:");  gets(s1->Data);//给子串s1赋值 int i,k;k=0;while(s1->Data[k]!='\0'){//计算子串S1长度 k++;}s1->len=k;//把计算得到s1长度的K赋值给len printf("输入插入子串的位置:");scanf("%d",&i);if(i>s->len){//如果插入子串S1的位置大于主串S,则直接报错 退出程序 printf("插入子串的位置错误!");exit(1); }else if(s->len+s1->len>100){//如果插入S1和主串S大于最大分配空间,则直接报错,退出程序 printf("\n错误!串超过存储空间!!");exit(1); }else{for(k=s->len-1;k>=i-1;k--){//将第i位开始向后移动S1长度 s->Data[s1->len+k]=s->Data[k];}for(k=0;k<s1->len;k++){//将s1插入到串S的第i为处 s->Data[i+k-1]=s1->Data[k];}s->len=s->len+s1->len;//修改S串的总长度 s->Data[s->len]='\0';//尾部加结束标志 }i=s->len;if(s->len==s->len-s1->len){//判断如果修改后的主串长度与修改前的主串长度相等则直接报错 printf("发错错误!!");exit(1);}else{printf("插入子串后的串:"); //输出插入子串后的串 for(k=0;k<i;k++){ printf("%5c",s->Data[k]);} }}

(7)子串的定位操作 (模式匹配 BF算法)

void StrIndex_BF(String *s,String *t){//子串的定位操作 (模式匹配 BF算法) printf("创建子串:");int i=0,j=0,k;gets(t->Data);while(t->Data[i]!='\0'){i++;}t->len=i;i=0;while(i<s->len&&j<t->len){ if(s->Data[i]==t->Data[j]){//主串元素等子串元素 i++; j++;}else{i=i-j+1;//如果不相等主串元素一项下一个元素,j归零重新比较 j=0;}}if(j>=t->len){//在串S中有串T k=i-t->len+1;printf("子串在主串的%d位置!",k);}else{printf("主串上并没有找到该子串!");}}

(8)子串的定位操作 (模式匹配 KMP算法)

void StrIndex_KMP(String *s,String *t){//子串的定位操作 (模式匹配 KMP算法)printf("创建子串:");gets(t->Data);int i,j,l,k;i=0;j=1;int nextval[100];//T的next函数修正值并存入数组nextval while(t->Data[i]!='\0'){i++;}t->len=i;l=0;k=1;nextval[1]=0;while(k<t->len){if(l==0||t->Data[k]==t->Data[l]){//t->Data[K]表示后缀,t->Data[l]表示前缀 ++l;++k;if(t->Data[k]!=t->Data[l]){//如果当前字符与前缀不相同 nextval[k]=l;//则修正数组存放当前字符的前缀。 }else{nextval[k]=nextval[l];//如果与前缀字符相同,则将前缀字符的 nextval值赋值给nextval在i位置的值 }}else {k=nextval[k];}}while(i<s->len&&j<t->len){if(j==0||s->Data[i]==t->Data[j]){i++;j++;}else{j=nextval[j];}}k=t->len;j=l=0;if(i>t->len){while(j<s->len){if(s->Data[j]==t->Data[l]&&l<=t->len){k--;}j++;l++;}if(k==0){printf("子串在主串的%d位置!",i-t->len+1);}else{printf("主串上并没有找到该子串!");}}else{printf("主串上并没有找到该子串!");}
}

(9)判断两串是否相等

void StrCompare(String *s,String *s1){printf("创建对比串:");gets(s1->Data);int i=0,floa=0;while(s1->Data[i]!='\0'){i++;}s1->len=i;i=0;if(s->len==s1->len){//判断长度是否相等,相等则进入下一步 while(s->len='\0'){//判断元素是否相等 if(s->Data[i]==s1->Data[i]){floa++;}}if(floa==s->len==s1->len){printf("这个两字符串相等。");}}else{printf("两字符串不相等!!"); }
}

(10)两串链接

void StrCat(String *s,String *t){//两串链接 printf("创建链接串:");gets(t->Data);int i=0;while(t->Data[i]!='\0'){i++;}t->len=i;if(s->len+t->len<=100){for(i=s->len;i<s->len+t->len;i++){s->Data[i]=t->Data[i-s->len];}s->Data[i]='\0';s->len=s->len+t->len;printf("链接后的串:");for(i=0;i<s->len;i++){printf("%5d",s->Data[i]);}}else if(s->len+t->len>100&&s->len<100){for(i=s->len,i<100;i++;){s->Data[i]=t->Data[i-s->len];}s->len=100;printf("链接后的串:");for(i=0;i<s->len;i++){printf("%5c",s->Data[i]);}}else{printf("出错了!!");}}

数据结构(C语言)-串相关推荐

  1. 串的堆分配存储c语言,数据结构c语言串的堆分配存储源程序

    <数据结构c语言串的堆分配存储源程序>由会员分享,可在线阅读,更多相关<数据结构c语言串的堆分配存储源程序(7页珍藏版)>请在人人文库网上搜索. 1.include#inclu ...

  2. c语言实现bf算法的定位函数,数据结构c语言版严蔚敏清华大学出版社第四章串.ppt...

    数据结构c语言版严蔚敏清华大学出版社第四章串 模式匹配(定位) 设有主串S和子串T(将S称为目标串,将T称为模式串),在主串S中,从位置start开始查找,如若在主串S中找到一个与子串T相等的子串,则 ...

  3. 以串结构存储c语言版,数据结构C语言版 串的块链存储表示和实现

    <数据结构C语言版 串的块链存储表示和实现>由会员分享,可在线阅读,更多相关<数据结构C语言版 串的块链存储表示和实现(13页珍藏版)>请在人人文库网上搜索. 1.*数据结构C ...

  4. 数据结构c语言版第四章题库,严蔚敏《数据结构(c语言版)习题集》答案第四章 串...

    严蔚敏<数据结构(c语言版)习题集>答案第四章 串 第四章 串 4.10 void String_Reverse(Stringtype s,Stringtype &r)//求s的逆 ...

  5. 字符串基本操作 c语言,数据结构C语言字符串的基本操作.doc

    数据结构C语言字符串的基本操作 串的基本操作 #include #include #include #define m 100 typedef struct{ char ch[m]; int leng ...

  6. a - 数据结构实验之串一:kmp简单应用_【在线教学示范课案例】数据结构(刘航)...

    一.教师简介 刘航,网络空间安全学院教师,本科生"数据结构"."算法设计综合实验" 和研究生"算法设计与优化"课程的主讲教师.近年来积极开展 ...

  7. 数据结构c语言版第16页,数据结构c语言版

    数据结构c语言版[编辑] 概述 <数据结构C语言版>本书的前半部分从抽象数据类型的角度讨论各种基本类型的数据结构及其应用;后半部分主要讨论查找和排序的各种实现方法及综合分析比较 出版信息 ...

  8. C语言数据结构编程实列,数据结构C语言实现----栈的实例

    用栈的知识,编写一个程序,输入二进制,输出十进制 注意点: 1.在主函数里别忘了先创建一个栈,在进行入栈操作 2.转换过程会用到一个循环,需要用到栈的实际长度作为条件,要在进入循环前先把长度计算出来存 ...

  9. 数据结构c语言版实验报告2,数据结构(C语言版) 实验报告 (2)

    <数据结构(C语言版) 实验报告 (2)>由会员分享,可在线阅读,更多相关<数据结构(C语言版) 实验报告 (2)(15页珍藏版)>请在人人文库网上搜索. 1.数据结构(C语言 ...

  10. 【知识索引】【数据结构(C语言)】

    数据结构(C语言)知识索引 本文为[数据结构(C语言)]知识索引 文章目录 数据结构(C语言)知识索引 1.[数据结构(C语言)]数据结构-表 2.[数据结构(C语言)]数据结构-树 3.[数据结构( ...

最新文章

  1. oracle11g insufficient,ORACLE11GORA-01031:insufficientprivileges
  2. GTDB:基因组分类数据库,物种注释和进化树构建工具GTDB-tk
  3. 解决Layui数据表格无数据最后列被顶出去的问题
  4. Linux常用基本命令:三剑客命令之-awk输入输出分隔符
  5. [转]将Ubuntu默认的邮件客户端Evolution替换为Thunderbird
  6. java中的图形界面编辑界面_第58节:Java中的图形界面编程-GUI
  7. ORA-01940:cannot drop a user that is currently connected
  8. Python初识与简介【开篇】
  9. 农村初中学校计算机课的意义,关于农村学校计算机课件使用的反思.pdf
  10. 301 302区别_如何正确理解301,302和canonial标签
  11. Javascrip之匿名函数
  12. python 网上爬取数据源码_Python爬虫经常爬不到数据,或许你可以看一下小编的这篇文章...
  13. delphi xe6 让 ListView 在 Android 可回弹[根据龟山阿卍原创修改为xe6版本]
  14. 基于Java毕业设计房产客户信息管理系统源码+系统+mysql+lw文档+部署软件
  15. Javaweb实现简易的留言板项目
  16. mysql 报表设计工具_如何使用报表创建工具Navicat创建报表
  17. ubuntu怎么连网线上网_安装完ubuntu 16.04连接网线无法上网解决
  18. Proe转Solidworks
  19. 如何根据业务需求来选择合适的代理IP
  20. Mac使用技巧:轻松自定义设置系统键盘

热门文章

  1. 51单片机跑马灯c语言,51单片机——跑马灯详解(示例代码)
  2. Wonderware-InTouch相关软件下载链接(intouch、驱动、OPC、数据库)
  3. maple 假设_Maple教程-第5章解方程讲解上
  4. WPF中StackPanel的尺寸的怪癖
  5. 删除WIN10右键解压缩菜单
  6. H5图像遮罩-遁地龙卷风
  7. Python:minicap实现快速截图
  8. 解析银行卡卡BIN的来龙去脉
  9. html绘制小球并跟随鼠标移动,Canvas跟随鼠标炫彩小球的实现
  10. NFT商城/NFT盲盒/虚拟盲盒/NFT交易/可定制二开