Java实现简单的计算器

Java实现简单的计算器``

用java语言写的一个简易计算器,实现了最基本的四则运算运算,支持小数点、括号、多位数运算。

首先附上效果图:
在这里插入图片描述

设计内容

界面由两个JTextField和20个JBotton组成,由构造方法实现ActionListener接口,按钮注册进行监听,并捕获按钮事件。
最终表达式显示在第一行文本,结果显示在第二行文本中。
因为计算器输入为中缀表达式,因此要将表达式转换为后缀表达式。result方法定义两个栈实现中缀表达式的求值。
express字符串存放的是以空格为分割符的中缀表达式,并以#作为结束符。result方法以空格分割表达式存放在字符串数组exps中。如果是数字直接压入operateNum栈,如果运算符比operateChara栈顶的优先级高则入栈,否则进行计算,并将结果压入operateNum栈,直至表达式运算结束。
最后定义五个异常:括号不匹配异常BracketsNotMatchException,除数为零异常DivisorIsZeroException,表达式错误异常ExpressFormatException,其他异常OtherException和取负错误异常SymbolErrorException。

以下为源代码

Experiment.class

import java.awt.*;
import java.awt.event.*;
import java.io.File;
import javax.script.*;
import javax.swing.*;
import java.io.IOException;
import java.io.*;
public class Experiment
{
	public static MyCalculator mc;
	public static void main(String[] args)
	{
		String express = new String();
		//File file = new File(".");
		mc = new MyCalculator();	
		mc.setVisible(true);
	}
}
class MyCalculator extends JFrame implements ActionListener
{
	//新建两个文本框
	JTextField text1 = new JTextField(null);
    JTextField text2 = new JTextField(null);
    //static boolean b=false;
    //定义上次操作
    public static final int INIT=0;//初始状态
    public static final int NUMBER=1;//数字
    public static final int OPERATOR=2;//运算符
    public static final int RIGHTBRACKET=3;//右括号
    public static final int LEFTBRACKET=4;//左括号
    public static final int DECIMALPOINT=5;//小数点
    public static final int MINUS=6;//取负
    public static final int CALCULATION=7;//计算
    static int lastOperation=INIT;
    //static boolean lastOperationIsOperator=false;//上一次操作是否是运算符
    //static boolean text2IsInit=true;//text2是否为初始
    //static boolean lastOperationIsBracket=false;//上一次操作是否是括号
    static boolean isError=false;//是否是异常结束
	static public String express=new String();//存放计算表达式
	static public int numOfBrackets=0;//用来判断括号匹配
    String op=new String("\u00F7\u00D7+-");//用来判断是否是运算符
	String num=new String("1234567890");//判断数字
	public MyCalculator() 
	{
		setTitle("计算器");//程序名称
		setSize(400,600);//界面大小
        Font f = new Font("黑体", Font.PLAIN, 40);//新建字体
        text1.setFont(f);
        text2.setFont(f);
        //设置右对齐
        text1.setHorizontalAlignment(JTextField.RIGHT);
        text2.setHorizontalAlignment(JTextField.RIGHT);
        //获取界面位置
        Container contentPane = getContentPane();
        contentPane.setLayout(new FlowLayout(FlowLayout.LEFT, 5, 5));
        contentPane.add(text1);
        contentPane.add(text2);
        text1.setPreferredSize(new Dimension(370, 70));
        text2.setPreferredSize(new Dimension(370, 75));
        text1.setEditable(false);
        text2.setEditable(false);
        text2.setText("0");
        //新建十六个按钮
        JButton[] button = new JButton[20];
        for(int i=0;i<20;i++)
        {
        	button[i]=new JButton();
        	button[i].setPreferredSize(new Dimension(90,75));
        	button[i].setBackground(Color.white);
        	button[i].setFont(f);
        	contentPane.add(button[i]);
        }
        this.setResizable(false);
        button[0].setText("+");
        button[1].setText("-");
        button[2].setText("(");
        button[3].setText(")");
        button[4].setText("\u00D7");//乘号
        button[5].setText("\u00F7");//除号
        //button[4].setText("*");
        //button[5].setText("/");
        button[6].setText("+/-");
        button[6].setFont(new Font("黑体", Font.PLAIN, 30));
        button[7].setText("C");
        button[7].setBackground(Color.ORANGE);
        button[8].setText("1");
        button[9].setText("2");
        button[10].setText("3");
        button[11].setText("=");
        button[12].setText("4");
        button[13].setText("5");
        button[14].setText("6");
        button[15].setText("0");
        button[16].setText("7");
        button[17].setText("8");
        button[18].setText("9");
        button[19].setText(".");
        for(int i=0;i<20;i++)//添加触发器
        	button[i].addActionListener(this);
	}
	public void actionPerformed(ActionEvent e)//处理触发器
	{
		if(e.getActionCommand()=="=")//处理表达式计算
		{
			String result=new String();
			if(lastOperation!=RIGHTBRACKET)
				express=express+" "+text2.getText();
			//System.out.println(express.trim());
			text1.setText(text1.getText()+text2.getText()+"=");
			try 
			{
				if(numOfBrackets!=0)
					throw new BracketsNotMatchException(new String("Bracket is not match"));
				else
				{
					result=new Calculation().result(express.trim()+" #");
					text2.setText(result);
				}
			}catch(DivisorIsZeroException err)//处理除数是零的异常
			{
				System.out.println(err.toString());
				text2.setText("error 02");
				isError=true;
				express=new String();
				numOfBrackets=0;
				lastOperation=INIT;
			}catch(ExpressFormatException err)//处理表达式不正确的异常
			{
				System.out.println(err.toString());
				text2.setText("error 03");
				isError=true;
				express=new String();
				numOfBrackets=0;
				lastOperation=INIT;
			}catch(BracketsNotMatchException error)//处理括号不匹配的异常
			{
				System.out.println(error.toString());
				text2.setText("error 01");
				isError=true;
				express=new String();
				numOfBrackets=0;
				lastOperation=INIT;
			}catch(OtherException error)
			{
				System.out.println(error.toString());
				text2.setText("error 05");
				isError=true;
				express=new String();
				numOfBrackets=0;
				lastOperation=INIT;
			}
			//System.out.println(express);
			//System.out.println(express.trim());
			express=new String();
		}
		else if(e.getActionCommand()=="C")//全部清零
		{
			text1.setText(null);
			text2.setText("0");
			express=new String();
			numOfBrackets=0;
			lastOperation=INIT;
			isError=false;
			//System.out.println(express.trim());
		}
		else if(e.getActionCommand()==".")//小数点操作
		{
			text2.setText(text2.getText()+e.getActionCommand());
			//System.out.println(express.trim());
			lastOperation=DECIMALPOINT;
		}
		else if(op.contains(e.getActionCommand()))//判断事件是运算符
		{
			if(lastOperation==INIT)
			{
				express=express+" "+text2.getText()+" "+e.getActionCommand();
				text1.setText(text2.getText());
				text2.setText(e.getActionCommand());
			}
			else
			{
				if(lastOperation!=RIGHTBRACKET)
					express=express+text2.getText()+" "+e.getActionCommand();
				else
					express=express+" "+e.getActionCommand();
				text1.setText(text1.getText()+text2.getText());
				text2.setText(e.getActionCommand());
			}			
			//System.out.println(express.trim());
			lastOperation=OPERATOR;
		}
		else if(e.getActionCommand().equals("+/-"))//取负号,只能数字取负,其他为异常
		{
			if(new Calculation().isDouble(text2.getText()))
			{
				if(text2.getText().charAt(0)=='-')
					text2.setText(text2.getText().substring(1, text2.getText().length()));				
				else
					text2.setText("-"+text2.getText());
			}
			else
			{
				try
				{
					throw new SymbolErrorException(text2.getText()+"不可取负");
				}catch(SymbolErrorException err)
				{
					System.out.println(err.toString());
					text2.setText("error 04");
					isError=true;
					express=new String();
					numOfBrackets=0;
					lastOperation=INIT;
				}
			}
			//System.out.println(express.trim());
			lastOperation=MINUS;
		}
		else if(e.getActionCommand().equals("("))//左括号
		{
			if(lastOperation==INIT)
			{
				text1.setText(null);
				text2.setText("(");
				express=express+"(";
				numOfBrackets++;
			}
			else
			{
				if(lastOperation==LEFTBRACKET)
					express=express+"( ";
				else
				{
					if(lastOperation==OPERATOR)
						express=express+" ";
					express=express+"( ";
				}
				text1.setText(text1.getText()+text2.getText());
				numOfBrackets++;
				text2.setText(e.getActionCommand());
			}
			//System.out.println(express.trim());
			lastOperation=LEFTBRACKET;
		}
		else if(e.getActionCommand().equals(")"))//右括号
		{
			express=express+" "+text2.getText();
			text1.setText(text1.getText()+text2.getText());
			text2.setText(")");
			numOfBrackets--;
			express=express+" )";
			//System.out.println(express.trim());
			lastOperation=RIGHTBRACKET;
		}
		//处理数字
		else
		{
			if(lastOperation==INIT||isError)
			{
				text1.setText(null);
				text2.setText(e.getActionCommand());
				if(isError)
					isError=false;
			}
			else
			{
				if(lastOperation==OPERATOR)//上一次是运算符
				{
					text1.setText(text1.getText()+text2.getText());
					text2.setText(e.getActionCommand());
				}
				else if(lastOperation==LEFTBRACKET)//上一次是括号
				{
					text1.setText(text1.getText()+text2.getText());
					text2.setText(e.getActionCommand());
				}
				else
					text2.setText(text2.getText()+e.getActionCommand());
			}
			//System.out.println(express.trim());
			lastOperation=NUMBER;
		}
	}
}

