DataTable列上多值运算

时间:2022-04-02 09:30:37

1、从网上找了个中缀算法(也不知道什么前缀后缀,抱歉),可以对字符串表达式进行运算

2、有些时候还是会用到ASCII码表的

char c = expression[k];//expression为一字符串
int intAsciiCode = (int)c;

3、里面用到了解决多种字符串日期显示格式,转换为日期类型的办法

DateTime time = DateTime.Now;

DateTimeFormatInfo dtfi = new CultureInfo("zh-CN", true).DateTimeFormat;
DateTime.TryParseExact(strTime, new string[] { "yyyyMMdd", "yyyy.M.d", "d-M-yyyy", "d-M月-yyyy", "yyyy-M-d", "yyyy_M_d" }, dtfi, DateTimeStyles.None, out time);//strTime为字符串类型日期

  public class DataTableCompute
{
/// <summary>
/// 对DataTabella行上的列根据运算式计算
/// </summary>
/// <param name="dicDecimal">数值类型表达式键值对</param>
/// <param name="dicTime">时间类型表达式键值对</param>
/// <param name="row">DataTable表上的行</param>
public static void ComputeColumns(Dictionary<string, string> dicDecimal, Dictionary<string, string> dicTime, DataRow row)
{
if (dicDecimal != null && dicDecimal.Count > )
{
foreach (KeyValuePair<string, string> kvp in dicDecimal)
{
GetExpressionByType(row, kvp, "decimal");
}
}
if (dicTime != null && dicTime.Count > )
{
foreach (KeyValuePair<string, string> kvp in dicTime)
{
GetExpressionByType(row, kvp, "time");
}
} } private static void GetExpressionByType(DataRow row, KeyValuePair<string, string> kvp, string type)
{
string result = kvp.Key;
string expression = kvp.Value;
string[] cols = expression.Split(new char[] { '(', ')', '+', '-', '*', '/', '\\' },StringSplitOptions.RemoveEmptyEntries);
for (int m = ; m < cols.Length; m++)
{
if (type == "time")
{
DateTime time = DateTime.Now;
if (cols[m].ToLower() != "now")
{
DateTimeFormatInfo dtfi = new CultureInfo("zh-CN", true).DateTimeFormat;
if (!DateTime.TryParseExact(row[cols[m]].ToString(), new string[] { "yyyyMMdd", "yyyy.M.d", "d-M-yyyy", "d-M月-yyyy", "yyyy-M-d", "yyyy_M_d" }, dtfi, DateTimeStyles.None, out time))
{
time = DateTime.Now;
}
}
cols[m] = (time.Year * + time.Month).ToString();
}
else
{
double d = ;
if (double.TryParse(row[cols[m]].ToString(), out d))
{
d = Math.Round(d, );
}
cols[m] = d.ToString();
}
}
StringBuilder newExpression = new StringBuilder();
int n = ;
for (int k = ; k < expression.Length; k++)
{
char c = expression[k];
int intAsciiCode = (int)c;
if (intAsciiCode >= && intAsciiCode <= )
{
newExpression.Append(c.ToString() + " ");
continue;
}
if (c == 'F' || c == 'n')
{
newExpression.Append(cols[n] + " ");
n++;
}
}
string str = newExpression.ToString();
row[result] = CalculateResult(str);
}
private static double CalculateResult(string expre)
{
List<string> temp = getColuExpression(expre);
try
{
while (temp.Count > )
{
for (int i = ; i < temp.Count; i++)
{
double resultTemp = ;
if (temp[i] == "+")
resultTemp = Convert.ToDouble(temp[i - ]) + Convert.ToDouble(temp[i - ]);
else if (temp[i] == "-")
resultTemp = Convert.ToDouble(temp[i - ]) - Convert.ToDouble(temp[i - ]);
else if (temp[i] == "*")
resultTemp = Convert.ToDouble(temp[i - ]) * Convert.ToDouble(temp[i - ]);
else if (temp[i] == "/")
resultTemp = Convert.ToDouble(temp[i - ]) / Convert.ToDouble(temp[i - ]);
else
continue;
temp[i - ] = resultTemp.ToString();
temp.RemoveAt(i);
temp.RemoveAt(i - );
break;
}
}
}
catch (Exception ex)//计算表达式的值错误,导致无法运算
{
temp.Clear();
temp.Add("");
}
return Convert.ToDouble(temp[]);
}
private static List<string> getColuExpression(string exp)
{
System.Text.ASCIIEncoding asc = new System.Text.ASCIIEncoding();
Stack st = new Stack();
string[] temp = exp.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
List<string> value = new List<string>(); for (int i = ; i < temp.Length; i++)
{
int num = (int)asc.GetBytes(temp[i])[];
if (num < && num > )
{
if (st.Count > )
{
string operatorStr = st.Peek().ToString();
if (temp[i] == "*" || temp[i] == "/")
{
if (temp[i + ] == "(")
{
st.Push(temp[i]); continue;
}
else
{
if (operatorStr == "(")
{
st.Push(temp[i]);
continue;
}
else if (operatorStr == "*" || operatorStr == "/")
{
value.Add(st.Pop().ToString());
st.Push(temp[i]);
continue;
}
else
{
st.Push(temp[i]);
continue;
}
}
}
else if (temp[i] == "+" || temp[i] == "-")
{
if (operatorStr == "(")
{
st.Push(temp[i]);
continue;
}
else
{
value.Add(st.Pop().ToString());
if (st.Count > && st.Peek().ToString() != "(")
{
value.Add(st.Pop().ToString());
}
st.Push(temp[i]);
continue;
}
}
else if (temp[i] == "(")
{
st.Push(temp[i]);
continue;
}
else
{
if (i + == temp.Length)
{
value.Add(st.Pop().ToString());
st.Pop();
while (st.Count > )
value.Add(st.Pop().ToString());
break;
}
else
{
value.Add(st.Pop().ToString());
st.Pop();
continue;
}
}
}
else
{
st.Push(temp[i]);
continue;
}
}
else if (i + == temp.Length)
{
value.Add(temp[i]);
value.Add(st.Pop().ToString());
while (st.Count > )
value.Add(st.Pop().ToString());
break;
}
else
{
value.Add(temp[i]);
continue;
}
}
return value;
}
}

DataTable列计算类