数据结构 | 实现行编辑程序(严蔚敏老师数据结构3.2)

————————————————————————————————————————————

/**************************************************/
/*
行编辑程序 */
/*
输入的数据存入缓冲区用来接收用户输入的一行字符 */
/*
之后逐行存入用户数据区 */
/*
当用户输入出错时可以输入退格符 # 来表示前一个字符无效 */
/*
输入@ 表示当前行中之前输入的字符无效 */
/**************************************************/

————————————————————————————————————————————

v1:读取一行直接打印,不存入数据区

代码实现:

 

  1 /**************************************************/
  2 /* v1:读取一行直接打印,不存入数据区 */
  3 /**************************************************/
  4 #include <stdio.h>
  5 #include <string.h>
  6 #include <stdlib.h>
  7 #define STACK_INIT_SIZE 100
  8 #define STACKINCREAMENT 10
  9 #define OK 1
 10 #define ERROR 0
 11 #define OVERFLOW -2
 12 typedef char SElemtype;
 13 typedef int Status;
 14 typedef struct
 15 {
 16     SElemtype *top;
 17     SElemtype *base;
 18     int stacksize;
 19 } SqStack;
 20 Status InitStack(SqStack *s)
 21 {
 22     s->base = (SElemtype *)malloc(STACK_INIT_SIZE * sizeof(SElemtype));
 23     if (!s->base)
 24         exit(OVERFLOW);
 25     s->top = s->base;
 26     s->stacksize = STACK_INIT_SIZE;
 27     return OK;
 28 }
 29 Status Push(SqStack *s, SElemtype c)
 30 {
 31     if (s->top - s->base == s->stacksize)
 32     {
 33         s->base = (SElemtype *)realloc(s->base, (s->stacksize + STACKINCREAMENT) * sizeof(SElemtype));
 34         if (!s->base)
 35             exit(OVERFLOW);
 36         s->top = s->base + s->stacksize;
 37         s->stacksize += STACKINCREAMENT;
 38     }
 39     s->top++;
 40     *(s->top) = c;
 41     return OK;
 42 }
 43 Status Pop(SqStack *s)
 44 {
 45     if (s->top == s->base)
 46         return ERROR;
 47     --s->top; //此处弹栈不需要返回栈顶元素,直接删除即可
 48 }
 49 Status PrintStack(SqStack *s)
 50 {
 51     int i = 0;
 52     while((s->base + i) != (s->top))//遍历栈,从栈底+1开始直到栈顶为止
 53     {
 54         i++;
 55         printf("%c", *(s->base + i));
 56     }
 57     return OK;
 58 }
 59 Status ClearStack(SqStack *s)
 60 {
 61     s->top = s->base;
 62     return OK;
 63 }
 64 /**************************************************/
 65 /* 通过getchar()接收当前输入的一个字符 */
 66 /* 输入为 非#@ 时压栈 */
 67 /* 输入为 # 时弹栈删除上一个字符 */
 68 /* 输入为 @ 时清空栈中元素 */
 69 /* 输入为 \n 时清栈 */
 70 /* 输入为 EOF 时结束输入 */
 71 /**************************************************/
 72 void LineEdit(SqStack *s, SElemtype c)
 73 {
 74     switch(c)
 75     {
 76     case '#':
 77         Pop(s);
 78         break;
 79     case '@':
 80         ClearStack(s);
 81         break;
 82     default:
 83         Push(s, c);
 84         break;
 85     }
 86 }
 87 int main(void)
 88 {
 89     SqStack s;
 90     SElemtype c, *temp;
 91     InitStack(&s);
 92     c = getchar();
 93     while(c != EOF)
 94     {
 95         while(c != EOF && c != '\n')
 96         {
 97             LineEdit(&s, c);
 98             c = getchar();
 99         }
100         PrintStack(&s);
101         ClearStack(&s);
102         printf("\n");
103         // if(c != EOF)
104         c = getchar(); // 读取下一行的第一个字符
105     }
106     return 0;
107 }

