C#实现eval 进行四则运算
昨天在园子里看到有园友,写了相同标题的一篇文章。重点讲的是中缀表达式转换为后缀表达式的算法,但是实现的四则运算 有bug。其实我没看之前也不懂什么是 中缀和后缀表达式,之前有用过js eval 内置函数,后边一想貌似C#中是没有这样的一个函数,加上自己也没事,就试着自己写了下 这个所谓的四则运算。
我没有研究计算机是怎么来进行四则运算的,我只是按自己的想法来实现 对 6-2*(5-3)+6/2*(6-3+3)/2 这样一个随意组合的四则运算表达式。
我的思路是样的:
<1> 先递归把表达式中的括号中的表达式给算出来,然后将值将之替换
#region 计算括号中的表达式
/// <summary>
/// 获取括号中的计算表达式
/// (递归)
/// </summary>
/// <param name="express"></param>
public void GetBraceExpress(ref string express)
{
int leftBraceMaxIndex = -;
IList<int> rightBraceMinIndexs = new List<int>();
for (int i = ; i < express.Length; i++)
{
if (express[i].ToString() == "(")
{
leftBraceMaxIndex = i;
}
if (express[i].ToString() == ")")
{
rightBraceMinIndexs.Add(i);
}
}
if (leftBraceMaxIndex != - && rightBraceMinIndexs.Count > )
{
int rightBraceIndex = ;
foreach (var item in rightBraceMinIndexs)
{
if (item > leftBraceMaxIndex)
{
rightBraceIndex = item;
break;
}
} string braceExpress = express.Substring(leftBraceMaxIndex, rightBraceIndex - leftBraceMaxIndex + );
double result = CalcExpress(braceExpress.TrimStart('(').TrimEnd(')')); //计算()中的表达式
express = express.Replace(braceExpress, result.ToString()); //结果替换 ()表达式
if (express.IndexOf("(") != - && express.IndexOf(")") != -)
{
GetBraceExpress(ref express);
return;
}
}
}
#endregion #region 计算表达式
/// <summary>
/// 计算表达式
/// </summary>
/// <param name="express">表达式</param>
/// <returns>表达式结果</returns>
public double CalcExpress(string express)
{
List<double> numbers = new List<double>(); //表达式中的数字
List<char> operaters = new List<char>(); //表达式中的操作符
int tempIndex = ;
for (int i = ; i < express.Length; i++)
{
if (!char.IsNumber(express[i]) && char.IsNumber(express[i - ]) && i > )
{
if (tempIndex != )
tempIndex = tempIndex + ;
numbers.Add(double.Parse(express.Substring(tempIndex, i - tempIndex)));
operaters.Add(express[i]);
tempIndex = i;
}
}
numbers.Add(double.Parse(express.Substring(tempIndex + , express.Length - tempIndex - )));
//开始计算
double result = ;
if (operaters.Count == )
{
return double.Parse(express);
}
else
{
CalcMultiplyDivide(numbers, operaters); //计算乘除
result = CalcAddSubduction(numbers, operaters); //计算加减
}
return result;
}
#endregion
<2> 递归将 没有括号的表达式中的乘除计算,将结果替换 乘除表达式
#region 计算乘除
/// <summary>
/// 递归计算表达式中的乘/除运算
/// </summary>
/// <param name="numbers">表达式中的数字集合</param>
/// <param name="operaters">操作符集合</param>
public void CalcMultiplyDivide(List<double> numbers, List<char> operaters)
{
for (int i = ; i < operaters.Count; i++)
{
bool temp = false;
double n = ;
if (operaters[i] == '*')
{
n = numbers[i] * numbers[i + ];
temp = true;
}
else if (operaters[i] == '/')
{
n = numbers[i] / numbers[i + ];
temp = true;
}
if (temp)
{
operaters.RemoveAt(i);
numbers.RemoveRange(i, );
numbers.Insert(i, n);
CalcMultiplyDivide(numbers, operaters);
break;
}
}
}
#endregion
<3> 递归算加减,直到表达式中没有操作符,然后返回结果。
#region 计算加减
/// <summary>
/// 递归计算加减
/// </summary>
/// <param name="numbers">表达式中的数字集合</param>
/// <param name="operaters">操作符集合</param>
/// <returns>计算的结果</returns>
public double CalcAddSubduction(List<double> numbers, List<char> operaters)
{ for (int i = ; i < operaters.Count; i++)
{
bool temp = false;
double n = ;
if (operaters[i] == '+')
{
n = numbers[i] + numbers[i + ];
temp = true;
}
else if (operaters[i] == '-')
{
n = numbers[i] - numbers[i + ];
temp = true;
}
if (temp)
{
operaters.RemoveAt(i);
numbers.RemoveRange(i, );
numbers.Insert(i, n);
CalcAddSubduction(numbers, operaters);
break;
}
}
double result = ;
if (operaters.Count == )
result = numbers[];
return result;
}
#endregion
这就可以实现像js eval 方法一样对一个四则运算表达式 计算了。这只是按我自己的思路来实现的,没有考虑性能啊什么的,如大家有什么好的法子,一起讨论下。
附上demo:http://files.cnblogs.com/joey0210/Calc.rar
C#实现eval 进行四则运算的更多相关文章
- C#实现eval 进行四则运算(有码)
在JavaScript中实现四则运算很简单,只需要调用eval函数就行了,但是不知道什么原因万能的.NET却没有封装这个函数~ 在这里为大家封装了一个C#版本的eval函数,具体的设计参考了<大 ...
- C#实现eval
C#实现eval 进行四则运算(有码) 在JavaScript中实现四则运算很简单,只需要调用eval函数就行了,但是不知道什么原因万能的.NET却没有封装这个函数~ 在这里为大家封装了一个C#版 ...
- 软件工程(FZU2015)增补作业
说明 张老师为FZU软件工程2015班级添加了一次增补作业,总分10分,deadline是2016/01/01-2016/01/03 前11次正式作业和练习的迭代评分见:http://www.cnbl ...
- 软件工程(FZU2015) 增补作业
SE_FZU目录:1 2 3 4 5 6 7 8 9 10 11 12 13 说明 张老师为FZU软件工程2015班级添加了一次增补作业,总分10分,deadline是2016/01/01-2016/ ...
- C#版的eval,C#Light开源嵌入式脚本,unity热更新不再愁
目前最新版本AlphaV0.06 完全的c#语法,可用于一切能运行C#的场合,wp windows xamarin mono asp.net unity3d 内嵌了int uint bool stri ...
- [置顶] js综合应用:表格的四则运算
在做调查问卷的过程中,遇到一个表格的统计问题,算是需要些js方面的综合知识,所以记录下来. 在上次完成了基本的求和的基础上,添加了基本的加减乘除四则运算. 基本需求简化后如下: 对应的htm了为: & ...
- 结对编程1---基于Flask的四则运算题目生成器
项目代码地址 / WEB应用地址 / 合作伙伴iFurySt博文链接 需求分析 本次程序是基于原有的控制台四则运算器的基础上,改成WEB的形式,同时还增加了一些新的功能.同时因为交互方式的改变,代码也 ...
- Python实现简单的四则运算
GitHub 项目地址 https://github.com/745421831/-/tree/master PSP PSP2.1 Personal Software Process Stages 预 ...
- 小学生噩梦——四则运算题库(python 全功能实现)
Github: https://github.com/holidaysss 小组:龙天尧(代码实现),林毓植(浮点转分数函数,代码审查) PSP2.1 Personal Software Proces ...
随机推荐
- eclipse使用
Eclipse 是一个开放源代码的.基于 Java 的可扩展开发平台. Eclipse 是 Java 的集成开发环境(IDE),当然 Eclipse 也可以作为其他开发语言的集成开发环境,如C,C++ ...
- 通过HttpClient来调用Web Api接口~续~实体参数的传递
并且我们知道了Post,Put方法只能有一个FromBody参数,再有多个参数时,上讲提到,需要将它封装成一个对象进行传递,而这讲主要围绕这个话题来说,接口层添加一个新类User_Info,用来进行数 ...
- 在opencv3中实现机器学习之:利用逻辑斯谛回归(logistic regression)分类
logistic regression,注意这个单词logistic ,并不是逻辑(logic)的意思,音译过来应该是逻辑斯谛回归,或者直接叫logistic回归,并不是什么逻辑回归.大部分人都叫成逻 ...
- Anaroid WebView 的属性汇总
1. 打开网页时不调用系统浏览器, 而是在本WebView中显示: mWebView.setWebViewClient(new WebViewClient(){ @Override public bo ...
- 免费Flash图表工具FusionChart
图表显示是很多开发工作所必不可少的一项功能,今天我介绍一个前段时间发现的免费的Flash图表开发工具,可以通过Adobe Flash实现数据的图表化,动态化以及相互交互. FusionChart是一个 ...
- 信息安全系统设计基础实验一 20135210&20135218
北京电子科技学院(BESTI) 实 验 报 告 课程: 密码系统设计基础 ...
- 关于个人博客和Github地址提交
请大家尽快按照http://www.cnblogs.com/SivilTaram/p/5857858.html的要求提交个人博客和Github地址.谢谢!
- 20145215实验三 敏捷开发与XP实践
20145215实验三 敏捷开发与XP实践 实验内容 XP基础 XP核心实践 相关工具 实验步骤 (一)敏捷开发与XP 软件工程是把系统的.有序的.可量化的方法应用到软件的开发.运营和维护上的过程.软 ...
- Html中metra的含义
from: http://dev.csdn.net/article/60/60902.shtm meta是用来在HTML文档中模拟HTTP协议的响应头报文.meta 标签用于网页的<head&g ...
- Jquery each() 如何操作动态添加的DOM元素
JQ each页面上的DOM元素的时候,如果有一部分的DOM是ajax异步加载的,那么each可能遍历不到元素,异步请求数据的同时不会影响后面的代码执行,今天就遇到这个问题了, 解决方案是讲ajax改 ...