网页功能: 加入收藏 设为首页 网站搜索  
算术表达式解析器的实现思路
发表日期:2004-05-17作者:activeandbadboy[转贴] 出处:CSDN  

  作为程序设计人员经常会遇到这样的情况,需要将某个指定的字符串表达式转换为算术表达式并计算其结果.使用Delphi的朋友可以在网上获取第三方控件来实现,而.Net框架类库并没有相关的处理类,正好在前不久的给一所大学开发的Web应用中也需要实现相关的处理.就抽空写了一个相关的处理类(实现了大部分的算术运算操作,需要其他运算可以在现有基础上扩展),现将部分代码贴出共大家参考,希望能够在交流中进步、互助中学习、探讨中深入:

//EnumExpress

using System;

namespace ExpressionTest

{

/// <summary>

/// EnumExpress 的摘要说明。

/// </summary>

public enum EnumExpress

{

 Add,//加号

 Dec,//减号

 Mul,//乘号

 Div,//除号

 Sin,//正玄

 Cos,//余玄

 Tan,//正切

 ATan,//余切

 Sqrt,//平方根

 Pow,//求幂

 None,//无

}

}

//ExpressDeal

using System;

namespace ExpressionTest

{

/// <summary>

/// ExpressDeal 的摘要说明。

/// </summary>

public class ExpressDeal

{

 static ExpressDeal()

 {

 

 }

 private double CalculateExpress(string strExpression)

 {

 

  string strTemp="";

  string strTempB="";

  string strOne="";

  string strTwo="";

  double ReplaceValue=0;

  while (strExpression.IndexOf("+")!=-1 || strExpression.IndexOf("-")!=-1

  || strExpression.IndexOf("*")!=-1 || strExpression.IndexOf("/")!=-1)

  {

  if (strExpression.IndexOf("*")!=-1)

  {

   strTemp=strExpression.Substring(strExpression.IndexOf("*")+1,strExpression.Length-strExpression.IndexOf("*")-1);

   strTempB=strExpression.Substring(0,strExpression.IndexOf("*"));

   strOne=strTempB.Substring(GetPrivorPos(strTempB)+1,strTempB.Length-GetPrivorPos(strTempB)-1);

  

   strTwo=strTemp.Substring(0,GetNextPos(strTemp));

   ReplaceValue=Convert.ToDouble(GetExpType(strOne))*Convert.ToDouble(GetExpType(strTwo));

   strExpression=strExpression.Replace(strOne+"*"+strTwo,ReplaceValue.ToString());

  }

  else if (strExpression.IndexOf("/")!=-1)

  {

   strTemp=strExpression.Substring(strExpression.IndexOf("/")+1,strExpression.Length-strExpression.IndexOf("/")-1);

   strTempB=strExpression.Substring(0,strExpression.IndexOf("/"));

   strOne=strTempB.Substring(GetPrivorPos(strTempB)+1,strTempB.Length-GetPrivorPos(strTempB)-1);

  

  

   strTwo=strTemp.Substring(0,GetNextPos(strTemp));

   ReplaceValue=Convert.ToDouble(GetExpType(strOne))/Convert.ToDouble(GetExpType(strTwo));

   strExpression=strExpression.Replace(strOne+"/"+strTwo,ReplaceValue.ToString());

  }

  else if (strExpression.IndexOf("+")!=-1)

  {

   strTemp=strExpression.Substring(strExpression.IndexOf("+")+1,strExpression.Length-strExpression.IndexOf("+")-1);

   strTempB=strExpression.Substring(0,strExpression.IndexOf("+"));

   strOne=strTempB.Substring(GetPrivorPos(strTempB)+1,strTempB.Length-GetPrivorPos(strTempB)-1);

  

   strTwo=strTemp.Substring(0,GetNextPos(strTemp));

   ReplaceValue=Convert.ToDouble(GetExpType(strOne))+Convert.ToDouble(GetExpType(strTwo));

   strExpression=strExpression.Replace(strOne+"+"+strTwo,ReplaceValue.ToString());

  }

  else if (strExpression.IndexOf("-")!=-1)

  {

   strTemp=strExpression.Substring(strExpression.IndexOf("-")+1,strExpression.Length-strExpression.IndexOf("-")-1);

   strTempB=strExpression.Substring(0,strExpression.IndexOf("-"));

   strOne=strTempB.Substring(GetPrivorPos(strTempB)+1,strTempB.Length-GetPrivorPos(strTempB)-1);

  

  

   strTwo=strTemp.Substring(0,GetNextPos(strTemp));

   ReplaceValue=Convert.ToDouble(GetExpType(strOne))-Convert.ToDouble(GetExpType(strTwo));

   strExpression=strExpression.Replace(strOne+"-"+strTwo,ReplaceValue.ToString());

  }

  }

 

  return Convert.ToDouble(strExpression);

 }

 

 private double CalculateExExpress(string strExpression,EnumExpress ExpressType)

