#include "mainwindow.h"
#include "ui_mainwindow.h"
#include <QMessageBox>
#include <map>
#include <stack>
#include <cmath>
#include <QClipboard>
#include <QTextBlock>
MainWindow::MainWindow(QWidget *parent) :
QMainWindow(parent),
ui(new Ui::MainWindow)
{
ui->setupUi(this);
waitForOperator = false;
on_action_3_triggered(false);
connectSlots();
setShortcutKeys();
}
MainWindow::~MainWindow()
{
delete ui;
}
void MainWindow::abortOperation()
{
setCurrentText("0");
waitForOperator = true;
statusBar()->showMessage(error,4000);
}
void MainWindow::specialOperatorClicked()
{
QPushButton *specialOperatorBtn = static_cast<QPushButton*>(sender());
QString value = specialOperatorBtn->text();
QString current = currentText();
if(waitForOperator)
{
log.append(current + '\n');
ui->textEdit->append(value);
waitForOperator = false;
}
else
{
if(current != "0")
setCurrentText(current + value);
else
setCurrentText(value);
}
}
void MainWindow::connectSlots()
{
QPushButton * digitBtns[10] = {
ui->digitBtn0, ui->digitBtn1, ui->digitBtn2, ui->digitBtn3,
ui->digitBtn4, ui->digitBtn5, ui->digitBtn6, ui->digitBtn7,
ui->digitBtn8, ui->digitBtn9
};
for (auto btn : digitBtns)
connect(btn,&QPushButton::clicked,this,&MainWindow::digitClicked);
QPushButton *operatorBtns[8] = {
ui->addBtn,ui->subtractionBtn,ui->multiplicationBtn,ui->divisionBtn,
ui->leftBracketBtn,ui->rightBracketBtn,ui->powBtn,ui->percentBtn
};
for (auto btn : operatorBtns)
connect(btn,&QPushButton::clicked,this,&MainWindow::operatorClicked);
QPushButton *specialOperatorBtns[5] = {
ui->sinBtn,ui->cosBtn,ui->tanBtn,ui->lnBtn,ui->lgBtn
};
for (auto btn : specialOperatorBtns)
connect(btn,&QPushButton::clicked,this,&MainWindow::specialOperatorClicked);
}
void MainWindow::digitClicked()
{
QPushButton *digiBtn = static_cast<QPushButton*>(sender());
QString value = digiBtn->text();
QString current = currentText();
if(current =="0" && value=="0")
return;
if(waitForOperator)
{
log.append(current + '\n');
ui->textEdit->append(value);
waitForOperator = false;
}
else
{
if(current != "0")
setCurrentText(current +value);
else
setCurrentText(value);
}
}
void MainWindow::on_clearBtn_clicked()
{
ui->textEdit->setText("0");
waitForOperator = true;
}
void MainWindow::on_clearAllBtn_clicked()
{
ui->textEdit->setText("0");
waitForOperator = true;
}
void MainWindow::on_equalBtn_clicked()
{
double result = 0.0;
try
{
result = compute(inToPost(currentText()));
}
catch(const char *er)
{
error = er;
abortOperation();
return;
}
log.append(currentText() + '\n');
ui->textEdit->append(QString::number(result));
waitForOperator = true;
}
void MainWindow::on_signBtn_clicked()
{
QString text = currentText();
QChar sign = text[text.size() - 1];
if(sign == '-')
{
text.remove(text.size() - 1,1);
}
else
{
text.append('-');
}
setCurrentText(text);
}
void MainWindow::operatorClicked()
{
QPushButton *clickedBtn = qobject_cast<QPushButton *>(sender());
QString clickedOperator = clickedBtn->text();
setCurrentText(currentText() + clickedOperator);
waitForOperator = false;
}
void MainWindow::on_pointBtn_clicked()
{
if(waitForOperator)
setCurrentText("0");
setCurrentText(currentText() + ".");
waitForOperator = false;
}
void MainWindow::setShortcutKeys()
{
Qt::Key key[27] = {
Qt::Key_0, Qt::Key_1, Qt::Key_2, Qt::Key_3,Qt::Key_4,
Qt::Key_5, Qt::Key_6, Qt::Key_7,Qt::Key_8,Qt::Key_9,
Qt::Key_Plus, Qt::Key_Minus, Qt::Key_Asterisk, Qt::Key_Slash,
Qt::Key_Enter,Qt::Key_Period,Qt::Key_Backspace,Qt::Key_M,
Qt::Key_ParenLeft,Qt::Key_ParenRight,Qt::Key_AsciiCircum,
Qt::Key_Percent,Qt::Key_S,Qt::Key_C,Qt::Key_T,Qt::Key_N,Qt::Key_G
};
QPushButton *btn[27] = {
ui->digitBtn0,ui->digitBtn1,ui->digitBtn2,ui->digitBtn3,ui->digitBtn4,
ui->digitBtn5,ui->digitBtn6,ui->digitBtn7,ui->digitBtn8,ui->digitBtn9,
ui->addBtn,ui->subtractionBtn,ui->multiplicationBtn,ui->divisionBtn,
ui->equalBtn,ui->pointBtn,ui->clearBtn,ui->signBtn,ui->leftBracketBtn,
ui->rightBracketBtn,ui->powBtn,ui->percentBtn,ui->sinBtn,ui->cosBtn,
ui->tanBtn,ui->lnBtn,ui->lgBtn
};
for(int i= 0;i<27;i++)
btn[i]->setShortcut(QKeySequence(key[i]));
ui->clearAllBtn->setShortcut(QKeySequence("Ctrl+Backspace"));
}
QString MainWindow::currentText()
{
QTextDocument *document = ui->textEdit->document();
QTextBlock block = document->lastBlock();
return block.text();
}
void MainWindow::setCurrentText(QString text)
{
QString allText = ui->textEdit->toPlainText();
int pos = allText.lastIndexOf('\n');
if(pos>=0)
allText.replace(allText.lastIndexOf('\n') + 1,allText.size(),text);
else
allText = text;
ui->textEdit->setText(allText);
}
QString MainWindow::inToPost(QString infix) throw(const char*)
{
std::stack<char>stack;
char current = 0;//读入的字符
QString postfix;//写入后缀表达式的字符串
std::map<char,int>priority;//运算符号优先级表
priority['+']=0;
priority['-']=0;
priority['*']=1;
priority['/']=1;
priority['^']=2;
priority['s']=3;
priority['c']=3;
priority['t']=3;
priority['n']=3;
priority['g']=3;
priority['%']=3;
for(int i=0;i<infix.length();++i)//逐个读取中缀表达式字符串中的字符
{
current = infix[i].toLatin1();
if(isdigit(current))//如果是数字直接输出
{
postfix.push_back(current);
continue;
}
switch(current)
{
case '+':
case '-':
case '*':
case '/':
case '^':
case '%':
if(infix[i-1] != ')')//如果运算符的前一项不是右括号则说明前一个数字输入完毕,用#表示前面几个字符组成一个数字
{
if(infix[i-1].isDigit())
postfix.push_back('#');
else if(infix[i-1] == '%')//什么也不做,跳出
infix.begin();
else
throw "表达式是非法的";
}
if(!stack.empty())//比较目前符号与栈顶符号优先级,低于则出栈,并输出字符串
{
char tempTop = stack.top();
while(tempTop!='('&&priority[current]<=priority[tempTop])
{
stack.pop();
postfix.push_back(tempTop);
if(stack.empty())
break;
tempTop=stack.top();
}
}
stack.push(current);//符号全部出栈或者遇到了'('或者大于栈顶符号的优先级,将新符号压入栈中
break;
case 's':
case 'c':
case 't':
if(i>0 && infix[i-1].isDigit())
throw "表达式非法";
if(!stack.empty())
{
char tempTop = stack.top();
while(tempTop != '('&&priority[current]<priority[tempTop])
{
stack.pop();
postfix.push_back(tempTop);
if(stack.empty())
break;
tem
没有合适的资源?快使用搜索试试~ 我知道了~
资源推荐
资源详情
资源评论
收起资源包目录
科学计算器实现.zip (6个子文件)
科学计算器实现
Calculator5.pro.user 23KB
mainwindow.h 1KB
mainwindow.cpp 13KB
Calculator5.pro 1KB
main.cpp 183B
mainwindow.ui 8KB
共 6 条
- 1
资源评论
一伦明悦
- 粉丝: 1439
- 资源: 12
上传资源 快速赚钱
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助
安全验证
文档复制为VIP权益,开通VIP直接复制
信息提交成功