返回目录:
Chilan Yu:《数据结构》目录链接zhuanlan.zhihu.com4.2.2 堆串
字符串包括串名与串值两部分,而串值采用堆串存储方式存储,串名用符号表存储。
堆串存储方式:这种存储方法以一组地址连续的存储单元存放串的字符序列,但它们的存储空间是在程序执行过程中动态分配的。系统将一个地址连续、容量很大的存储空间作为字符串的可用空间,每当建立一个新串时,系统就从这个空间中分配一个大小和字符串长度相同的空间存储新串的串值。
串名符号表:所有串名的存储映像构成一个符号表。借助此结构可以在串名和串值之间建立一个对应关系,称为串名的存储映像。
堆串的存储映象示例: a='a program',b='string ',c='process',free=23
(注意:b中string后有一个空格)
堆串定义:
/*堆串的定义*/
typedef struct{char * ch;//位置指针(指示串的起始地址)int len;//串的长度
}HString;
1. 堆串赋值函数
/*堆串赋值函数*/
void StrAssign(HString * s,char * tval){//将字符串常量tval的值赋给堆串sint len,i=0;if(s->ch!=NULL) free(s->ch);//如果堆串的起始位置指针有所指,则释放空间while(tval[i]!='0') ++i;//遍历一遍字符串常量tval得到其长度len = i;if(len){//如果字符串常量tval长度不为0s->ch = (char *)malloc(len);//开辟空间for(i=0;i<len;++i) s->ch[i] = tval[i];//每个字符一一赋值}else s->ch = NULL;//否则把堆串的起始位置指针指向NULLs->len = len;//修改堆串长度
}
2. 堆串插入函数
/*堆串插入函数*/
void StrInsert(HString * s,int pos,HString * t){//在串s中下标为pos的字符之前插入串tint i;char * temp;if(pos<0 || pos>s->len || s->len==0) return ;//插入位置不合法temp = (char *)malloc(s->len+t->len);for(i=0;i<pos;++i) temp[i] = s->ch[i];//先把s中在pos之前的字符复制到temp中for(i=0;i<t->len;++i) temp[i+pos] = t->ch[i];//再把t插入for(i=pos;i<s->len;++i) temp[i+t->len] = s->ch[i];//最后把s中在pos之后的字符复制到temp中s->len += t->len;//更新长度free(s->ch);//释放原来所指位置s->ch = temp;//把起始位置指针指向新的位置
}
3. 堆串删除函数
/*堆串删除函数*/
void StrDelete(HString * s,int pos,int len){//在串s中删除从序号pos起len个字符int i;char * temp;if(pos<0 || pos>(s->len-len)) return ;temp = (char *)malloc(s->len-len);for(i=0;i<pos;++i) temp[i] = s->ch[i];for(i=pos;i<s->len-len;i++) temp[i] = s->ch[i+len];s->len = s->len-len;free(s->ch);s->ch = temp;
}
4. 堆串复制函数
/*堆串复制函数*/
void StrCopy(HString * s,HString t){//将串t的值复制到串s中int i;s->ch = (char *)malloc(t.len);for(i=0;i<t.len;++i)s->ch[i] = t.ch[i];s->len = t.len;
}
5. 判空函数
/*判空函数*/
int StrEmpty(HString s){//若串s为空(即串长为0),则返回1,否则返回0if(s.len==0) return 1;else return 0;
}
6. 堆串比较函数
/*堆串比较函数*/
int StrCompare(HString s,HString t){//若串s和t相等,则返回0,若s>t返回1,若s<t返回-1int i;for(i=0;i<s.len && i<t.len;++i)if(s.ch[i]!=t.ch[i])return(s.ch[i]-t.ch[i]);return(s.len-t.len);
}
7. 求串长函数
/*求串长函数*/
int StrLength(HString s){//返回串s的长度return s.len;
}
8. 清空函数
/*清空函数*/
void StrClear(HString * s){//将串s置为空串if(s->ch!=NULL) free(s->ch);s->ch = NULL;s->len = 0;
}
9. 连接函数
/*连接函数*/
void StrCat(HString * s,HString t){//将串t联接在串s的后面int i;char * temp;temp = (char *)malloc(s->len+t.len);for(i=0;i<s->len;++i)temp[i] = s->ch[i];for(i=s->len;i<s->len+t.len;++i)temp[i] = t.ch[i-s->len];s->len += t.len;free(s->ch);s->ch = temp;
}
10. 求子串函数
/*求子串函数*/
void SubString(HString * sub,HString s,int pos,int len){//将串s中序号pos起len个字符复制到sub中int i;if(sub->ch!=NULL) free(sub->ch);if(pos<0 || pos>s.len || len<1 || len>s.len-pos){sub->ch = NULL;sub->len = 0;return;}else{sub->ch = (char *)malloc(len);for(i=0;i<len;++i)sub->ch[i] = s.ch[i+pos];sub->len = len;}
}
11. 定位函数
/*定位函数*/
int StrIndex(HString s,int pos,HString t){//求串t在串s中的位置int i,j;if(s.len==0 || t.len==0) return 0;i = pos;j = 0;while(i<s.len && j<t.len)if(s.ch[i]==t.ch[j]){i++;j++;}else{i = i-j+1;j = 0;}if(j>=t.len) return i-j;else return 0;
}