————————————————————————————————————————————

v2:将读取到的行存入数据区(字符串数组),最终统一打印

代码实现:

 

  1 /**************************************************/
  2 /* v2:将读取到的行存入数据区(字符串数组),最终统一打印 */
  3 /**************************************************/
  4 #include <stdio.h>
  5 #include <string.h>
  6 #include <stdlib.h>
  7 #define STACK_INIT_SIZE 100
  8 #define STACKINCREAMENT 10
  9 #define OK 1
 10 #define ERROR 0
 11 #define OVERFLOW -2
 12 typedef char SElemtype;
 13 typedef int Status;
 14 typedef struct
 15 {
 16     SElemtype *top;
 17     SElemtype *base;
 18     int stacksize;
 19 } SqStack;
 20     Status InitStack(SqStack *s)
 21 {
 22     s->base = (SElemtype *)malloc(STACK_INIT_SIZE * sizeof(SElemtype));
 23     if (!s->base)
 24         exit(OVERFLOW);
 25     s->top = s->base;
 26     s->stacksize = STACK_INIT_SIZE;
 27     return OK;
 28 }
 29 Status Push(SqStack *s, SElemtype c)
 30 {
 31     if (s->top - s->base == s->stacksize)
 32     {
 33         s->base = (SElemtype *)realloc(s->base, (s->stacksize + STACKINCREAMENT) * sizeof(SElemtype));
 34         if (!s->base)
 35             exit(OVERFLOW);
 36         s->top = s->base + s->stacksize;
 37         s->stacksize += STACKINCREAMENT;
 38     }
 39     s->top++;
 40     *(s->top) = c;
 41     return OK;
 42 }
 43 Status Pop(SqStack *s)
 44 {
 45     if (s->top == s->base)
 46         return ERROR;
 47     --s->top;
 48 }
 49 Status ClearStack(SqStack *s)
 50 {
 51     s->top = s->base;
 52     return OK;
 53 }
 54 /**************************************************/
 55 /* 通过getchar()接收当前输入的一个字符 */
 56 /* 输入为 非#@ 时压栈 */
 57 /* 输入为 # 时弹栈删除上一个字符 */
 58 /* 输入为 @ 时清空栈中元素 */
 59 /* 输入为 \n 时清栈 */
 60 /* 输入为 EOF 时结束输入 */
 61 /**************************************************/
 62 void LineEdit(SqStack *s, SElemtype c)
 63 {
 64     switch(c)
 65     {
 66     case '#':
 67         Pop(s);
 68         break;
 69     case '@':
 70         ClearStack(s);
 71         break;
 72     default:
 73         Push(s, c);
 74         break;
 75     }
 76 }
 77 /**************************************************/
 78 /* 读取栈中的元素存入字符串数组str中 */
 79 /* 需要传入已有的数据长度,避免覆盖之前行的数据 */
 80 /**************************************************/
 81 Status SaveStack(SqStack *s, char *str, int lenData)
 82 {
 83     char temp;
 84     int i, j;
 85     for (i = 0; i < s->top - s->base; ++i)
 86         *(str + i + lenData) = *(s->base + i + 1);
 87     return OK;
 88 }
 89 /**************************************************/
 90 /* 打印数据区元素 */
 91 /**************************************************/
 92 Status PrintDataField(char *str, int lenData)
 93 {
 94     int i;
 95     for(i = 0; i < lenData; i++)
 96         printf("%c", *(str + i));
 97     printf("\n");
 98 }
 99 int main(void)
100 {
101     SqStack s;
102     SElemtype c;
103     char str[]; //数据区通过字符串数组str存放
104     int lenData = 0; //定义数据区长度
105     InitStack(&s);
106     c = getchar();
107     while(c != EOF)
108     {
109         while(c != EOF && c != '\n')
110         {
111             LineEdit(&s, c);
112             c = getchar();
113         }
114         Push(&s, '\n'); //本行结束,将换行符压入栈中
115         SaveStack(&s, str, lenData); //保存到数据区
116         lenData += s.top - s.base; 
117               ClearStack(&s); //清空栈
118         c = getchar(); //读取下一行的第一个字符
119     }
120     printf("- - - - - - data field - - - - - - \n");
121     PrintDataField(str, lenData); //打印数据区
122     return 0;
123 }

