⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 bianyi .txt

📁 一些编译原理词法分析和语法分析的源程序,比较深,因为编译本身比较难,所以适合学习编译有一定时间的人学习
💻 TXT
📖 第 1 页 / 共 3 页
字号:
 switch(type)
 {
 case INTEGER: get_exp((int*)result,index);
            return 1;
 default:    return 0;
 }

}

int CExecutable::Ai_GetVarNo(char *name,int *result,int type)
{
 switch(type)
 {
 case INTEGER:
  {
   if(m_intArray.size()==0)
    return 0;
   for(int i=0;i<=m_intArray.size()-1;i++)
    if(!strcmp(name,m_intArray.at(i).name))
     *result=i;
    return 1;
  }
 default: return 0;
 }

}
void CExecutable::get_exp(int *result,int *index)
{
    if (!*m_tokens.at(*index).token)
 {
        serror(2);
        return;
    }
    level2(result,index);
    
 }


/* add or subtract two terms */
void CExecutable::level2(int *result,int *index)
{
    register char op;
    int hold;
    level3(result,index);
    while ((op = *m_tokens.at(*index).token) =='+' || op == '-')  
 {
        (*index)++;
        level3(&hold,index);
        arith(op,result,&hold);
    }
}


/* multiply or divide two factors */
void CExecutable::level3(int *result,int *index)
{
 register char op;
    int hold;
    level4(result,index);
    while ((op = *m_tokens.at(*index).token) == '*' || op == '/' || op == '%')  
 {
        (*index)++;
        level3(&hold,index);
        arith(op,result,&hold);
    }
}


/* process integer exponent */
void CExecutable::level4(int *result,int *index)
{
 register char op;
    int hold;
    level5(result,index);
    if ((op = *m_tokens.at(*index).token) == '^') 
 {
        (*index)++;
        level5(&hold,index);
        arith(op,result,&hold);
    }
}
              

/* is a unary + or - */              
void CExecutable::level5(int *result,int *index)
{
    register char op;
    op = 0;
    if ((m_tokens.at(*index).token_type==DELIMITER) && 
  *m_tokens.at(*index).token == '+' || 
  *m_tokens.at(*index).token == '-' )  
 {
        op = *m_tokens.at(*index).token;
        (*index)++;
    }
    level6(result,index);
    if (op)  
  if(op=='-')
   *result=-(*result);
}
                

/* process parenthesized expression */                
void CExecutable::level6(int *result,int *index)
{
 if ((*m_tokens.at(*index).token == '(') && (m_tokens.at(*index).token_type == DELIMITER))  
 {
        (*index)++;
        level2(result,index);
        if (*m_tokens.at(*index).token!=')')
            serror(1);
        (*index)++;
    }
    else 
        primitive(result,index);
}

/* find value of number or variable */
void CExecutable::primitive(int *result,int *index)
{
 int token_type=m_tokens.at(*index).token_type;
    if(Isvar(m_tokens.at(*index).token))  
  token_type=VARIABLE;
    switch (token_type)  {
        case VARIABLE:
            find_var(m_tokens.at(*index).token,result);
            (*index)++;
            return;
        case NUMBER:
            *result = atoi(m_tokens.at(*index).token);
            (*index)++;
            return;
        default:
            serror(0);
    }
}

int CExecutable::find_var(char *var_name,void *value)
{
 for(int i=0;i<=m_intArray.size()-1;i++)
  if(!strcmp(var_name,m_intArray.at(i).name))
  {
   int *int_value=(int *)value;
   *int_value=m_intArray.at(i).value;
   return 1;
  }
    return 0;
}

int CExecutable::Isvar(char *name)
{
 if(m_intArray.size()==0)
  return 0;
 for(int i=0;i<=m_intArray.size()-1;i++)
  if(!strcmp(name,m_intArray.at(i).name))
        return INTEGER;
 return 0;
}

/* perform the specified arithmetic */
void CExecutable::arith(char o,int *r,int *h)
{
    /*register*/ int t,ex;
    
    switch (o)  {
        case '-':
            *r = *r-*h;
            break;
        case '+':
            *r = *r+*h;
            break;
        case '*':
            *r = *r**h;
            break;
        case '/':
            *r = (*r)/(*h);
            break;
        case '%':
            *r = (*r)%(*h);
            break;
        case '^':
            ex = *r;
            if (*h==0)  {
                *r = 1;
                break;
            }
            for (t=*h-1;t>0;--t)  *r=(*r)*ex;
            break;
    }
}

int CExecutable::look_up(char *c)
{
 if(strcmp(c,"print")==0)
  return PRINT;
    if(strcmp(c,"Integer")==0)
  return INTEGER;
 if(strcmp(c,"Dim")==0)
  return DIM;
 if(strcmp(c,"As")==0)
  return AS;
    return 0;
}

