表达式求值


表达式求值是程序设计中的一个经典问题,主要考察对栈的应用。
一般是形如:

int	expr(char* s){
   
}

入口参数 s 是待求表达式。我们就以s包含 “+, -, *, /, (, ), 10进制数非负整数”,表达式合法作为已知条件讨论这个问题。
返回值 即表达式的结果。

Step1. Token 提取

第一步,我们需要提取 Token。主要有以下两种方法:

正则表达式

C 中本身没有 RE 特性,但 Linux 中 regex.h 提供 RE 特性;
使用 RE ,优点是拓展性好,需要加什么操作很容易完成。

#include <sys/types.h>
#include <regex.h>
#include <stdlib.h>

enum {
   
    TK_NOTYPE = 256, TK_NUM,  
};

static struct rule {
   
    char *regex;
    int token_type;
} rules[] = {
   
    {
   " +", TK_NOTYPE},            			// spaces
    {
   "\\+", '+'},                 			// plus
	{
   "-", '-'},								// decrease
	{
   "\\*", '*'},							// multiply
	{
   "/", '/'},								// divide
	{
   "\\(",'('},							// Left parenthesis
	{
   "\\)",')'},							// Right parenthesis
	{
   "([1-9][0-9]{1,31})|[0-9]",TK_NUM},	// Decimal integer	
};

#define NR_REGEX (sizeof(rules) / sizeof(rules[0]) )

static regex_t re[NR_REGEX];

/* Rules are used for many times.
 * Therefore we compile them only once before any usage.
 */
void init_regex() {
   
    int i;
    char error_msg[128];
    int ret;

    for (i = 0; i < NR_REGEX; i ++) {
   
        ret = regcomp(&re[i], rules[i].regex, REG_EXTENDED);
        if (ret != 0) 
            regerror(ret, &re[i], error_msg, 128);
    }
}

typedef struct token {
   
    int type;
    char str[32];
} Token;

Token tokens[10000];
int nr_token;

static bool make_token(char *e) {
   
    int position = 0;
    int i;
    regmatch_t pmatch;

    nr_token = 0;

    while (e[position] != '\0') {
   
        /* Try all rules one by one. */
        for (i = 0; i < NR_REGEX; i ++) {
   
            if (regexec(&re[i], e + position, 1, &pmatch, 0) == 0 && pmatch.rm_so == 0) {
   
                char *substr_start = e + position;
                int substr_len = pmatch.rm_eo;
                
                position += substr_len;
                switch (rules[i].token_type) {
   
					case '+':
					case '-':
					case '*':
					case '/':
					case '(':
					case ')':
					case TK_NUM:
					{
   
						tokens[nr_token].type = rules[i].token_type;
						strncpy(tokens[nr_token].str, substr_start, substr_len);
						tokens
  • 1
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值