C# net 使用Irony+XLParser实现类似于Excel中的公式和运算
C# net 使用Irony+XLParser实现类似于Excel中的公式和运算
安装包 XLParser
使用方法:
var bbb = new PnHelp().Jx("=1+2+A1","3");
public class PnHelp
{
public List<Exception> ErrAll = new List<Exception>();
public Exception ErrFirst { get => ErrAll.FirstOrDefault(); }
public bool IsSucceed { get; private set; } = false;
public string Jx(string text, string th_A1 = null)
{
var aaa = new Dictionary<string, string>();
if (!string.IsNullOrWhiteSpace(th_A1))
aaa.Add("A1", th_A1);
return Jx(text, aaa);
}
public string Jx(string text, Dictionary<string, string> th = null)
{
if (string.IsNullOrWhiteSpace(text) || !text.StartsWith("="))
return text;
var par = ExcelFormulaParser.Parse(text.Substring(1));
var aaa1 = Jx(par, th);
var bbb = aaa1.AllNodes().LastOrDefault();
if (bbb != null && bbb.Is(GrammarNames.TokenError))
throw ErrFirst;
IsSucceed = true;
return bbb?.Token.ValueString ?? "";
}
public string JxTry(string text, string th_A1 = null)
{
var aaa = new Dictionary<string, string>();
if (!string.IsNullOrWhiteSpace(th_A1))
aaa.Add("A1", th_A1);
return JxTry(text, aaa);
}
public string JxTry(string text, Dictionary<string, string> th = null)
{
if (string.IsNullOrWhiteSpace(text) || !text.StartsWith("="))
return text;
var par = ExcelFormulaParser.Parse(text.Substring(1));
var aaa1 = Jx(par, th);
var bbb = aaa1.AllNodes().LastOrDefault();
IsSucceed = !(bbb != null && bbb.Is(GrammarNames.TokenError));
return bbb?.Token.ValueString ?? "";
}
private ParseTreeNode Jx(ParseTreeNode treeNode, Dictionary<string, string> th = null)
{
var nodes = treeNode.ChildNodes;
foreach (var node in nodes)
{
var p1 = node.Print();
if (node.IsFunction())
{
//函数
var hs = node.GetFunction();
//参数
var csList = node.GetFunctionArguments();
//参数
List<ParseTreeNode> csa = new List<ParseTreeNode>();
foreach (var cs in csList)
{
var p12 = cs.Print();
var cs4 = cs.AllNodes().ElementAtOrDefault(3);
if (cs4 != null && (cs4.Is(GrammarNames.TokenText) || cs4.Is(GrammarNames.TokenNumber) || cs4.Is(GrammarNames.TokenBool) || cs4.Is(GrammarNames.TokenError)))
{
csa.Add(cs4);
}
else if (cs4 != null && cs4.Is(GrammarNames.TokenCell))
{
var cellval = cs4.Token.ValueString;
if (th != null && th.TryGetValue(cellval, out string val2))
csa.Add(GetNode(val2).AllNodes().ElementAtOrDefault(3));
else
csa.Add(GetNode(cellval).AllNodes().ElementAtOrDefault(3));
}
else
{
var csjg = Jx(cs, th);
var cs5 = csjg.AllNodes().LastOrDefault();
csa.Add(cs5);
}
}
//执行
ParseTreeNode newval;
try
{
newval = keyValuePairs[hs].Item1.Invoke(csa);
}
catch (Exception ex)
{
newval = GetErrNode();
ErrAll.Add(ex);
}
treeNode.ChildNodes.Clear();
treeNode.ChildNodes.Add(newval);
return newval;
}
else if (node.Is(GrammarNames.Reference))
{
return Jx(node, th);
}
else if (node.Is(GrammarNames.Formula))
{
return Jx(node, th);
}
//else if (node.Is(GrammarNames.Cell))
//{
// return Jx(node, th);
//}
}
return treeNode;
}
public static Dictionary<string, (Func<List<ParseTreeNode>, ParseTreeNode>, string)> keyValuePairs = new Dictionary<string, (Func<List<ParseTreeNode>, ParseTreeNode>, string)>()
{
//excel自带
{ "+",(Jia,"加号")},
{ "-",(Jian,"减号、负数")},
{ "*",(Cen,"乘号")},
{ "/",(Chu,"除号")},
{ "%",(BaiFenBi,"百分号")},
{ "^",(CenMu,"乘幂")},
{ "&",(HeBin,"和号,连接文本或数值。")},
{ "=",(DengYu,"等于")},
{ "<>",(BuDengYu,"不等于")},
{ ">",(DaYu,"大于")},
{ "<",(XiaoYu,"小于")},
{ ">=",(DaYuDengYu,"大于等于")},
{ "<=",(XiaoYuDengYu,"小于等于")},
{ "IF",(IF,"条件判断。IF(TRUE|FALSE,值_true,值_false)")},
{ "IFS",(IFS,"多条件判断并执行。IFS(TRUE|FALSE,值1,TRUE|FALSE,值2,...)")},
{ "IFERROR",(IFERROR,"错误时采用其他值。IFERROR(值,错误时采用的值)")},
{ "AND",(AND,"多个条件判断,需要所有满足。AND(TRUE|FALSE,TRUE|FALSE,...)")},
{ "OR",(OR,"多个条件判断,需要一个满足。OR(TRUE|FALSE,TRUE|FALSE,...)")},
{ "ABS",(ABS,"绝对值。ABS(值)")},
{ "LOG",(LOG,"对数。LOG(值,[底,默认10])")},
{ "REPLACE",(REPLACE,"替换字符串。REPLACE(值,开始位置,个数,新值)")},
{ "SUBSTITUTE",(SUBSTITUTE,"替换字符串。SUBSTITUTE(值,原值,新值,[替换序号|未实现])")},
{ "MID",(MID,"截取字符串。MID(值,开始位置|负数倒取,[字符个数,默认结尾])")},
{ "SEARCH",(SEARCH,"查找字符串,没有找到为0。SEARCH(值,查找值,[开始位置,默认1])")},
{ "TRIM",(TRIM,"清除前后空格。TRIM(值)")},
{ "LEN",(LEN,"获取长度。LEN(值)")},
{ "VALUE",(VALUE,"文本转为数字。VALUE(值,[视为小数点的值])")},
//自定义函数
{ "REVERSE",(REVERSE,"反转字符串。REVERSE(值)")},
{ "REPLACES",(REPLACES,"替换多个字符串。REPLACES(值,新值,查找值1,查找值2,...)")},
{ "CONTAINS",(CONTAINS,"字符串中是否存在。CONTAINS(值,值1,值2,...)")},
{ "WHERENUM",(WHERENUM,"只保留数字,可识别小数点。WHERENUM(值,[1不停止,2不满足停止,默认1])")},
{ "WHERENUM2",(WHERENUM2,"只保留数字。WHERENUM(值)")},
{ "WHEREAZ",(WHEREAZ,"只保留字母。WHEREAZ(值,[1不停止,2不满足停止,默认1],[1默认,2转大写,3转小写,默认1])")},
{ "WHERENUMAZ",(WHERENUMAZ,"只保留数字和字母。WHERENUMAZ(值)")},
{ "SPLIT",(SPLIT,"分隔字符串。SPLIT(值,[取的位置|负数倒取,默认1],[分隔值1,分隔值2...,默认_])")},
{ "PADLEFT",(PADLEFT,"字符串左侧填充字符,实现右对齐。PADLEFT(值,长度,[对齐字符,默认0])")},
{ "PADRIGHT",(PADRIGHT,"字符串右侧填充字符,实现左对齐。PADRIGHT(值,长度,[对齐字符,默认0])")},
{ "DEC2DEC",(DEC2DEC,"进制转换。DEC2DEC(值,当前进制2-36,目标进制2-36)")},
{ "MIDLOG10",(MIDLOG10,"截取后计算10底的指数(如:1000=102)。MIDLOG10(值,基数位数,[1末尾追加基数|2不追加,默认1])")},
{ "MIDLOG10R",(MIDLOG10R,"尾位当做10底的指数转为整数,<10返回本身(如:102=1000)。MIDLOG10R(值,[尾位长度,默认1])")},
{ "KILO4",(KILO4,"千值转为4长度字符串(如:1000=001K)。KILO4(值,从小到大的3个长度的字符单位)")},
{ "KILO4R",(KILO4R,"4长度字符串转为千值(如:001K=1000)。KILO4R(值,从小到大的3个长度的字符单位)")},
};
#region 内置
public static ParseTreeNode GetNode(object val)
{
if (val is bool bo)
return ExcelFormulaParser.Parse(bo.ToString().ToUpper());
else if (val is "#VALUE!")
return ExcelFormulaParser.Parse($"{val.ToString()}");
else if (val is ParseTreeNode node)
{
if (node.Is(GrammarNames.TokenError))
return ExcelFormulaParser.Parse("#VALUE!");
else
return ExcelFormulaParser.Parse($"\"{node.Token.ValueString}\"");
}
else
return ExcelFormulaParser.Parse($"\"{val}\"");
}
public static ParseTreeNode GetErrNode()
{
return GetNode("#VALUE!");
}
public static bool TryGetErrNode(List<ParseTreeNode> datas, out ParseTreeNode errNode)
{
errNode = null;
foreach (var item in datas)
{
if (item.Is(GrammarNames.TokenError))
{
errNode = GetErrNode();
return true;
}
}
return false;
}
public static bool TryGetErrNode(ParseTreeNode data, out ParseTreeNode errNode)
{
errNode = null;
if (data.Is(GrammarNames.TokenError))
{
errNode = GetErrNode();
return true;
}
return false;
}
#endregion
static ParseTreeNode Jia(List<ParseTreeNode> data)
{
return GetNode((Convert.ToDecimal(data[0].Token.ValueString) + Convert.ToDecimal(data[1].Token.ValueString)));
}
static ParseTreeNode Jian(List<ParseTreeNode> data)
{
if (data.Count() == 1)
return GetNode((0m - Convert.ToDecimal(data[0].Token.ValueString)));
else
return GetNode((Convert.ToDecimal(data[0].Token.ValueString) - Convert.ToDecimal(data[1].Token.ValueString)));
}
static ParseTreeNode Cen(List<ParseTreeNode> data)
{
return GetNode((Convert.ToDecimal(data[0].Token.ValueString) * Convert.ToDecimal(data[1].Token.ValueString)));
}
static ParseTreeNode Chu(List<ParseTreeNode> data)
{
return GetNode((Convert.ToDecimal(data[0].Token.ValueString) / Convert.ToDecimal(data[1].Token.ValueString)));
}
static ParseTreeNode BaiFenBi(List<ParseTreeNode> data)
{
return GetNode((Convert.ToDecimal(data[0].Token.ValueString) / 100m));
}
static ParseTreeNode CenMu(List<ParseTreeNode> data)
{
return GetNode((Math.Pow(Convert.ToDouble(data[0].Token.ValueString), Convert.ToDouble(data[1].Token.ValueString))));
}
static ParseTreeNode HeBin(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode(string.Join("", data.Select(o => o.Token.ValueString)));
}
static ParseTreeNode DengYu(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode((data[0].Token.ValueString == data[1].Token.ValueString));
}
static ParseTreeNode BuDengYu(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode((data[0].Token.ValueString != data[1].Token.ValueString));
}
static ParseTreeNode DaYu(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode((Convert.ToDecimal(data[0].Token.ValueString) > Convert.ToDecimal(data[1].Token.ValueString)));
}
static ParseTreeNode XiaoYu(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode((Convert.ToDecimal(data[0].Token.ValueString) < Convert.ToDecimal(data[1].Token.ValueString)));
}
static ParseTreeNode DaYuDengYu(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode((Convert.ToDecimal(data[0].Token.ValueString) >= Convert.ToDecimal(data[1].Token.ValueString)));
}
static ParseTreeNode XiaoYuDengYu(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode((Convert.ToDecimal(data[0].Token.ValueString) <= Convert.ToDecimal(data[1].Token.ValueString)));
}
static ParseTreeNode IF(List<ParseTreeNode> data)
{
if (TryGetErrNode(data[0], out ParseTreeNode errNode))
return errNode;
if (data[0].Token.ValueString == "TRUE")
return GetNode(data[1]);
else
return GetNode(data[2]);
}
static ParseTreeNode IFS(List<ParseTreeNode> data)
{
int i = 0;
while (true)
{
if (data[i * 2].Token.ValueString == "TRUE")
return GetNode(data[(i * 2) + 1]);
i++;
}
}
static ParseTreeNode IFERROR(List<ParseTreeNode> data)
{
if (data[0].Is(GrammarNames.TokenError) || data[0].Is(GrammarNames.TokenRefError))
return GetNode(data[1]);
return GetNode(data[0]);
}
static ParseTreeNode AND(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode(data.All(o => o.Token.ValueString == "TRUE"));
}
static ParseTreeNode OR(List<ParseTreeNode> data)
{
return GetNode(data.Any(o => o.Token.ValueString == "TRUE"));
}
static ParseTreeNode ABS(List<ParseTreeNode> data)
{
return GetNode(Math.Abs(Convert.ToDecimal(data[0].Token.ValueString)));
}
static ParseTreeNode LOG(List<ParseTreeNode> data)
{
return GetNode(Math.Log(Convert.ToDouble(data[0].Token.ValueString), data.Count() == 1 ? 10 : Convert.ToDouble(data[1].Token.ValueString)));
}
static ParseTreeNode REPLACE(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode($"{data[0].Token.ValueString.Substring(0, Convert.ToInt32(data[1].Token.ValueString) - 1)}{data[3].Token.ValueString}{data[0].Token.ValueString.Substring(Convert.ToInt32(data[1].Token.ValueString) + Convert.ToInt32(data[2].Token.ValueString) - 1)}");
}
static ParseTreeNode SUBSTITUTE(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode(data.Count == 3 ? data[0].Token.ValueString.Replace(data[1].Token.ValueString, data[2].Token.ValueString) : data[0].Token.ValueString.Replace(data[1].Token.ValueString, data[2].Token.ValueString));
}
static ParseTreeNode MID(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var v0 = data[0].Token.ValueString;
var v1 = Convert.ToInt32(data[1].Token.ValueString);
var v2 = data.Count < 3 ? v0.Length : Convert.ToInt32(data[2].Token.ValueString);
return GetNode(v1 > 0 ? new string(v0.Skip(v1 - 1).Take(v2).ToArray()) : new string(v0.Reverse().Skip(Math.Abs(v1) - 1).Take(v2).Reverse().ToArray()));
}
static ParseTreeNode SEARCH(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var v1 = data[0].Token.ValueString;
var v2 = data[1].Token.ValueString;
var v3 = data.Count > 2 ? Convert.ToInt32(data[2].Token.ValueString) - 1 : 0;
var v = v1.Substring(v3).IndexOf(v2) + 1;
return GetNode(v);
}
static ParseTreeNode TRIM(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode(data[0].Token.ValueString.Trim());
}
static ParseTreeNode LEN(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode(data[0].Token.ValueString.Length);
}
static ParseTreeNode VALUE(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
if (data.Count == 1)
return GetNode(double.Parse(data[0].Token.ValueString));
else
return GetNode(double.Parse(data[0].Token.ValueString.Replace(data[1].Token.ValueString, ".")));
}
static ParseTreeNode REVERSE(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
return GetNode(new string(data[0].Token.ValueString.Reverse().ToArray()));
}
static ParseTreeNode REPLACES(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var va = data[0].Token.ValueString;
foreach (var v in data.Skip(2))
{
va = va.Replace(v.Token.ValueString, data[1].Token.ValueString);
}
return GetNode(va);
}
static ParseTreeNode CONTAINS(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
foreach (var item in data.Skip(1))
{
if (data[0].Token.ValueString.Contains(item.Token.ValueString))
return GetNode(true);
}
return GetNode(false);
}
static ParseTreeNode WHERENUM(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var v1 = data[0].Token.ValueString;
var v2 = data.Count > 1 ? data[1].Token.ValueString : "1";
var sb = new StringBuilder();
foreach (var item in v1)
if (Char.IsDigit(item) || (item == '.' && !sb.ToString().Contains('.')))
sb.Append(item);
else if (v2 == "2" && sb.Length > 0)
break;
return GetNode(Convert.ToDouble(sb.ToString()));
}
static ParseTreeNode WHERENUM2(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var v1 = data[0].Token.ValueString;
var sb = new StringBuilder();
foreach (var item in v1)
if (Char.IsDigit(item))
sb.Append(item);
return GetNode(sb.ToString());
}
static ParseTreeNode WHEREAZ(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var v1 = data[0].Token.ValueString;
var v2 = data.Count > 1 ? data[1].Token.ValueString : "1";
var v3 = data.Count > 2 ? data[2].Token.ValueString : "1";
var sb = new StringBuilder();
foreach (var item in v1)
if (Char.IsLetter(item))
sb.Append(item);
else if (v2 == "2" && sb.Length > 0)
break;
if (v3 == "2")
return GetNode(sb.ToString().ToUpper());
else if (v3 == "3")
return GetNode(sb.ToString().ToLower());
else
return GetNode(sb.ToString());
}
static ParseTreeNode WHERENUMAZ(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var sb = new StringBuilder();
foreach (var item in data[0].Token.ValueString)
if (Char.IsLetterOrDigit(item))
sb.Append(item);
return GetNode(sb.ToString());
}
static ParseTreeNode SPLIT(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var v0 = data[0].Token.ValueString;
var v1 = data.Count < 3 ? new string[] { "_" } : data.Skip(2).Select(o => o.Token.ValueString).ToArray();
var v2 = data.Count < 2 ? 1 : Convert.ToInt32(data[1].Token.ValueString);
return GetNode(v2 > 0 ? v0.Split(v1, StringSplitOptions.None).ElementAtOrDefault(v2 - 1) : v0.Split(v1, StringSplitOptions.None).Reverse().ElementAtOrDefault(Math.Abs(v2) - 1));
}
static ParseTreeNode PADLEFT(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var zf = data.Count() >= 3 ? data[2].Token.ValueString.First() : '0';
return GetNode(data[0].Token.ValueString.PadLeft(Convert.ToInt32(data[1].Token.ValueString), zf));
}
static ParseTreeNode PADRIGHT(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var zf = data.Count() >= 3 ? data[2].Token.ValueString.First() : '0';
return GetNode(data[0].Token.ValueString.PadRight(Convert.ToInt32(data[1].Token.ValueString), zf));
}
const string digits = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ";
static ParseTreeNode DEC2DEC(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var val = data[0].Token.ValueString.ToUpper();
var j1 = Convert.ToInt32(data[1].Token.ValueString);
var j2 = Convert.ToInt32(data[2].Token.ValueString);
if (j1 < 2 || j1 > 36 || j2 < 2 || j2 > 36)
throw new Exception("进制参数必须为2-36");
double j10 = 0;
if (j1 == 10)
j10 = Convert.ToDouble(val);
else
{
var zs = val.Split('.').ElementAtOrDefault(0) ?? "";
var xs = val.Split('.').ElementAtOrDefault(1) ?? "";
int js = zs.Length;
foreach (var x in zs)
{
double aa = digits.IndexOf(x);
if (aa == -1 || aa >= j1)
throw new Exception($"进制参数[{x}]不在进制[{j1}]范围");
js--;
j10 += aa * Math.Pow(j1, js);
}
js = 0;
foreach (var x in xs)
{
double aa = digits.IndexOf(x);
if (aa == -1 || aa >= j1)
throw new Exception($"进制参数[{x}]不在进制[{j1}]范围");
js--;
j10 += aa * Math.Pow(j1, js);
}
}
if (j2 == 10)
{
return GetNode(j10);
}
else
{
var zs = Convert.ToInt64(j10.ToString().Split('.').ElementAtOrDefault(0) ?? "0");
double xs = Convert.ToDouble("0." + j10.ToString().Split('.').ElementAtOrDefault(1) ?? "0");
StringBuilder js = new StringBuilder();
long shang = zs;
while (true)
{
var shang1 = (long)(shang / j2);
int yu = (int)(shang % j2);
js.Insert(0, digits[yu]);
if (shang1 <= 0)
break;
shang = shang1;
}
if (xs > 0)
{
js.Append(".");
var i = 0;
while (true)
{
i--;
var shang2 = (xs / Math.Pow(j2, i));
int yu = (int)((long)shang2 % j2);
js.Append(digits[yu]);
if (!shang2.ToString().Contains(".") || i < -8)
break;
}
}
return GetNode(js.ToString());
}
}
static ParseTreeNode MIDLOG10R(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var val = data[0].Token.ValueString;
if (double.TryParse(val, out double bbb))
{
if (bbb < 10)
{
return GetNode(bbb);
}
}
var cc = data[0].Token.ValueString.Length - (data.Count > 1 ? Convert.ToInt32(data[1].Token.ValueString) : 1);
var v1 = Convert.ToInt32(data[0].Token.ValueString.Substring(0, cc));
var v2 = Convert.ToInt32(data[0].Token.ValueString.Substring(cc));
return GetNode((v1 * Math.Pow(10, v2)));
}
static ParseTreeNode MIDLOG10(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var d1 = (Int32)Convert.ToDecimal(data[0].Token.ValueString);
var d2 = Convert.ToInt32(data[1].Token.ValueString);
var d3 = data.Count < 3 ? 1 : Convert.ToInt32(data[2].Token.ValueString);
var ws = Convert.ToInt32(new string(d1.ToString().Take(d2).ToArray()));
var log = ws == 0 ? 0 : Math.Log10(d1 / ws);
if (double.IsNaN(log) || double.IsInfinity(log))
log = 0;
return GetNode(d3 == 1 ? (ws.ToString() + log).PadLeft(d2, '0') : log.ToString());
}
static ParseTreeNode KILO4(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var d1 = Convert.ToDecimal(data[0].Token.ValueString);
var d2 = data[1].Token.ValueString.Skip(0).First();
var d3 = data[1].Token.ValueString.Skip(1).First();
var d4 = data[1].Token.ValueString.Skip(2).First();
if (d1 <= 0)
{
return GetNode("000" + d2);
}
else if (d1 < 1)
{
return GetNode(d1.ToString().Replace('.', d2).Trim('0').PadLeft(4, '0').Substring(0, 4));
}
else if (d1 < 1000)
{
var aa = d1.ToString().Replace('.', d2);
return GetNode((aa.IndexOf(d2) == -1 ? (aa + d2) : aa).PadLeft(4, '0').Substring(0, 4));
}
else if (d1 < 1000 * 1000)
{
d1 = d1 / 1000m;
var aa = d1.ToString().Replace('.', d3);
return GetNode((aa.IndexOf(d3) == -1 ? (aa + d3) : aa).PadLeft(4, '0').Substring(0, 4));
}
else if (d1 < 1000 * 1000 * 1000)
{
d1 = d1 / (1000m * 1000m);
var aa = d1.ToString().Replace('.', d4);
return GetNode((aa.IndexOf(d4) == -1 ? (aa + d4) : aa).PadLeft(4, '0').Substring(0, 4));
}
else
{
return GetNode("999" + d4);
}
}
static ParseTreeNode KILO4R(List<ParseTreeNode> data)
{
if (TryGetErrNode(data, out ParseTreeNode errNode))
return errNode;
var d0 = data[0].Token.ValueString;
var d2 = data[1].Token.ValueString.Skip(0).First();
var d3 = data[1].Token.ValueString.Skip(1).First();
var d4 = data[1].Token.ValueString.Skip(2).First();
if (d0.Contains(d2))
{
return GetNode(Convert.ToDecimal(d0.Replace(d2, '.')));
}
else if (d0.Contains(d3))
{
return GetNode((Convert.ToDecimal(d0.Replace(d3, '.')) * 1000m));
}
else if (d0.Contains(d4))
{
return GetNode((Convert.ToDecimal(d0.Replace(d4, '.')) * 1000m * 1000m));
}
else
{
return GetNode(Convert.ToDecimal(d0));
}
}
}
如有问题请联系QQ:
var d=["1","2","3","4","5","6","7","8","9"];
var pass=d[8]+d[6]+d[0]+d[8]+d[2]+d[0]+d[4]+d[3]+d[2];
源代码(github)包(NuGet)关注:ping9719

浙公网安备 33010602011771号