趣味编程:从字符串中提取信息(C语言版本)

大概就是如下一个字符串

cpu-3.0g--color-red-green-black--price-5000-8000--weight-'3-'--keywords-'levi''s'

要拆分成如下格式

{ "cpu", "3.0g" },

{ "color", "red", "green", "black" },

{ "price", "5000", "8000" },

{ "weight", "3-" },

{ "keywords", "levi's" }, 

原题目要求地址如下

http://www.cnblogs.com/JeffreyZhao/archive/2009/10/12/code-for-fun-tokenizer.html 

老赵的C#语言版本如下 

http://www.cnblogs.com/JeffreyZhao/archive/2009/10/21/code-for-fun-tokenizer-answer-1.html

最近学C语言, 我翻译成c语言的了,在dev-c++4.9.9.2编译运行通过,代码如下


代码
#include  < stdio.h >

#define  MAX_TOKEN_LEN  20

const  e_arg_invalid  =   - 1 ;
const  e_token_overfllow  =   - 2 ;
const  s_ok  =   0 ;
int  last_error  =   0 ;

void *  p1( char  ch);
void *  p2( char  ch);
void *  p3( char  ch);
void *  p4( char  ch);
void *  p5( char  ch);

typedef  void *  ( * fn_parse)( char  c);
void  aggregate(fn_parse parse,  char *  input){
     
while ( * input  !=   ' /0 ' ){
        
if (last_error  ==  s_ok){
            parse  =  (fn_parse)( * parse)( * input);
            input ++ ;
        } else {
            printf( " ocurr an error:%d " , last_error);
            
break ;
        }
     }
}

struct  token{
       
char *  inner_token;
       
int  index;
};
void  append( struct  token *  t,  char  ch){
     
if (t  ->  index ++   >  MAX_TOKEN_LEN){
         last_error  =  e_token_overfllow;
         
return ;
     }
     t  ->  inner_token[ t  ->  index ]  =  ch;
}
struct  token *  current_token;
void  reset(){
   current_token  =  ( struct  token * )malloc( sizeof ( struct  token));
   current_token  ->  inner_token  =  ( char * )calloc(MAX_TOKEN_LEN,  sizeof ( char ));
   current_token  ->  index  =   - 1 ;
}

struct  token_group{
       
struct  token **  tokens;
       
int  index;
};
void  append2( struct  token_group *  g,  struct  token *  t){
   
struct  token *  tt;
   
   
if ( g  ->  index ++   >  MAX_TOKEN_LEN ){
      last_error  =  e_token_overfllow;
      
return ;
   }
   tt  =  g  ->  tokens[ 0 ];
   g  ->  tokens[g  ->  index]  =  t;
}            
struct  token_group *  current_group;
void  reset2(){
   current_group  =  ( struct  token_group * )malloc( sizeof ( struct  token_group));
   current_group  ->  index  =   - 1 ;
   current_group  ->  tokens  =  ( struct  token ** )calloc(MAX_TOKEN_LEN,  sizeof ( struct  token ** ));
}

struct  parse_result{
   
struct  token_group **  groups;
   
int  index;

};
void  append3( struct  parse_result *  ret, struct  token_group *  g){
  
if ( ret  ->  index ++   >  MAX_TOKEN_LEN ){
      last_error  =  e_token_overfllow;
      
return ;
  }
  ret  ->  groups[ret  ->  index]  =  g;
}            
struct  parse_result *  result;
void  reset3(){
   result  =  ( struct  parse_result * )malloc( sizeof ( struct  parse_result));
   result  ->  index  =   - 1 ;
   result  ->  groups  =  ( struct  token_group ** )calloc(MAX_TOKEN_LEN,  sizeof ( struct  token_group ** ));
}

void *  p1( char  ch){
   
if  (ch  ==   ' - ' ){
      last_error  =  e_arg_invalid;
      
return  NULL;
   }
   
if  (ch  ==   ' / '' ){
       return  p5;
   }
   
else {
      append(current_token,  ch );
      
return  p4;
   }
}

void *  p2( char  ch){
   
if  (ch  ==   ' - ' ){
      append3(result, current_group );
      reset2();
      
return  p1;
   }
   
else   if  (ch  ==   ' / '' ){
       return  p5;
   }
   
else {
      append(current_token, ch);
      
return  p4;
   }
}
void *  p3( char  ch){
   
if  (ch  ==   ' / '' ){
      append(current_token,  ' / '' );
       return  p5;
   }
   
else   if  (ch  ==   ' - ' ){
      append2(current_group, current_token);
      reset();
      
return  p2;
   }
   
else {
      last_error  =  e_arg_invalid;
      
return  NULL;
   }
}
void *  p4( char  ch){
   
if  (ch  ==   ' / '' ){
      last_error  =  e_arg_invalid;
      
return  NULL;
   }
   
if  (ch  ==   ' - ' ){
      append2(current_group, current_token);
      reset();
      
return  p2;
   }
   
else {
      append(current_token, ch);
      
return  p4;
   }
}
void *  p5( char  ch){
   
if  (ch  ==   ' / '' ){
       return  p3;
   }
   
else  {
      append(current_token, ch);
      
return  p5;
   }
}

void  test_parse(){
   
int  i, j;
   
struct  token_group *  group;
   
struct  token *  t;
   
   reset();
   reset2();
   reset3();
   
   
char *  str  =   " cpu-3.0g--color-red-green-black--price-5000-8000--weight-'3-'--keywords-'levi''s' " ;
   aggregate( & p1, str);
   append2(current_group, current_token);
   append3(result, current_group );

   
for (i  =   0 ; i  <=  result  ->  index; i ++ ){
      group  =  result  ->  groups[i];
      printf( " group:%d/r/n " , i);
      
for (j  =   0 ; j  <=  group  ->  index; j ++ ){
         t  =  group  ->  tokens[j];
         printf( " /ttoken:%d-%s/r/n " , j, t  ->  inner_token);
      }      
   }
   
   
for (i  =   0 ; i  <=  result  ->  index; i ++ ){
      group  =  result  ->  groups[i];
      
for (j  =   0 ; j  <=  group  ->  index; j ++ ){
         t  =  group  ->  tokens[j];
         free(t  ->  inner_token);
         free(t);
      }
      free(group  ->  tokens);
      free(group);
   }
   free(result  ->  groups);
}

int  main( void )
{
    
int  key;
    test_parse();
    scanf( " %d " , & key);        
}

 

运行结果如下:

group:0

        token:0-cpu

        token:1-3.0g

group:1

        token:0-color

        token:1-red

        token:2-green

        token:3-black

group:2

        token:0-price

        token:1-5000

        token:2-8000

group:3

        token:0-weight

        token:1-3-

group:4

        token:0-keywords

        token:1-levi's 

 

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值