Expanding Standard Library
Some checks failed
Build / build (push) Successful in 37s
Tests / tests (push) Failing after 31s

Expanding functions in the standard library.
This commit is contained in:
Jordan Wages 2026-06-27 19:41:26 -05:00
commit 5556010c91
12 changed files with 366 additions and 3 deletions

View file

@ -0,0 +1,50 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace CSMic.StandardLibrary.Functions
{
public class Lerp: FunctionBase, ICodedFunction
{
public string Name
{
get
{
return "lerp";
}
}
public override IEnumerable<FunctionArgument> ExpectedArguments
{
get
{
yield return new FunctionArgument("start", FunctionValue.NUMBER);
yield return new FunctionArgument("end", FunctionValue.NUMBER);
yield return new FunctionArgument("ammount", FunctionValue.NUMBER);
}
}
public FunctionValue Execute(params FunctionArgument[] args)
{
return base.Execute(args, (_args) =>
{
var input = _args[0].Value;
var input2 = _args[1].Value;
var input3 = _args[2].Value;
decimal start = Convert.ToDecimal(input);
decimal end = Convert.ToDecimal(input2);
decimal ammount = Convert.ToDecimal(input3);
if (start == end)
{
return new FunctionValue(FunctionValueType.Numeric, start);
}
var lerp = start + (ammount * (end - start));
return new FunctionValue(FunctionValueType.Numeric, lerp);
});
}
}
}

View file

@ -0,0 +1,39 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace CSMic.StandardLibrary.Functions
{
public class Log: FunctionBase, ICodedFunction
{
public string Name
{
get
{
return "log";
}
}
public override IEnumerable<FunctionArgument> ExpectedArguments
{
get
{
yield return new FunctionArgument("value", FunctionValue.NUMBER);
yield return new FunctionArgument("base", FunctionValue.NUMBER);
}
}
public FunctionValue Execute(params FunctionArgument[] args)
{
return base.Execute(args, (_args) =>
{
var input = _args[0].Value;
var input2 = _args[1].Value;
double number = Convert.ToDouble(input.Value);
double _baseNumber = Convert.ToDouble(input2.Value);
return new FunctionValue(FunctionValueType.Numeric, Math.Log(number, _baseNumber));
});
}
}
}

View file

@ -0,0 +1,58 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace CSMic.StandardLibrary.Functions
{
public class Map: FunctionBase, ICodedFunction
{
public string Name
{
get
{
return "map";
}
}
public override IEnumerable<FunctionArgument> ExpectedArguments
{
get
{
yield return new FunctionArgument("value", FunctionValue.NUMBER);
yield return new FunctionArgument("oldMinimum", FunctionValue.NUMBER);
yield return new FunctionArgument("oldMaximum", FunctionValue.NUMBER);
yield return new FunctionArgument("newMinimum", FunctionValue.NUMBER);
yield return new FunctionArgument("newMaximum", FunctionValue.NUMBER);
}
}
public FunctionValue Execute(params FunctionArgument[] args)
{
return base.Execute(args, (_args) =>
{
var input = _args[0].Value;
var input2 = _args[1].Value;
var input3 = _args[2].Value;
var input4 = _args[3].Value;
var input5 = _args[4].Value;
decimal number = Convert.ToDecimal(input);
decimal oldMinimum = Convert.ToDecimal(input2);
decimal oldMaximum = Convert.ToDecimal(input3);
decimal newMinimum = Convert.ToDecimal(input4);
decimal newMaximum = Convert.ToDecimal(input5);
if (oldMinimum == oldMaximum)
{
return FunctionValue.ZERO;
}
var oldRange = oldMaximum - oldMinimum;
var newRange = newMaximum - newMinimum;
var newNumber = newMinimum + ((number - oldMinimum) * (newRange / oldRange));
return new FunctionValue(FunctionValueType.Numeric, newNumber);
});
}
}
}

View file