————————————————————————————————————————————

v3:将读取到的行存入数据区(结构体),最终统一打印

代码实现:

 

  1     /**************************************************/
  2 /* v3:将读取到的行存入数据区(结构体),最终统一打印 */
  3 /**************************************************/
  4 #include <stdio.h>
  5 #include <string.h>
  6 #include <stdlib.h>
  7 #define STACK_INIT_SIZE 100
  8 #define STACKINCREAMENT 10
  9 #define OK 1
 10 #define ERROR 0
 11 #define OVERFLOW -2
 12 typedef char SElemtype;
 13 typedef int Status;
 14 typedef struct
 15 {
 16     SElemtype *top;
 17     SElemtype *base;
 18     int stacksize;
 19 } SqStack;
 20 /**************************************************/
 21 /* 定义结构体SqDataField,使用字符数组存放数据 */
 22 /**************************************************/
 23 typedef struct
 24 {
 25     char str[100];
 26 } SqDataField;
 27 Status InitStack(SqStack *s)
 28 {
 29     s->base = (SElemtype *)malloc(STACK_INIT_SIZE * sizeof(SElemtype));
 30     if (!s->base)
 31         exit(OVERFLOW);
 32     s->top = s->base;
 33     s->stacksize = STACK_INIT_SIZE;
 34     return OK;
 35 }
 36 Status Push(SqStack *s, SElemtype c)
 37 {
 38     if (s->top - s->base == s->stacksize)
 39     {
 40         s->base = (SElemtype *)realloc(s->base, (s->stacksize + STACKINCREAMENT) * sizeof(SElemtype));
 41         if (!s->base)
 42             exit(OVERFLOW);
 43         s->top = s->base + s->stacksize;
 44         s->stacksize += STACKINCREAMENT;
 45     }
 46     s->top++;
 47     *(s->top) = c;
 48     return OK;
 49 }
 50 Status Pop(SqStack *s)
 51 {
 52     if (s->top == s->base)
 53         return ERROR;
 54     --s->top;
 55 }
 56 Status ClearStack(SqStack *s)
 57 {
 58     s->top = s->base;
 59     return OK;
 60 }
 61 void LineEdit(SqStack *s, SElemtype c)
 62 {
 63     switch(c)
 64     {
 65     case '#':
 66         Pop(s);
 67         break;
 68     case '@':
 69         ClearStack(s);
 70         break;
 71     default:
 72         Push(s, c);
 73         break;
 74     }
 75 }
 76 Status SaveStack(SqStack *s, SqDataField *data, int lenData) //形参接收指向结构体data的地址
 77 {
 78     char temp;
 79     int i, j;
 80     for (i = 0; i < s->top - s->base; ++i)
 81         data->str[i + lenData] = *(s->base + i + 1);
 82     return OK;
 83 }
 84 Status PrintDataField(SqDataField *data, int lenData)
 85 {
 86     int i;
 87     for(i = 0; i < lenData; i++)
 88         printf("%c", data->str[i]);
 89     printf("\n");
 90 }
 91 int main(void)
 92 {
 93     SqDataField data;
 94     SqStack s;
 95     SElemtype c;
 96     int lenData = 0; 
 97     InitStack(&s);
 98     c = getchar();
 99     while(c != EOF)
100     {
101         while(c != EOF && c != '\n')
102         {
103             LineEdit(&s, c);
104             c = getchar();
105         }
106         Push(&s, '\n'); 
107         SaveStack(&s, &data, lenData);  //传入结构体data的地址
108         lenData += s.top - s.base;
109         ClearStack(&s); 
110         c = getchar(); 
111     }
112     printf("- - - - - - data field - - - - - - \n");
113     PrintDataField(&data, lenData); 
114     return 0;
115 }