void CExecutable::serror(int error)
{
 char *e[] = {
        "syntax error",
        "unbalanced parentheses",
        "no expression present",
        "equal sign expected",
        "not a variable",
        "label table full",
        "duplicate label",
        "undefined label",
        "THEN expected",
        "TO expected",
        "too many nested FOR loops",
        "NEXT without FOR",
        "too many nested GOSUB",
        "RETURN without GOSUB"
    };

    printf ("%s ",e[error]);
}

 
 
---------------------------
接着昨天的词法分析器,语法分析主要是将从词法分析那里得来的记号构成一棵语法树。这次我将作案的词法分析部分的代码稍作了修改,让他更适合语法分析器。我使用的是自下而上的分析法,针对算符优先文法的产生式构造语法树。
        以下的代码只支持7种节点——加减乘除,标识符,数字,表达式。想要加入其他节点,在opprio数组中加入优先级。
////////////////////////////////Parse.h//////////////////////////////////
#ifndef _PARSE_H_
#define _PARSE_H_
#include "lexical.h"

//算法优先文法中优先级关系枚举
typedef enum {LS, GT, EQ,UN} Priority;
//移进归约算法中使用到的栈节点结构(双向链表)
typedef struct _pstacktoken
{
    LexToken *ptoken;
    struct _pstacktoken *pr;
    struct _pstacktoken *nt;
    struct _pstacktoken *child;
}PStackToken;
void PStackPush(LexToken *t);
LexToken* PStackPop();

//产生式链表节点结构(单向链表)
typedef struct _generator {LexTokenType *gen; int size; struct _generator *nt;} Generator;
PStackToken* Parse(char *Source);

#endif//_PARSE_H
////////////////////////////////////////Parse.c/////////////////////////////
#include "Parse.h"
#include <malloc.h>
#include <string.h>
#include <stdarg.h>
#include <stdio.h>

//各个运算符之间的优先级定义
#define OPNUM 7
Priority opprio[OPNUM][OPNUM]={
    {GT,GT,LS,LS,LS,LS,GT,},
    {GT,GT,LS,LS,LS,LS,GT,},
    {GT,GT,GT,GT,LS,LS,GT,},
    {GT,GT,GT,GT,LS,LS,GT,},
    {GT,GT,GT,GT,UN,UN,GT,},
    {GT,GT,GT,GT,UN,UN,GT,},
    {LS,LS,LS,LS,LS,LS,EQ,},
};
Priority PrioCmp(LexTokenType first, LexTokenType second)//这段函数被优化代码替代
{
    if (first>=OPNUM || second>=OPNUM)
        return UN;
    return opprio[first][second];
}


PStackToken *PSbot = NULL;//栈底指针
PStackToken *PStop = NULL;//栈顶指针
//int PSnum = 0;//栈元素个数
void PStackPush(LexToken *t)
{
    static int size = sizeof(PStackToken);
    PStackToken *p = (PStackToken*)malloc(size);//不检查合法性
    p->ptoken = t;//不对t的合法性检查
    if (!PSbot)//第一个节点
    {
        PSbot = PStop = p;
        p->pr = p->nt = NULL;
    }
    else
    {
        PStop->nt = p;
        p->pr = PStop;
        p->nt = NULL;
        PStop = p;
    }
    p->child = NULL;
}
LexToken* PStackPop()
{
    LexToken *p = PStop->ptoken;
    PStackToken *last = PStop;
    if (PStop==NULL)//如果已无元素可弹出
        return NULL;
    PStop = PStop->pr;
    PStop->nt = NULL;
    free(last);
    return p;
}


Generator *GLhead = NULL;
Generator *GLend = NULL;
void AddGen(int num, ...)
{
    static int sizegen = sizeof(Generator);
    static int sizetype = sizeof(LexTokenType);
    Generator *pGen = (Generator*)malloc(sizegen);
    int i;
    va_list pArgList;
    va_start (pArgList, num);
    pGen->size = num;
    pGen->gen = (LexTokenType*)malloc(sizetype);
    pGen->nt = NULL;
    for (i=0; i<num; i++)
    {
        pGen->gen[i] = va_arg(pArgList, LexTokenType);
    }
    va_end (pArgList);
    if (!GLhead)
    {
        GLhead = pGen;
        GLend = pGen;
    }
    else
    {
        GLend->nt = pGen;
        GLend = pGen;
    }
}
void InitGenerator()
{
    AddGen(3,EXPRESSION,PLUS,EXPRESSION);
    AddGen(3,EXPRESSION,MINUS,EXPRESSION);
    AddGen(3,EXPRESSION,MULTI,EXPRESSION);
    AddGen(3,EXPRESSION,DIVIDE,EXPRESSION);
    AddGen(1,IDENTI);
    AddGen(1,NUMBER);
}