 {

  double retValue=0;

  switch(ExpressType)

  {

  case EnumExpress.Sin:

   retValue=Math.Sin(Convert.ToDouble(strExpression));

   break;

  case EnumExpress.Cos:

   retValue= Math.Cos(Convert.ToDouble(strExpression));

   break;

  case EnumExpress.Tan:

   retValue= Math.Tan(Convert.ToDouble(strExpression));

   break;

  case EnumExpress.ATan:

   retValue= Math.Atan(Convert.ToDouble(strExpression));

   break;

  case EnumExpress.Sqrt:

   retValue= Math.Sqrt(Convert.ToDouble(strExpression));

   break;

  case EnumExpress.Pow:

   retValue= Math.Pow(Convert.ToDouble(strExpression),2);

   break;

  }

  if (retValue==0) return Convert.ToDouble(strExpression);

  return retValue;

 }

 private int GetNextPos(string strExpression)

 {

  int[] ExpPos=new int[4];

  ExpPos[0]=strExpression.IndexOf("+");

  ExpPos[1]=strExpression.IndexOf("-");

  ExpPos[2]=strExpression.IndexOf("*");

  ExpPos[3]=strExpression.IndexOf("/");

  int tmpMin=strExpression.Length;

  for (int count=1;count<=ExpPos.Length;count++)

  {

  if (tmpMin>ExpPos[count-1] && ExpPos[count-1]!=-1)

  {

   tmpMin=ExpPos[count-1];

  }

  }

  return tmpMin;

 

 }

 private int GetPrivorPos(string strExpression)

 {

  int[] ExpPos=new int[4];

  ExpPos[0]=strExpression.LastIndexOf("+");

  ExpPos[1]=strExpression.LastIndexOf("-");

  ExpPos[2]=strExpression.LastIndexOf("*");

  ExpPos[3]=strExpression.LastIndexOf("/");

  int tmpMax=-1;

  for (int count=1;count<=ExpPos.Length;count++)

  {

  if (tmpMax<ExpPos[count-1] && ExpPos[count-1]!=-1)

  {

   tmpMax=ExpPos[count-1];

  }

  }

  return tmpMax;

 

 }

 public string SpiltExpression(string strExpression)

 {

  string strTemp="";

  string strExp="";

  while (strExpression.IndexOf("(")!=-1)

  {

  strTemp=strExpression.Substring(strExpression.LastIndexOf("(")+1,strExpression.Length-strExpression.LastIndexOf("(")-1);

  strExp=strTemp.Substring(0,strTemp.IndexOf(")"));

  strExpression=strExpression.Replace("("+strExp+")",CalculateExpress(strExp).ToString());

  }

  if(strExpression.IndexOf("+")!=-1 || strExpression.IndexOf("-")!=-1

  || strExpression.IndexOf("*")!=-1 || strExpression.IndexOf("/")!=-1)

  {

  strExpression=CalculateExpress(strExpression).ToString();

  }

  return strExpression;

 }

 

 private string GetExpType(string strExpression)

 {

  strExpression=strExpression.ToUpper();

  if (strExpression.IndexOf("SIN")!=-1)

  {

  return CalculateExExpress(strExpression.Substring(strExpression.IndexOf("N")+1,strExpression.Length-1-strExpression.IndexOf("N")),EnumExpress.Sin).ToString();

  }

  if (strExpression.IndexOf("COS")!=-1)

  {

  return CalculateExExpress(strExpression.Substring(strExpression.IndexOf("S")+1,strExpression.Length-1-strExpression.IndexOf("S")),EnumExpress.Cos).ToString();

  }

  if (strExpression.IndexOf("TAN")!=-1)

  {

  return CalculateExExpress(strExpression.Substring(strExpression.IndexOf("N")+1,strExpression.Length-1-strExpression.IndexOf("N")),EnumExpress.Tan).ToString();

  }

  if (strExpression.IndexOf("ATAN")!=-1)

  {

  return CalculateExExpress(strExpression.Substring(strExpression.IndexOf("N")+1,strExpression.Length-1-strExpression.IndexOf("N")),EnumExpress.ATan).ToString();

  }

  if (strExpression.IndexOf("SQRT")!=-1)

  {

  return CalculateExExpress(strExpression.Substring(strExpression.IndexOf("T")+1,strExpression.Length-1-strExpression.IndexOf("T")),EnumExpress.Sqrt).ToString();

  }

  if (strExpression.IndexOf("POW")!=-1)

  {

  return CalculateExExpress(strExpression.Substring(strExpression.IndexOf("W")+1,strExpression.Length-1-strExpression.IndexOf("W")),EnumExpress.Pow).ToString();

  }

  return strExpression;

 }

}

}

我来说两句】 【加入收藏】 【返加顶部】 【打印本页】 【关闭窗口
中搜索 算术表达式解析器的实现思路
本类热点文章
  简单的多人聊天(C#.Socket)
  C#的office操作[word&Excel]
  在C#中调用VBScript、JavaScript等脚本..
  在C#中调用VBScript、JavaScript等脚本..
  C#程序编码规范
  C#程序编码规范
  使用c#获得cpu,硬盘的序列号
  在Linux上运行C#
  在Linux上运行C#
  弹出窗口杀手
  弹出窗口杀手
  算术表达式解析器的实现思路
最新分类信息我要发布 
最新招聘信息

关于我们 / 合作推广 / 给我留言 / 版权举报 / 意见建议 / 广告投放  
Copyright ©2003-2024 Lihuasoft.net webmaster(at)lihuasoft.net
网站编程QQ群   京ICP备05001064号 页面生成时间:0.00401