————————————————————————————————————————————

v4:定义结构体数组为数据区

代码实现:

 

  1     /**************************************************/
  2 /* v4:定义结构体数组为数据区 */
  3 /**************************************************/
  4 #include <stdio.h>
  5 #include <string.h>
  6 #include <stdlib.h>
  7 #define STACK_INIT_SIZE 100
  8 #define STACKINCREAMENT 10
  9 #define OK 1
 10 #define ERROR 0
 11 #define OVERFLOW -2
 12 typedef char SElemtype;
 13 typedef int Status;
 14 typedef struct
 15 {
 16     SElemtype *top;
 17     SElemtype *base;
 18     int stacksize;
 19 } SqStack;
 20 /**************************************************/
 21 /* 定义结构体数组来存放数据 */
 22 /**************************************************/
 23 typedef struct SqDataField
 24 {
 25     char c;
 26 } SqStr;
 27     Status InitStack(SqStack *s)
 28 {
 29     s->base = (SElemtype *)malloc(STACK_INIT_SIZE * sizeof(SElemtype));
 30     if (!s->base)
 31         exit(OVERFLOW);
 32     s->top = s->base;
 33     s->stacksize = STACK_INIT_SIZE;
 34     return OK;
 35 }
 36 Status Push(SqStack *s, SElemtype c)
 37 {
 38     if (s->top - s->base == s->stacksize)
 39     {
 40         s->base = (SElemtype *)realloc(s->base, (s->stacksize + STACKINCREAMENT) * sizeof(SElemtype));
 41         if (!s->base)
 42             exit(OVERFLOW);
 43         s->top = s->base + s->stacksize;
 44         s->stacksize += STACKINCREAMENT;
 45     }
 46     s->top++;
 47     *(s->top) = c;
 48     return OK;
 49 }
 50 Status Pop(SqStack *s)
 51 {
 52     if (s->top == s->base)
 53         return ERROR;
 54     --s->top;
 55 }
 56 Status ClearStack(SqStack *s)
 57 {
 58     s->top = s->base;
 59     return OK;
 60 }
 61 void LineEdit(SqStack *s, SElemtype c)
 62 {
 63     switch(c)
 64     {
 65     case '#':
 66         Pop(s);
 67         break;
 68     case '@':
 69         ClearStack(s);
 70         break;
 71     default:
 72         Push(s, c);
 73         break;
 74     }
 75 }
 76 Status SaveStack(SqStack *s, struct SqDataField *SqStr, int lenData)//形参为指向结构体数组的指针
 77 {
 78     char temp;
 79     int i, j;
 80     for (i = 0; i < s->top - s->base; ++i)
 81         SqStr[i + lenData].c = *(s->base + i + 1);
 82     return OK;
 83 }
 84 Status PrintDataField(struct SqDataField *SqStr, int lenData)
 85 {
 86     int i;
 87     for(i = 0; i < lenData; i++)
 88         printf("%c", SqStr[i].c);
 89     printf("\n");
 90 }
 91 int main(void)
 92 {
 93     struct SqDataField SqStr[STACK_INIT_SIZE]; //声明结构体数组
 94     SqStack s;
 95     SElemtype c;
 96     int lenData = 0;
 97     InitStack(&s);
 98     c = getchar();
 99     while(c != EOF)
100     {
101         while(c != EOF && c != '\n')
102         {
103             LineEdit(&s, c);
104             c = getchar();
105         }
106         Push(&s, '\n');
107         SaveStack(&s, SqStr, lenData);  //传入结构体数组的首地址
108         lenData += s.top - s.base;
109         ClearStack(&s);
110         c = getchar();
111     }
112     printf("- - - - - - data field - - - - - - \n");
113     PrintDataField(SqStr, lenData);
114         return 0;
115 }

 

 

 

posted @ 2017-05-02 18:53  hugh.dong  阅读(568)  评论(0编辑  收藏  举报