1. 程式人生 > >[資料結構]--PTA求字首表示式的值

[資料結構]--PTA求字首表示式的值

算術表示式有字首表示法、中綴表示法和字尾表示法等形式。字首表示式指二元運算子位於兩個運算數之前,例如2+3*(7-4)+8/4的字首表示式是:+ + 2 * 3 - 7 4 / 8 4。請設計程式計算字首表示式的結果值。
輸入格式:
輸入在一行內給出不超過30個字元的字首表示式,只包含+、-、*、\以及運算數,不同物件(運算數、運算子號)之間以空格分隔。
輸出格式:
輸出字首表示式的運算結果,保留小數點後1位,或錯誤資訊ERROR。
輸入樣例:
+ + 2 * 3 - 7 4 / 8 4
輸出樣例:
13.0
————————————
其實如果只是對於一位數就非常簡單直接從後向前掃描即可,但是如果要滿足兩位數可以進棧,就有一點麻煩,需要判斷有幾位,再將其入棧,我這裡用的是鏈棧,其實可以用順序棧,就當做一個小小練習吧~
從後向前掃描,如果不是空格就要進行判斷,判斷有幾位,如果是兩位就存入臨時的陣列中,再利用反轉(要吐槽這裡不能使用庫函式的strrev(),只好再重新寫一個了。。。)和atof()函式將char[]轉換為double型別,如果是一位直接入棧,如果是運算子就讓兩個數出棧,出棧前要判斷是否為空(這裡很容易出現錯誤的情況,如果空直接錯誤就退出就好~),之後直接進行運算,記得將運算結果入棧。
最後輸出判斷top的next是不是空就好,就是保證最後鏈棧只有一個元素,說明正確,其他情況不正確。

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#define N 30
//定義鏈棧
typedef struct snode
{
    double data;
    struct snode *next;
}StackNode,*LinkStack;
//置空棧
LinkStack top=NULL;
//入棧
LinkStack Push_LinkStack(double x)
{
    StackNode *p;
    p=(StackNode *)malloc(sizeof(StackNode));
    p->data=x;
    p->next=top;
    top=p;
    return
top; } //出棧 double Pop_LinkStack() { double x; StackNode *p; if(top==NULL) return 0; else{ x=top->data; p=top; top=top->next; free(p); return x; } } //計算 double calcul(double a,double b,char c) { switch(c) { case '+': return a+b; case
'-': return b-a; case '*': return a*b; case '/': return b/a; default : return 0; } } //判棧空 int Empty_SeqStack() { if(top==NULL) return 1; else return 0; } //字串反轉 char *revstr(char *str, int len) { char *start = str; char *end = str + len - 1; char ch; if (str != NULL) { while (start < end) { ch = *start; *start++ = *end; *end-- = ch; } } return str; } int main() { char s[N]; gets(s); char temp[N]; char *strrevtemp; int i; int j=-1; double a,b,result; for(i=strlen(s)-1;i>=0;i--) { if(s[i]!=' ') { if(s[i-1]==' '||i==0)//判斷下一位是不是空格 { if(s[i]>='0'&&s[i]<='9') { Push_LinkStack(s[i]-'0'); i--; } else if(s[i]=='+'||s[i]=='-'||s[i]=='*'||s[i]=='/'){ if(!Empty_SeqStack()) a=Pop_LinkStack(); else{ printf("ERROR"); return 0; } if(!Empty_SeqStack()) b=Pop_LinkStack(); else{ printf("ERROR"); return 0; } if(s[i]=='/'&&b==0) { printf("ERROR"); return 0; } result=calcul(b,a,s[i]); Push_LinkStack(result); } else{ printf("ERROR"); return 0; } } else{ j=0; while(s[i]!=' '&&i>=0) temp[j++]=s[i--]; temp[j]='\0'; if(strlen(temp)<=1) { printf("ERROR"); return 0; } strrevtemp=revstr(temp,strlen(temp)); Push_LinkStack(atof(strrevtemp)); i++; } } } if(top!=NULL) printf("%.1lf",top->data); else printf("ERROR"); return 0; }