7-7 使用原子 和 子表存储的广义表,<求广义表的长度

来源:互联网 发布:dc元数据 编辑:程序博客网 时间:2024/06/05 01:20

使用原子 和 子表存储的广义表,<求广义表的长度


原子 和 子表存储的广义表的结构

    typedef char DataType;    typedef struct node{       int flag;  //表明是子表还是与原子       struct node * next ; //指向表尾的原子是一定存在的       union{           DataType data;           struct node * head;       }var;    }GNode;

将广义表字符串分割成头表 和尾表

/**  *函数功能描述 , 将广义表字符串分割成头表和尾表结构  *@Param str  ; 传进去的表和充当接受尾表的空间  *@Param hstr ; 接受头表字符串  *  */  void split(char *str,char *hstr){   int lastIndex =  -1; //找到最中间的逗号的位置   int length = strlen(str);   int i,j;   int temp=0;   //找到最中间的,的位置;   for(i=0;i<length;i++){      if(str[i] == '('){        temp++;      }else if(str[i] == ')'){        temp--;      }      if(temp == 1 && str[i] == ','){        lastIndex = i;        break;      }    }      //开始分割:      //1.只有表头的情况      if(lastIndex == -1){         //抽取表头         char *temp = str+1; //移动str的指针         str[length-1] = '\0';         strcpy(hstr,temp);         //返回空表尾         strcpy(str,"()\0");      }else{//两者都有的情况         //构造表头         char * temp = str+1;         str[lastIndex] = '\0';         strcpy(hstr,temp);         //恢复         str[lastIndex] = ',';         //构造表尾         //使用前移动         str[0] = '(';         for(i=lastIndex+1;i<length;i++){             str[i-lastIndex] = str[i];         }         str[i-lastIndex]='\0';      }  }//split

创建广义表

/*  函数功能描述 : 创建一个原子和字表的存储结构  @Param str  :等待创建的字符串  @Return  : 返回当前节点的引用*/ GNode * createGT(char *str,int add){    GNode * node = (GNode *)malloc(sizeof(GNode));    if(strcmp(str,"()") == 0){        return NULL;    }    if(strlen(str) == 1){            node->flag = 0; //表示是一个原子            node->var.data = str[0];            return node;    }else if(strlen(str) == 3){            node->flag = 0;            node->var.data = str[1];            node->next = NULL;            return node;    }else{         //计算是不是只有一对括号        int count = 0;        int i;        for(i =0;i<strlen(str);i++){            if(str[i] == '(') count++;        }       //如果不是就当做普通子表来处理       if(count !=1){        node->flag = 1;        char hstr[20];        split(str,hstr);        // printf(" htsr is %s\n",hstr);        // printf(" str is  %s\n",str);        node->var.head = createGT(hstr,add);        node->next = createGT(str,add);        }else{//如果是 ,第一次的当做普通的子表来处理,否则当做原子来处理        if(add){            node->flag = 0;            char hstr[20];            split(str,hstr);            node->var.data = hstr[0];            // printf(" htsr is %s\n",hstr);            // printf(" str is  %s\n",str);            node->next = createGT(str,add+1);        }else{            node->flag = 1;            node->next = NULL;            node->var.head = createGT(str,add+1);        }       }    }    return node;}

打印广义表

    /*     函数功能描述 :打印输出原子和子表结构的广义表     @Param GNode      */     void printGT(GNode * S){         if(S->flag == 0){                printf("%c ",S->var.data);               if(S->next){                printGT(S->next);               }         }else{              for(;S !=NULL;S = S->next){                 (S->flag == 1)? printGT(S->var.head) : printf("%c",S->var.data);               }         }    }

获取广义表中的原子的个数

/* 求广义表中的原子的个数*/     int GetListAtom(GNode * S){       int num = 0;       if(S->flag == 0){ //是原子的结构          num++;          if(S->next){              num+=GetListAtom(S->next);          }       }else{          for(;S!=NULL;S = S->next){             if(S->flag == 0){                 num++;             }else{             num +=GetListAtom(S->var.head) ;             }          }            }     return num;    }

所有代码演示

/* 设广义表用原子和子表的存储结构来,求广义表中的原子的个数*/#include <stdio.h>#include <string.h>#include <malloc.h>/* @Param str  :等待创建的字符串 @Return  : 返回当前节点的引用>*///原子和字表的结构typedef char DataType;typedef struct node{   int flag;  //表明是子表还是与原子   struct node * next ; //指向表尾的原子是一定存在的   union{       DataType data;       struct node * head;   }var;}GNode;/**  *函数功能描述 , 将广义表字符串分割成头表和尾表结构  *@Param str  ; 传进去的表和充当接受尾表的空间  *@Param hstr ; 接受头表字符串  *  */  void split(char *str,char *hstr){   int lastIndex =  -1; //找到最中间的逗号的位置   int length = strlen(str);   int i,j;   int temp=0;   //找到最中间的,的位置;   for(i=0;i<length;i++){      if(str[i] == '('){        temp++;      }else if(str[i] == ')'){        temp--;      }      if(temp == 1 && str[i] == ','){        lastIndex = i;        break;      }    }      //开始分割:      //1.只有表头的情况      if(lastIndex == -1){         //抽取表头         char *temp = str+1; //移动str的指针         str[length-1] = '\0';         strcpy(hstr,temp);         //返回空表尾         strcpy(str,"()\0");      }else{//两者都有的情况         //构造表头         char * temp = str+1;         str[lastIndex] = '\0';         strcpy(hstr,temp);         //恢复         str[lastIndex] = ',';         //构造表尾         //使用前移动         str[0] = '(';         for(i=lastIndex+1;i<length;i++){             str[i-lastIndex] = str[i];         }         str[i-lastIndex]='\0';      }  }//split/*  函数功能描述 : 创建一个原子和字表的存储结构  @Param str  :等待创建的字符串  @Return  : 返回当前节点的引用*/ GNode * createGT(char *str,int add){    GNode * node = (GNode *)malloc(sizeof(GNode));    if(strcmp(str,"()") == 0){        return NULL;    }    if(strlen(str) == 1){            node->flag = 0; //表示是一个原子            node->var.data = str[0];            return node;    }else if(strlen(str) == 3){            node->flag = 0;            node->var.data = str[1];            node->next = NULL;            return node;    }else{         //计算是不是只有一对括号        int count = 0;        int i;        for(i =0;i<strlen(str);i++){            if(str[i] == '(') count++;        }       //如果不是就当做普通子表来处理       if(count !=1){        node->flag = 1;        char hstr[20];        split(str,hstr);        // printf(" htsr is %s\n",hstr);        // printf(" str is  %s\n",str);        node->var.head = createGT(hstr,add);        node->next = createGT(str,add);        }else{//如果是 ,第一次的当做普通的子表来处理,否则当做原子来处理        if(add){            node->flag = 0;            char hstr[20];            split(str,hstr);            node->var.data = hstr[0];            // printf(" htsr is %s\n",hstr);            // printf(" str is  %s\n",str);            node->next = createGT(str,add+1);        }else{            node->flag = 1;            node->next = NULL;            node->var.head = createGT(str,add+1);        }       }    }    return node;}/* 函数功能描述 :打印输出原子和子表结构的广义表 @Param GNode  */ void printGT(GNode * S){     if(S->flag == 0){            printf("%c ",S->var.data);           if(S->next){            printGT(S->next);           }     }else{          for(;S !=NULL;S = S->next){             (S->flag == 1)? printGT(S->var.head) : printf("%c",S->var.data);           }     }}/* 求广义表中的原子的个数*/ int GetListAtom(GNode * S){   int num = 0;   if(S->flag == 0){ //是原子的结构      num++;      if(S->next){          num+=GetListAtom(S->next);      }   }else{      for(;S!=NULL;S = S->next){         if(S->flag == 0){             num++;         }else{         num +=GetListAtom(S->var.head) ;         }      }        } return num;}int main(){   char  str[20];   strcpy(str,"((a,b,c),d)");   GNode * S = createGT(str,0);   printGT(S);   printf("the atom count is %d",GetListAtom(S));    return 0;}