栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > C/C++/C#

【图解数据结构】串全面总结

C/C++/C# 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

【图解数据结构】串全面总结

一、基本概念
  • 串(string):由0个或多个字符组成的有序序列,称为字符串,记为s=‘abcdefg’ 其中s是字符串的名字,a b c称为串的值,可以是字母、数字或者字符

  • 串长度:串中元素个数

  • 空串:不含任何字符的串,串长度为0

  • 子串:主串中任意连续字符组成的字符串

  • 串s1、s2相等的条件:

    1. s1、s2长度相等
    2. s1、s2对应位置的元素处处相等
二、串的类型 1.定长顺序串

定义:用一组地址连续的存储单元存储串值的字符序列,类似于线性表的顺序存储结构。

静态存储分布代码实现:

#define MAXLEN 30 // 用户可在255以内定义最大串长 
typedef struct 
{
    char ch[MAXLEN];
    int len;
} SString ; 

动态演示:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-9J6hPQ0Y-1652680719887)(https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/dabebec6e1d440d3b65bc37f3ba3afbb~tplv-k3u1fbpfcp-zoom-in-crop-mark:1956:0:0:0.image)]

  • 其实就是依次插入
2.基本算法

串插入:

int StrInsert(SString *s, int pos, SString t)
 {	int i;
	if (pos<0 || pos>s->len)   
		return 0; 
	if (s->len + t.len<=MAXLEN) 
	{
		for (i=s->len + t.len-1;i>=t.len + pos;i--)
			s->ch[i]=s->ch[i-t.len]; //将插入位置现有字符后移
		for (i=0;ich[i+pos]=t.ch[i];   //在空出的位置逐个插入字符串
		s->len=s->len+t.len;
	}	
else
	{         if (pos+t.len<=MAXLEN) 
             
		{
			for (i=MAXLEN-1;i>t.len+pos-1;i--) 
   			s->ch[i]=s->ch[i-t.len]; //将插入位置现有字符后移
			for (i=0;ich[i+pos]=t.ch[i]; //在空出的位置逐个插入字符串
			s->len=MAXLEN;
		}
		else 
		{ 	for (i=0;ich[i+pos]=t.ch[i];
			s->len=MAXLEN;
		}
		return 1;
	}
} 

串删除:

int StrDelete(SString *s, int pos, int len)
 { 
	int i;
	if (pos<0 || pos>(s->len-len))  
		return 0; 
	for (i=pos+len;ilen;i++)
		s->ch[i-len]=s->ch[i];   
	s->len=s->len - len;    
	return 1;
} 

串复制:

void StrCopy(SString *s, SString t)
 { 
	int i;
	for (i=0;ich[i]=t.ch[i];
	s->len=t.len;
} 

串比较:

int StrCompare(SString s, SString t)
 { 
	int i;
	for (i=0;i 

串连接:

int StrCat(SString *s, SString t)
 { 	int i, flag;
	if (s->len + t.len<=MAXLEN) 
                   
	{ 
		for (i=s->len; ilen + t.len; i++)
			s->ch[i]=t.ch[i-s->len]; //t的下标从0开始
		s->len+=t.len;
		flag=1;
   }
	else 
    {
        if (s->lenlen;ich[i]=t.ch[i-s->len];
		    s->len=MAXLEN;
	    	flag=0;
	    }
	    else 
	    	flag=0;  
	return flag;
    } 

求子串:

int SubString(SString *sub, SString s, int pos, int len) 
 { 	int i;
       if (pos<0 || pos>s.len || len<1 || len>s.len-pos) //位置或长度不合法时
       {
		sub->len=0;
		return 0; 
	}
	else 
	{
           for (i=0; ich[i]=s.ch[i+pos];
            
            sub->len=len;
            return 1;
	}
} 
3.堆串
  • 堆:自由存储区域,malloc()实现
  • 以一组地址连续的存储单元存储串值的字符序列,在程序执行过程中由动态分配而得到

代码:

typedef struct {  
      char *ch; // 若非空串则按串长分配存储区,否则为NULL
      int length;// 串长度
} HString; 
4.块链串
  • 定义:与链表类似,但每一个结点可以存放多个字符,结尾增加尾指针

代码实现:

#define BLOCK_SIZE 4 // 可由用户定义的块大小 
typedef struct Block
 { 
     char ch[BLOCK_SIZE];
     struct Block *next;
} Block; 
三、模式匹配
  • 定义:求解子串首次在主串中出现的位置
  • 模式匹配也称为子串的定位操作,用函数StrIndex(S,pos,T)实现,T被称为模式串。

代码:

int StrIndex(SString s,int pos, SString t) 
 { 	int i, j, start;
	if (t.len==0)  return(0);   
	start=pos; i=start; j=0;  
	while (i=t.len) 
			return(start);    
		else 
			return(-1);    
} 

演示图:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-WoTdkRGP-1652680719889)(https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/ad8b2c8cdd504a6e8e072aafeb3f29c5~tplv-k3u1fbpfcp-zoom-in-crop-mark:1956:0:0:0.image)]

解析:

  • 设置两个指针i和k,输入目标串Hello World!,模式串orl
  • 如果i指向的值和模式串首个元素不一致,则指针i j同时向后移动
  • 如果i指向的值和模式串首个元素一致,则只是指针j向后移动
  • 如果j指向的元素和模式串后续元素一致,继续移动,直到查找完成
  • 如果j指向的元素和模式串后续元素不一致,指针i到k的位置,继续开始
四、总结与提高

在C++中,C++ 标准库提供了 string 类类型,支持上述所有的操作,另外还增加了其他更多的功能。

编程时加入头文件:

#include//或者万能头文件#include
using namespace std; 
String函数:

用string定义s类(定义什么都可以,只要把s变成定义的字母就可以调用C++中的函数),具体使用方法为:

函数用法
常见操作
s.resize(10)设置字符串长度为10
string s(“ABC”)构造字符串s的值为ABC
s.empty()判断字符串是否为空
s.length()或者s.size()求解字符串长度
s.begin()开始值
s.end()结尾值
查找(查找成功返回元素位置,失败返回-1)
s.find(‘A’)查找字符A
s.find(“ABC”)查找字符串ABC
s.find(‘A’,2)从位置2开始查找字符A
s.find(“ABCD”,1,2)从位置1开始,查找ABCD的前两个字符
s.rfind()从字符串尾部开始查找
插入
s.insert(2,3,‘A’)在下标为2的地方添加三个A
s.insert(2,“ABC”)在下标为2的地方添加字符串ABC
s.insert(2,“ABC”,1)在下标为2的地方添加ABC中的一个
s.insert(2,“ABCD”, 2,2)在下标为2的地方从字符串ABCD中位置2开始的2个字符
s.push_back(‘A’)在尾部添加字符A
替换
s.replace(2,4,“ABCD”)从下标2的位置,替换4个字符为 “ABCD”
删除
s.erase(2)删除下标2以后的全部元素
s.erase(2,1)删除下标2以后的第一个元素
翻转
reverse(s.begin(),s.end())翻转所有字符串,即逆序输出
复制
s1=s.substring(2)提取字符串s从2到尾部赋值给s1
s1=s.substring(2,3)提取字符串s从2开始三个字符赋值给s1
const char*s1=s.data()将string类转为字符串数组
s.copy(s1,2,3)将s中从第3个位置拷贝2个字符到s1中
比较(假设原字符串为ABCD)
s.compare(“ABCD”)相等返回0,大于原字符串返回1,小于返回-1
清空
s.assign(“ABC”)清空字符串,并置为ABC
s.assign(“ABC”,2)清空字符串,并置为ABC的前2个字符AB
s.assign(“ABC”,2,1)清空字符串,并置为ABC的从2开始的1个字符
s.assign(5,‘A’)清空字符串,并置为5个A
s.clear()清空字符串所有字符

文档的具体内容可以参考:C++标准官方文档

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/890333.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号