【串】串的链式存储结构与应用/例题

块链串

在这里插入图片描述
如果一个结点大小为 4 ,链域大小为 2 ,根据**存储密度=串值占用的存储位/实际为串分配存储位,故该字符串的存储密度为 2 /3 。**显然,串的存储密度越小,运算处理就越方便,但存储占用的量较大。应根据具体情况来确定使用串的何种存储结构。

  1. 结点大小等于 1 :当 BLOCK_SIZE 等于 1 时,每个结点存放 1 个字符,结构同线性链表,存
    储结构可定义如下,插入、删除的处理方法和线性链表一样,参见本章典型题解部分串的链式
    模式匹配,算法处理简单,但存储密度较低。
  2. 结点大于 1 :当 BLOCK_SIZE 大于 1 时,每个结点存放多个字符,当最后一个结点未存满
    时,不足处可用特定字符(如#)补齐。虽然存储密度相对结点大小等于 1 的存储方法来说,存储
    密度较高,但此时插入、删除的处理方法比较复杂,需要考虑结点的分拆和合并。
块链串的结构
#define BLOCK_SIZE 4 /*每结点存放字符个数 4*/
typedef struct Block
{
    char ch[BLOCK_SIZE];
    struct Block *next;
} Block;
typedef struct
{
    Block *head;
    Block *tail;
    int len;
} BLString;
串的应用举例:简单的行编辑器

可将文本看成为一个大的字符串,文本编辑就相当对字符串的处理。文本编辑程序用于源程序的输入和修改,公文书信、报刊和书籍的编辑排版等。常用的文本编辑程序有Edit,WPS,Word 等。文本编辑的实质是修改字符数据的形式和格式,虽然各个文本编辑程序的功能不同,但基本操作是一样的,都包括串的查找、插入和删除等。
为了编辑方便,可以用分页符和换行符将文本分为若干页,每页有若干行。可以把文本当作一个字符串,称为文本串,页是文本串的子串,行是页的子串。这里采用堆存储结构来存储文本,同时设立页指针、行指针和字符指针,分别指向当前操作的页、行和字符,同时建立页表和行表存储每一页、每一行的起始位置和长度。

  • 假设有如下 Pascal 源程序:
    FUNC max(x,y:integer):integer;
    VAR z:integer;
    BEGIN
    IF x>y THEN z:=x;
    ELSE z:=y;
    RETURN(z);
    END;

该程序输入内存后放到一个堆中,如图 4.3 所示。其中↙为换行符。表 4-1 和表 4-2 分别
为下图所示文本串的页表和行表。

在这里插入图片描述
由表 4 -1 、表 4 -2 可以看出,当在某行内插入字符时,就要修改行表中该行的长度,若该行的长度超出了分配给它的存储空间,则要重新给它分配存储空间,同时修改它的起始位置和长度。如果要插入或删除一行,就要进行行表的插入和删除,当行的插入和删除涉及页的变化是时要对页表进行修改。

典型题例

要求编写一个用带头结点的单链表实现串的模式匹配算法,每个结点存放一个字符(结
点大小为 1 )。借助于前面的结点大小为 1 定义链串类型 LKString。
【问题分析】该算法类同顺序串的简单模式匹配,实现匹配过程需考虑链表的特征(从头
比较的技术,指针保留的技术)。
【算法思想】
①初始化:主串从start开始,模式串从头开始
②两串逐位比较:当主串模式串均未遍历完时,对应字符作比较
若相等:主串模式串的当前比较位置均后移
若不等:主串从开始比较位置的下一个开始,模式串从头开始
③判别:若匹配成功返回起始位置指针,若不成功,返回NULL
【算法描述】

Link *StrIndex(LKString *s, LKString *t)
/* 求模式串 t 在主串 s 中第一次出现的位置指针 */
{
    Link *sp, *tp, *start;
    if (t->len == 0)
        return s->head->next; /* 空串是任意串的子串 */
    start = s->head->next;    /* 记录主串的起始比较位置 */
    sp = start;               /* 主串从 start 开始 */
    tp = t->head->next;       /* 模式串从第一个结点开始 */
    while (sp != NULL && tp != NULL)
    {
        if (sp->ch == tp->ch) /* 若当前对应字符相同,则继续比较 */
        {
            sp = sp->next;
            tp = tp->next;
        }
        else /* 发现失配字符,则返回到主串当前起始位置的下一个结点继续比较*/
        {
            start = start->next; /* 更新主串的起始位置 */
            sp = start;
            tp = t->head->next; /* 模式串从第一个结点重新开始 */
        }
    }
    if (tp == NULL)
        return start; /* 匹配成功,返回主串当前起始位置指针 */
    else
        return NULL; /* 匹配不成功,返回空指针 */
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值