@ -0,0 +1,36 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace CSMic.StandardLibrary.Functions
{
public class Natural_Log: FunctionBase, ICodedFunction
{
public string Name
{
get
{
return "ln";
}
}
public override IEnumerable<FunctionArgument> ExpectedArguments
{
get
{
yield return new FunctionArgument("value", FunctionValue.NUMBER);
}
}
public FunctionValue Execute(params FunctionArgument[] args)
{
return base.Execute(args, (_args) =>
{
var input = _args[0].Value;
double number = Convert.ToDouble(input.Value);
return new FunctionValue(FunctionValueType.Numeric, Math.Log(number));
});
}
}
}

View file

@ -0,0 +1,50 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace CSMic.StandardLibrary.Functions
{
public class Normalize : FunctionBase, ICodedFunction
{
public string Name
{
get
{
return "normalize";
}
}
public override IEnumerable<FunctionArgument> ExpectedArguments
{
get
{
yield return new FunctionArgument("value", FunctionValue.NUMBER);
yield return new FunctionArgument("minimum", FunctionValue.NUMBER);
yield return new FunctionArgument("maximum", FunctionValue.NUMBER);
}
}
public FunctionValue Execute(params FunctionArgument[] args)
{
return base.Execute(args, (_args) =>
{
var input = _args[0].Value;
var input2 = _args[1].Value;
var input3 = _args[2].Value;
decimal number = Convert.ToDecimal(input);
decimal minimum = Convert.ToDecimal(input2);
decimal maximum = Convert.ToDecimal(input3);
if (minimum == maximum)
{
return FunctionValue.ZERO;
}
var normalization = (number - minimum) / (maximum - minimum);
return new FunctionValue(FunctionValueType.Numeric, normalization);
});
}
}
}

View file

@ -58,7 +58,7 @@ namespace CSMic.StandardLibrary.Functions.NumberTheory
decimal first = Convert.ToDecimal(inputFirst.Value); decimal first = Convert.ToDecimal(inputFirst.Value);
decimal second = Convert.ToDecimal(inputSecond.Value); decimal second = Convert.ToDecimal(inputSecond.Value);
if (first <= 0 || second <= 0) if (first <= 0 && second <= 0)
{ {
return FunctionValue.ZERO; return FunctionValue.ZERO;
} }

View file

@ -0,0 +1,39 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace CSMic.StandardLibrary.Functions
{
public class Power : FunctionBase, ICodedFunction
{
public string Name
{
get
{
return "pow";
}
}
public override IEnumerable<FunctionArgument> ExpectedArguments
{
get
{
yield return new FunctionArgument("base", FunctionValue.NUMBER);
yield return new FunctionArgument("exponent", FunctionValue.NUMBER);
}
}
public FunctionValue Execute(params FunctionArgument[] args)
{
return base.Execute(args, (_args) =>
{
var input = _args[0].Value;
var input2 = _args[1].Value;
double _base = Convert.ToDouble(input.Value);
double exponent = Convert.ToDouble(input2.Value);
return new FunctionValue(FunctionValueType.Numeric, Math.Pow(_base, exponent));
});
}
}
}

View file

@ -0,0 +1,46 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace CSMic.StandardLibrary.Functions
{
public class SmoothStep : FunctionBase, ICodedFunction
{
public string Name
{
get
{
return "lerp";
}
}
public override IEnumerable<FunctionArgument> ExpectedArguments
{
get
{
yield return new FunctionArgument("startEdge", FunctionValue.NUMBER);
yield return new FunctionArgument("endEdge", FunctionValue.NUMBER);
yield return new FunctionArgument("value", FunctionValue.NUMBER);
}
}
public FunctionValue Execute(params FunctionArgument[] args)
{
return base.Execute(args, (_args) =>
{
var input = _args[0].Value;
var input2 = _args[1].Value;
var input3 = _args[2].Value;
decimal startEdge = Convert.ToDecimal(input);
decimal endEdge = Convert.ToDecimal(input2);
decimal value = Convert.ToDecimal(input3);
var normalization = Math.Clamp((value - startEdge) / (endEdge - startEdge), 0, 1);
var polynomialization = normalization * normalization * (3 - (2 * normalization));
return new FunctionValue(FunctionValueType.Numeric, polynomialization);
});
}
}
}

View file

@ -0,0 +1,36 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace CSMic.StandardLibrary.Functions
{
public class SquareRoot: FunctionBase, ICodedFunction
{
public string Name
{
get
{
return "sqrt";
}
}
public override IEnumerable<FunctionArgument> ExpectedArguments
{
get
{
yield return new FunctionArgument("value", FunctionValue.NUMBER);
}
}
public FunctionValue Execute(params FunctionArgument[] args)
{
return base.Execute(args, (_args) =>
{
var input = _args[0].Value;
double number = Convert.ToDouble(input.Value);
return new FunctionValue(FunctionValueType.Numeric, Math.Sqrt(number));
});
}
}
}

View file

@ -64,6 +64,7 @@ namespace CSMic.StandardLibrary
inputInterpreter.RegisterFunction(new Sign()); inputInterpreter.RegisterFunction(new Sign());
inputInterpreter.RegisterFunction(new Min()); inputInterpreter.RegisterFunction(new Min());
inputInterpreter.RegisterFunction(new Max()); inputInterpreter.RegisterFunction(new Max());
inputInterpreter.RegisterFunction(new SquareRoot());
} }
/// <summary> Initializes the angle-related functions. </summary> /// <summary> Initializes the angle-related functions. </summary>
@ -177,7 +178,7 @@ namespace CSMic.StandardLibrary
inputInterpreter.Interpret("tau :: 6.2831853071795862"); inputInterpreter.Interpret("tau :: 6.2831853071795862");
inputInterpreter.Interpret("phi :: 1.6180339887498948"); inputInterpreter.Interpret("phi :: 1.6180339887498948");
inputInterpreter.Interpret("goldenratio :: 1.6180339887498948"); inputInterpreter.Interpret("goldenratio :: 1.6180339887498948");
inputInterpreter.Interpret("eurler :: 0.5772156649015329"); inputInterpreter.Interpret("euler :: 0.5772156649015329");
inputInterpreter.Interpret("omega :: 0.5671432904097839"); inputInterpreter.Interpret("omega :: 0.5671432904097839");
} }
} }

View file

@ -34,7 +34,7 @@ public class NumberTheoryFunctionsTests
{ {
AssertSuccess(_interp.Interpret("gcd(54, 24)"), 6m, _interp); AssertSuccess(_interp.Interpret("gcd(54, 24)"), 6m, _interp);
AssertSuccess(_interp.Interpret("gcd(7, 3)"), 1m, _interp); AssertSuccess(_interp.Interpret("gcd(7, 3)"), 1m, _interp);
AssertSuccess(_interp.Interpret("gcd(0, 5)"), 0m, _interp); AssertSuccess(_interp.Interpret("gcd(0, 5)"), 5m, _interp);
AssertSuccess(_interp.Interpret("gcd(5.5, 2)"), 0m, _interp); AssertSuccess(_interp.Interpret("gcd(5.5, 2)"), 0m, _interp);
} }

View file

@ -90,6 +90,14 @@ public class StdlibFunctionsTests
AssertSuccess(result, expected, _interp); AssertSuccess(result, expected, _interp);
} }
[TestCase("sqrt(25)", 5)]
[TestCase("sqrt(1)", 1)]
public void Sqrt_Works(string expr, decimal expected)
{
var result = _interp.Interpret(expr);
AssertSuccess(result, expected, _interp);
}
[TestCase("pi", "3.1415926535897931")] [TestCase("pi", "3.1415926535897931")]
[TestCase("e", "2.7182818284590451")] [TestCase("e", "2.7182818284590451")]
[TestCase("tau", "6.2831853071795862")] [TestCase("tau", "6.2831853071795862")]