PStackToken *PSnow = NULL;
LexToken *gettoken = NULL;
PStackToken *PStail = NULL;
PStackToken* Parse(char *Source)
{
    static int sizeLexToken = sizeof(LexToken);
    Generator *pgennow = NULL;//查找产生式时使用
    LexToken *pstart = (LexToken*)malloc(sizeLexToken);//不检查合法性
    Priority PrioCmpRlt = UN;
    InitGenerator();
    pstart->strName = NULL;
    pstart->type = JINGHAO;
    PStackPush(pstart);
    while (gettoken = GetNextToken(Source))
    {
        if (PStop->ptoken->type == EXPRESSION)
        {
            PSnow = PStop->pr;
        }
        else
        {
            PSnow = PStop;
        }
        while ((PrioCmpRlt = PrioCmp(PSnow->ptoken->type, gettoken->type)) == GT)//PSnow未作检查,找到最左素短语尾部
        {
            while (1)//查找最左素短语头部
            {
                PStail = PSnow;
                PSnow = PSnow->pr;
                if (PSnow->ptoken->type == EXPRESSION)//未做合法性检查
                {
                    PSnow = PSnow->pr;
                }
                if (PrioCmp(PSnow->ptoken->type, PStail->ptoken->type) == LS)
                {//归约
                    int i;
                    PStackToken *pst;
                    pgennow = GLhead;
                    while(pgennow)
                    {
                        pst = PSnow->nt;
                        for (i=0; i<pgennow->size && pst!=PStop->nt; i++)
                        {
                            if (pst->ptoken->type != pgennow->gen[i])
                                break;
                            pst = pst->nt;
                        }
                        if(i==pgennow->size && pst==PStop->nt)//找到了产生式
                        {
                            LexToken *pExp = (LexToken*)malloc(sizeof(LexToken));
                            pst = PSnow->nt;
                            pExp->strName = NULL;
                            pExp->type = EXPRESSION;
                            PStop = PSnow;
                            PStackPush(pExp);//插入一个Expression节点
                            PStop->child = pst;//为该节点建立树
                            pst->pr = NULL;
                            break;
                        }
                        pgennow = pgennow->nt;
                    }
                    //在这里考虑无法归约的情况
                }
                break;
            }
//            break;
        }
        if (PrioCmpRlt == LS)
        {
            PStackPush(gettoken);
            continue;
        }
        if (PrioCmpRlt == EQ)
        {
            if (PSnow->ptoken->type == JINGHAO)
            {
                //识别
                break;
            }
            else
            {
                PStackPush(gettoken);
                continue;
            }
        }
    }
    return PStop;
}
-------------------------------
C++编写的词法分析程序

这个是我编译原理课程设计的 内容,呵呵 我遍的是词法分析,基本的功能都能够实现,如词法分析,词法查错,删除无实质意义的字符等,不懂编译的就不用看了,编译真的很难!!!不过好象没什么用

#include<iostream.h>
#include<ctype.h>
#include<string.h>
#include<stdio.h>
#include<stdlib.h>

#define ID 6    
#define INT 7
#define LT 8
#define LE 9
#define EQ 10
#define NE 11
#define GT 12
#define GE 13
#define FZ 14        
#define DEV 15

 

struct KeyWord        //关键字结构
{
 char *word;
 int id;
};

KeyWord keyword[]={    //关键字数组
 {"begin",1},
 {"end",2},
 {"if",3},
 {"then",4},
 {"else",5},
 {"integer",16},
 {"float",17},
 {"double",18}
};


char TOKEN[20];
int graphnum=1;     //记录错误所在的位置


int lookup(char *string);
void out(int id ,char *string);
void report_error(char ERR_CH);
bool isalpha(char c) ;
bool isdigit(char c);
bool isalnum(char c);
void scanner_example(FILE *fp);

 

int lookup(char *string)
{
 for(int i=0;i<sizeof(keyword)/sizeof(KeyWord);i++)
 {
  if(strcmp(string,keyword[i].word)==0)
   return keyword[i].id;
 }
 return 0;
}

void out(int id ,char *string)
{
 printf("(%d,%s)\n",id,string);;
}

void report_error(char ERR_CH)        //错误处理程序
{
 printf("undeclared identifler %c int %d line!\n",ERR_CH,graphnum);
}

bool isalpha(char c)   
{
 if( (c>='a'&&c<='z') || (c>='A'&&c<='Z') )
  return true;
 else
  return false;
}

bool isdigit(char c)
{
 if(c>='0'&&c<='9')
  return true;
 else
  return false;
}

bool isalnum(char c)
{
 if( isalpha(c) || isdigit(c) )
  return true;
 else
  return false;
}

void scanner_example(FILE *fp)
{
 char ch;
 int i,c;
 
 while(!feof(fp))
 {

 ch=fgetc(fp);
 if(isalpha(ch))  
 {
  TOKEN[0]=ch;
  ch=fgetc(fp);
  i=1;
  while(isalnum(ch))  
  {
   TOKEN[i]=ch;
   i++;
   ch=fgetc(fp);
  }
  TOKEN[i]='\0';
  fseek(fp,-1,1);
  c=lookup(TOKEN);
  if(c==0) 
   out (ID,TOKEN);
  else
   out (c," ");
 }
 else if(isdigit(ch))
 {
  TOKEN[0]=ch;
  ch=fgetc(fp);
  i=1;
  while(isdigit(ch))
  {
   TOKEN[i]=ch;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -