Untitled
unknown
csharp
2 years ago
3.4 kB
10
Indexable
Never
class NumberOperatorWithTimeAndString : IYCNumberOperator<object> { public static readonly YCBasicNumberOperators.Double Base = YCBasicNumberOperators.Double.Instance; public bool TryParseConstant(string repr, out object value) { //first try redirecting to the base implementation for type double if (Base.TryParseConstant(repr, out var unboxedValue)) { value = unboxedValue; return true; } return TryParseStringConstant(repr, out value); } //just redirect to the base implementation for type double public FormatException ValidateIdentifier(string identifier) => Base.ValidateIdentifier(identifier); //just a really basic way of recognizing a single-quote string and getting its contents bool TryParseStringConstant(string repr, out object value) { if (repr.Length >= 2 && repr[0] == '\'' && repr[^1] == '\'') { value = repr.Substring(1, repr.Length - 2).Replace("\\'", "'").Replace("''", "'"); //replace escaped quotes and double quotes inside the raw string with just quotes return true; } value = null; return false; } object UnsupportedType(object a, object b) => throw new ArgumentException($"Unsupported operand type of '{a?.GetType()}' and '{b?.GetType()}'"); public object Add(object a, object b) => a switch { string s => s + b, double d => d + (double)b, TimeSpan t => t + (TimeSpan)b, _ => UnsupportedType(a, b) }; public object Subtract(object a, object b) => a switch { double d => d - (double)b, TimeSpan t => t - (TimeSpan)b, _ => UnsupportedType(a, b) }; public object Multiply(object a, object b) => (double)a * (double)b; public object Divide(object a, object b) => (double)a / (double)b; public object Modulo(object a, object b) => (double)a % (double)b; public object UnaryMinus(object a) => -(double)a; public object Power(object a, object power) => Base.Power((double)a, (double)power); public object IsEqual(object a, object b) => a.Equals(b); public object IsLess(object a, object b) => Base.IsLess((double)a, (double)b); public object IsLessOrEqual(object a, object b) => Base.IsLessOrEqual((double)a, (double)b); public bool IsTrue(object a) => Base.IsTrue((double)a); public object NegateLogical(object a) => Base.NegateLogical((double)a); } public static class UsageSample { public static void Main() { var compiler = IYCCompiler<object>.Make(new NumberOperatorWithTimeAndString()); var calculator = IYoowzxCalculator<object>.Make(compiler: compiler); calculator.AddFunction<Func<object, object>>("fromSeconds", d => TimeSpan.FromSeconds((double)d)); var f = calculator.Compile<Func<object, object, object>> ("f(mins, secs) := 'This much seconds: ' + (fromSeconds(mins*60 + secs) + fromSeconds(10)) + ' seconds'"); Console.WriteLine(f(2D, 43D)); //make sure you're passing args of type double and not int } }