Calculation.class

import java.awt.List;
import java.io.*;
import java.util.ArrayList;
import java.util.Stack;
import java.util.regex.*;
public class Calculation 
{
	public String exp;
	public String[][] Table={ { " ", "+", "-", "×", "÷", "(", ")", "#" },//e代表表达式错误
		 	  				  { "+", ">", ">", "<", "<", "<", ">", ">" },
		 	  				  { "-", ">", ">", "<", "<", "<", ">", ">" },
		 	  				  { "×", ">", ">", ">", ">", "<", ">", ">" },
		 	  				  { "÷", ">", ">", ">", ">", "<", ">", ">" },
		 	  				  { "(", "<", "<", "<", "<", "<", "=", "e" },
		 	  				  { ")", ">", ">", ">", ">", "e", ">", ">" },
		 	  				  { "#", "<", "<", "<", "<", "<", "e", "=" } };
	public String result(String ss) throws DivisorIsZeroException,ExpressFormatException,OtherException
	{
		exp=ss;
		String[] exps=exp.split(" ");
		Stack<Double> operateNum=new Stack<Double>();//数字栈
		Stack<String>operateChara=new Stack<String>();//符号栈
		operateChara.push("#");
		int i=0;
		String str=exps[i++];
		while(!str.equals("#")||!operateChara.peek().equals("#"))
		{
			if(isDouble(str))
			{
				operateNum.push(Double.parseDouble(str));
				str=exps[i++];
			}
			else
			{
				if(str.length()!=1)
				{
					throw new ExpressFormatException(exp.substring(0,exp.length()-2).replaceAll(" ","")+"表达式错误");
				}
				else
				{
					switch(precede(str,operateChara.peek()))
					{
					case "<"://栈顶优先级低
						operateChara.push(str);
						str=exps[i++];
						break;
					case "="://脱括号
						operateChara.pop();
						str=exps[i++];
						break;
					case ">":
						String op=operateChara.pop();
						double num1=operateNum.pop();
						double num2=operateNum.pop();
						try{
							double num3=operata(num1,op,num2);//计算
							operateNum.push(num3);
						}catch(DivisorIsZeroException e)
						{
							throw e;
						}catch(OtherException e)
						{
							throw e;
						}
						break;
					case "e":
						throw new ExpressFormatException(exp.substring(0,exp.length()-2).replaceAll(" ","")+"表达式错误");
					}
				}

			}
			
		}
		//System.out.println(operateNum);
		//System.out.println(operateChara);
		return String.valueOf(operateNum.pop());
	}
	public double operata(double num1,String op,double num2) throws DivisorIsZeroException,OtherException
	{
			switch(op)
			{
			case "+":
				return num1+num2;
			case "-":
				return num2-num1;
			case "×":
				return num1*num2;
			case "÷":
				if(num1==0)
					throw new DivisorIsZeroException(exp.substring(0,exp.length()-2).replaceAll(" ","")+":除数为零");
				else
					return num2/num1;
			default:
					throw new OtherException(exp.substring(0,exp.length()-2).replaceAll(" ","")+":表达式错误");
			}
	}
	public String precede(String str1,String str2)
	{
		int i=0,j=0;
		for(i=0;i<8;i++)
			if(Table[0][i].equals(str1))
				break;
		for(j=0;j<8;j++)
			if(Table[j][0].equals(str2))
				break;
		return Table[j][i];
	}
	public boolean isDouble(String str) //判断是否是数字
	{
		if(str.equals("-"))
			return false;
		int i=str.indexOf(".");
		if(i==-1)
		{
			int j=0;
			if(str.charAt(0)=='-')
				j=1;
			for (;j<str.length();j++)
			{
				if (!Character.isDigit(str.charAt(j)))
				{
				return false;
				}
			}
			return true;
		}
		Pattern pattern = Pattern.compile("^[-\\+]?\\d*[.]\\d+$"); // 正则表达式
		return pattern.matcher(str).matches();
	}
	}

BracketsNotMatchException.class

public class BracketsNotMatchException extends Exception
{
	public BracketsNotMatchException() {}
	public BracketsNotMatchException(String str)
	{
		super(str);
	}
}

DivisorIsZeroException.class


public class DivisorIsZeroException extends Exception
{
	public DivisorIsZeroException() {}
	public DivisorIsZeroException(String str)
	{
		super(str);
	}
}

ExpressFormatException.class


public class ExpressFormatException extends Exception
{
	public ExpressFormatException() {}
	public ExpressFormatException(String str)
	{
		super(str);
	}

}

OtherException.class


public class OtherException extends Exception
{
	public OtherException() {}
	public OtherException(String str)
	{
		super(str);
	}
}

SymbolErrorException.class


public class SymbolErrorException extends Exception
{
	public SymbolErrorException() {}
	public SymbolErrorException(String str)
	{
		super(str);
	}
}

最后附上运行截图

在这里插入图片描述
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值