#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void eat_space(char *s)
{
int i = 0, j = 0;
while ((s[i] = s[j++]) != '\0')
if (s[i] != ' ')
i++;
}
double expr(char *);
char *extract(char *s, int *index)
{
int cnt = 0;
int start_pos = *index, len;
char *sub_expr = NULL;
while (s[*index] != '\0')
{
switch (s[*index])
{
case '(':
cnt++;
break;
case ')':
cnt--;
if (cnt == 0)
{
len = *index - start_pos - 1;
printf("start = %d, *index = %d, len = %d\n",
start_pos, *index, len);
sub_expr = malloc(len + 1);
if (NULL == sub_expr)
{
printf("内存不足!\n");
exit(1);
}
memcpy(sub_expr, s + start_pos + 1, len);
sub_expr[len] = '\0';
return sub_expr;
}
break;
}
*index += 1;
}
printf("括号不匹配, 跑出整个表达式, 表达式错误!\n");
exit(1);
}
double number(char *s, int *index)
{
double val = 0.0;
char *subexpr = NULL;
if (s[*index] == '(')
{
subexpr = extract(s, index);
val = expr(subexpr);
printf("subexpr = %s, val = %lf\n", subexpr, val);
free(subexpr);
*index += 1;
return val;
}
if (!strchr("0123456789", s[*index]))
goto err0;
while ('0' <= s[*index] && s[*index] <= '9')
{
val *= 10;
val += s[*index] - '0';
*index += 1;
}
if (s[*index] != '.')
return val;
if (!strchr("0123456789", s[(*index) + 1]))
goto err0;
double factor = 1.0;
while ('0' <= s[++*index] && s[*index] <= '9')
{
factor *= 0.1;
val += factor * (s[*index] - '0');
}
return val;
err0:
printf("表达式中包含不合法字符!\n");
exit(1);
}
double term(char *s, int *index)
{
double ret = 0.0;
ret = number(s, index);
while (s[*index] == '*' || s[*index] == '/')
{
if (s[*index] == '*')
{
*index += 1;
ret *= number(s, index);
}
if (s[*index] == '/')
{
*index += 1;
ret /= number(s, index);
}
}
return ret;
}
double expr(char *s)
{
double ret = 0.0;
int index = 0;
ret = term(s, &index);
while (1)
{
switch (s[index++])
{
case '+':
ret += term(s, &index);
break;
case '-':
ret -= term(s, &index);
break;
case '\0':
return ret;
break;
default:
goto err0;
break;
}
}
err0:
printf("错误的表达式.\n");
exit(1);
}
int main(void)
{
char s[1024];
printf("pls input a expression: ");
gets(s);
eat_space(s);
puts(s);
printf("------------\n");
printf("the result of this expression is: %lf\n", expr(s));
return 0;
}