Lex和Yacc实现句子识别

借助自动生成工具LEX和YACC完成句子识别。

词法分析:cifa.l

%{
/*
 * We now build a lexical analyzer to be used by a higher-level parser.
 */

#include "yufa.tab.h"	/* token codes from the parser */

#define LOOKUP 0 /* default - not a defined word type. */

int state; 

%}

%%

\n	{ state = LOOKUP; }

\.\n	{	state = LOOKUP;
		return 0; /* end of sentence */
	}

^verb	{ state = VERB; }
^adj	{ state = ADJECTIVE; }
^adv	{ state = ADVERB; }
^noun	{ state = NOUN; }
^prep	{ state = PREPOSITION; }
^pron	{ state = PRONOUN; }
^conj	{ state = CONJUNCTION; }

[a-zA-Z]+ { 
	     if(state != LOOKUP) {
	     	add_word(state, yytext);
	     } else {
		switch(lookup_word(yytext)) {
		case VERB:
		  return(VERB);
		case ADJECTIVE:
		  return(ADJECTIVE);
		case ADVERB:
		  return(ADVERB);
		case NOUN:
		  return(NOUN);
		case PREPOSITION:
		  return(PREPOSITION);
		case PRONOUN:
		  return(PRONOUN);
		case CONJUNCTION:
		  return(CONJUNCTION);
		default:
		  printf("%s:  don't recognize\n", yytext);
		  /* don't return, just ignore it */
		}
            }
          }

.	; 

%%
/* define a linked list of words and types */
struct word {
	char *word_name;
	int word_type;
	struct word *next;
};

struct word *word_list; /* first element in word list */

extern void *malloc();

int
add_word(int type, char *word)
{
	struct word *wp;	

	if(lookup_word(word) != LOOKUP) {
		printf("!!! warning: word %s already defined \n", word);
		return 0;
	}
	
	/* word not there, allocate a new entry and link it on the list */

	wp = (struct word *) malloc(sizeof(struct word));

	wp->next = word_list;

	/* have to copy the word itself as well */
	
	wp->word_name = (char *) malloc(strlen(word)+1);
	strcpy(wp->word_name, word);
	wp->word_type = type;
	word_list = wp;
	return 1;	/* it worked */
}

int
lookup_word(char *word)
{
	struct word *wp = word_list;

	/* search down the list looking for the word */
	for(; wp; wp = wp->next) {
		if(strcmp(wp->word_name, word) == 0)
			return wp->word_type;
	}

	return LOOKUP;	/* not found */
}

int yywrap()
{
    return 1;
}

yufa.y

%{
/*
 * A lexer for the basic grammar to use for recognizing english sentences.
 */
#include "lex.yy.c"
#include <stdio.h>
%}

%token NOUN PRONOUN VERB ADVERB ADJECTIVE PREPOSITION CONJUNCTION

%%
sentence: subject VERB object part_1	{ printf("Sentence is valid.\n"); }
	;

part_1:	ADVERB part_2
	|	object
	|
	;
part_2:	prepositional_phrase
	|
	;

subject:	NOUN
	|	PRONOUN
	;

object:	NOUN
	|	PRONOUN
	|	NOUN CONJUNCTION NOUN
	|	PRONOUN CONJUNCTION PRONOUN
	;
prepositional_phrase:	PREPOSITION NOUN;	
%%

extern FILE *yyin;


int main()
{
    yyparse();
    while(!feof(yyin)){
        yyparse();
    }

    return 0;
}   

yyerror(s)
char *s;
{
    fprintf(stderr,"%s\n",s);
}

运行结果:
在这里插入图片描述

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

言川_

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值