zoukankan      html  css  js  c++  java
  • 串的动态存储分配

          串:由零个或者多个字符组成的有限序列。零个字符的串称为空串,和空格串【一个或多个空格诸城的串】有区别,请注意比较。在串的抽象数据类型中,有五个操作组成最小操作子集,分别是串赋值StrAssign,串比较StrCompare,求串长StrLength ,串联接Concat,求子串SubString。现以串的动态存储结构为例,将5个基本操作实现如下:

    具体介绍详见注释。

      1 /**
      2 在串的抽象数据类型的13中操作中:串赋值StrAssign,串比较StrCompare,求串长StrLength
      3 串连接Concat,求子串SubString构成串类型的最小操作子集
      4 
      5 串有三种表示方法:
      6     定长顺序表示
      7     堆分配存储表示
      8     块链存储表示
      9 */
     10 
     11 //主要介绍动态分配:对分配储存表示
     12 //仍然以一组地址连续的存储单元来存放串值字符序列,但他们的存储空间是在程序执行的过程中动态分配的。
     13 //C语言中有一个称之为“堆”自由存储区,并有malloc和free函数来管理
     14 #include <stdio.h>
     15 #include <stdlib.h>
     16 #include <string.h>
     17 //------------------串的堆分配存储结构-----------------
     18 typedef struct
     19 {
     20     char *ch;  //若是非空串,则按串长分配存储区,否则ch为NULL
     21     int length;//串长度
     22 } HString;
     23 
     24 //---------------------串插入操作-----------------------
     25 void StrInsert(HString &S,int pos,HString T)
     26 {
     27     //1<=pos<=StrLength(S)+1,在串S的第pos个字符之前插入串T
     28     if ( pos<1 || pos>S.length+1 )
     29     {
     30         printf("插入位置有误,请确认后重新输入
    ");
     31         getchar();
     32         exit(1);
     33     }
     34     if (T.length)//T非空,则重新分配空间,插入T
     35     {
     36         if(!(S.ch = (char*)realloc(S.ch,(S.length+T.length)*sizeof(char))))
     37         {
     38             printf("空间重新分配有误,任意键退出!
    ");
     39             getchar();
     40             exit(1);
     41         }
     42         for (int i = S.length-1 ; i >= pos-1; --i)
     43         {
     44             /* 为插入T腾出位置 ,从最后一个全体向后挪动T.length个长度*/
     45             S.ch[i+T.length] = S.ch[i];
     46         }
     47         for (int i = 0 ; i < T.length; ++i)
     48         {
     49             /* 将T中的字符插入到S中 */
     50             S.ch[i+pos-1] = T.ch[i];
     51         }
     52         S.length +=T.length;
     53     }
     54 }
     55 //-------------------串的五种基本操作-------------------
     56 void StrAssign(HString &T,char *chars)
     57 {
     58     //生成一个其值等于串常量chars的串T
     59 
     60     if(T.ch)
     61     {
     62         /* 释放T原有空间 */
     63         free(T.ch);
     64     }
     65     int count = 0;//计算字符串长度;
     66     char *c = NULL;
     67 
     68     for(count = 0,c = chars; *c ; ++count,++c);//求chars的长度count
     69     if (!count)
     70     {
     71         /* 空串 */
     72         T.ch = NULL;
     73         T.length = 0;
     74     }
     75     else
     76     {
     77         if (!(T.ch = (char *)malloc(count * sizeof(char))))
     78         {
     79             printf("分配存储空间有误!
    ");
     80             exit(1);
     81         }
     82         for (int i = 0; i < count; ++i)
     83         {
     84             T.ch[i] = chars[i];
     85         }
     86         T.length = count;
     87     }
     88 
     89 }
     90 
     91 //---------------------------求串长度-----------------------
     92 int StrLength(HString S)
     93 {
     94     //返回S的元素个数,称为串的长度
     95     return S.length;
     96 }
     97 
     98 //--------------------------串比较函数------------------------
     99 int StrCompare(HString S,HString T)
    100 {
    101     //若S>T,则返回值大于0;若S<T,则返回值<0;若S=T,则返回值=0
    102     for (int i = 0; i < S.length && i < T.length; ++i)
    103     {
    104         if (S.ch[i] != T.ch[i])
    105         {
    106             return S.ch[i] - T.ch[i];
    107         }
    108     }
    109     return S.length - T.length;
    110 }
    111 
    112 //--------------------------串清除函数------------------------
    113 void ClearString(HString &S)
    114 {
    115     //将串S清除为空串
    116     if (S.ch)
    117     {
    118         free(S.ch);
    119         S.length = 0;
    120     }
    121     S.length = 0;
    122 }
    123 
    124 //--------------------------串联接函数------------------------
    125 void Concat(HString &T,HString S1,HString S2)
    126 {
    127     //用串T返回串S1和串S2联接给成的新串
    128     if (!T.ch)
    129     {
    130         free(T.ch);//释放旧空间
    131     }
    132     if (!(T.ch = (char*)malloc((S1.length+S2.length)*sizeof(char))))
    133     {
    134         printf("分配存储空间有误!
    ");
    135         exit(1);
    136     }
    137     //将两个串联接起来
    138     for (int i = 0; i < S1.length; ++i)
    139     {
    140         T.ch[i] = S1.ch[i];
    141     }
    142     T.length = S1.length + S2.length;
    143     for (int i = 0; i < S2.length; ++i)
    144     {
    145         T.ch[i+S1.length] = S2.ch[i];
    146     }
    147 }
    148 
    149 //----------------------------求子串函数----------------------------
    150 void SubString(HString &Sub,HString S,int pos,int len)
    151 {
    152     //用Sub返回串S的第pos个字符起长度为len的子串
    153     //其中,1<=pos<=StrLength(S)且  0<=len<=StrLength(S)-pos+1
    154     if (pos<1 || pos>S.length || len<0 || len>S.length-pos+1)
    155     {
    156         printf("输入的求子串位置有误,请确认后重新输入!
    ");
    157     }
    158     if (Sub.ch)
    159     {
    160         free(Sub.ch); //释放旧空间
    161     }
    162     if(!len)
    163     {
    164         //空子串
    165         Sub.ch = NULL;
    166         Sub.length = 0;
    167 
    168     }
    169     else
    170     {
    171         Sub.ch = (char*)malloc(len * sizeof(char));
    172         for (int i = 0; i < len; ++i)
    173         {
    174             Sub.ch[i] = S.ch[pos+i-1];
    175         }
    176         Sub.length = len;
    177 
    178     }
    179 }
    180 //--------------------------输出串内容---------------------------
    181 void PrintStr(HString S)
    182 {
    183     if(S.ch)
    184     {
    185         for(int i=0; i<S.length; ++i)
    186         {
    187             printf("%c",S.ch[i]);
    188         }
    189         printf("
    ");
    190     }
    191     else
    192     {
    193         printf("该串是空串!
    ");
    194     }
    195 }
    196 
    197 int main(int argc, char const *argv[])
    198 {
    199     char *c1 = "Hello,this is a test for String";
    200     char *c2 = "I'm string2";
    201     HString s1,s2,s3;
    202     //先将s1,s2,s3置为空串
    203     s1.ch = NULL;
    204     s1.length = 0;
    205     s2.ch = NULL;
    206     s2.length = 0;
    207     s3.ch = NULL;
    208     s3.length = 0;
    209     //测试串赋值
    210     StrAssign(s1,c1);
    211     StrAssign(s2,c2);
    212     printf("两个串赋值之后:
    ");
    213     PrintStr(s1);
    214     PrintStr(s2);
    215     //测试串比较
    216     printf("%d
    ",StrCompare(s1,s2));
    217     //测试串连接
    218     Concat(s3,s1,s2);
    219     PrintStr(s3);
    220     //测试求子串
    221     SubString(s3,s1,1,5);
    222     printf("子串:");
    223     PrintStr(s3);
    224     //测试清空串
    225     ClearString(s3);
    226     printf("清空该串后,输出结果为:");
    227     PrintStr(s3);//无输出结果(串的内容为空),串长度为0
    228     return 0;
    229 }
  • 相关阅读:
    在Ubuntu中通过update-alternatives切换软件版本
    SCons: 替代 make 和 makefile 及 javac 的极好用的c、c++、java 构建工具
    mongodb 的使用
    利用grub从ubuntu找回windows启动项
    How to Repair GRUB2 When Ubuntu Won’t Boot
    Redis vs Mongo vs mysql
    java script 的工具
    python 的弹框
    how to use greendao in android studio
    python yield的终极解释
  • 原文地址:https://www.cnblogs.com/wujiyang/p/4420084.html
Copyright © 2011-2022 走看看