#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <ctype.h>
#include <math.h>
#define MAX(X, Y) (((X) > (Y))? (X) : (Y))
#define MIN(X, Y) (((X) < (Y))? (X) : (Y))
int compare_int(const void *a, const void *b){
  return *(long int*)b - *(long int*)a; // 大きい順
}
int compare_int_small(const void *a, const void *b){
  return *(long int*)a - *(long int*)b; // 小さい順
}
// 公約数
long long int gcd(long long int a, long long int b){
  if(b == 0){
    return a;
  }else{
    return gcd(b, a % b);
  }
}
// 最小公倍数 = a * b / 最大公約数
// 公倍数
long long int lcm(long long int a, long long int b){
  return a * b / gcd(a, b);
}

#define TRUE 1
#define FALSE 0
#define MAX_NUM 101
int top = 0;
int x = 0;
int *Stack = NULL;
char *S = NULL;

void initialize(){
  // Stackにはint型の数値のみ入れる。演算子は入ることがない
  Stack = (int *)malloc(MAX_NUM * sizeof(int));
  top = 0;
}

void finalize(){
  if(Stack != NULL){
    free(Stack);
    // 今まで確保していた領域を今後辿れないようにNULLとしておく
    Stack = NULL;
  }
}

int isEmpty(){
  if(top < 0){
    return TRUE;
  }else{
    return FALSE;
  }
}

int isFull(){
  if(top >= MAX_NUM - 1){
    return TRUE;
  }else{
    return FALSE;
  }
}

int push(int x){
  //  printf("push x = %d\n",x);
  if(isFull() != FALSE){
    //    fprintf(stderr, "pushしたのは%d top = %d\n", Stack[top], top);
    printf("Error! Overfllow\n");
    return 0;
  }else{
    top++;
    if(Stack != NULL){
      Stack[top] = x;
    }
    return 0;
  }
}

int  pop(){
  if(isEmpty() != FALSE){
    printf("Error! Underfllow\n");
    return 0;
  }else{
    top--;
    // return では取りだす値を返す
    //    fprintf(stderr, "popしたのは%d top = %d\n", Stack[top + 1], top);
    return Stack[top+1];
  }
}

// 10min
int main(void){
  char *ptr = NULL;
  int num = 0;
  long int ans = 0;
  initialize();

  // malloc 追加。追加したら2つ目のサンプルNGになった。4以降取り込まない
  // 10^6の数字は7Byte * 100
  // 演算子は1Byte * 100
  // 空白は 1 Byte * 100
  // 余裕を見て、倍の2000
  S = (char *)malloc(2000 * sizeof(char));
  // mallocでは欲しい個数(ここでは2000)とそのサイズ(ここではsizeof(char))をかけ算して確保したい領域を指定すると良い
  //  S = (char *)malloc(1000000001);
  if(S == NULL){
    printf("メモリが確保できません\n");
    exit(EXIT_FAILURE);
  }
  
  fgets(S, 2000, stdin);
  //　なぜかSに文字列が途中までしか取り込めてない。謎。<- fgetsのやり方がよくなかった
  //  printf("aa %s\n", S);
  ptr = strtok(S, " ");
  //  fprintf(stderr, "まずpushする %s\n", ptr);
  // 分解したけど、え、記号と数値わけるよね、、あ。演算子は3つだけ
  // 違う。文字列思ったように取得できてない。
  num = atoi(ptr);

  push(num);

  while(ptr != NULL){
    ptr = strtok(NULL, " ");
    if(ptr != NULL){
      //      printf("%s\n", ptr);
      // 演算子かそうでないかで処理をわける
      if(*ptr == '+' || *ptr == '-' || *ptr == '*'){
	long int a, b;

        //fprintf(stderr, "演算子！popする！ %c\n", *ptr);
	a = pop();
	b = pop();
	if(*ptr == '+'){
	  ans = b + a;
	}else if(*ptr == '-'){
	  ans = b - a;
	  //	  printf("b - a = %ld\n", ans);
	}else if(*ptr == '*'){
	  ans = b * a;
	}
	push(ans);
      }else{
	//fprintf(stderr, "数値！pushする！%d\n", atoi(ptr));
	num = atoi(ptr);
	push(num);
      }      
    }
  }
  // ansの位置を間違えてた。while文の中にあった
  ans = pop();
  free(S);

  // 一旦やってみたけど違う、、、
  printf("%ld\n", ans);
  finalize();

  return 0;
}

