still WIP, FR works

This commit is contained in:
Vyacheslav Matyukhin 2022-09-11 20:57:28 +04:00
parent 7a29be3845
commit f2dccd4f1e
No known key found for this signature in database
GPG Key ID: 3D2A774C5489F96C
9 changed files with 77 additions and 65 deletions

View File

@ -135,23 +135,23 @@ export const ExpressionViewer: React.FC<Props> = ({ value, width }) => {
{() => value.value.toString()} {() => value.value.toString()}
</VariableBox> </VariableBox>
); );
case SqValueTag.Symbol: // case SqValueTag.Symbol:
return ( // return (
<VariableBox value={value} heading="Symbol"> // <VariableBox value={value} heading="Symbol">
{() => ( // {() => (
<> // <>
<span className="text-slate-500 mr-2">Undefined Symbol:</span> // <span className="text-slate-500 mr-2">Undefined Symbol:</span>
<span className="text-slate-600">{value.value}</span> // <span className="text-slate-600">{value.value}</span>
</> // </>
)} // )}
</VariableBox> // </VariableBox>
); // );
case SqValueTag.Call: // case SqValueTag.Call:
return ( // return (
<VariableBox value={value} heading="Call"> // <VariableBox value={value} heading="Call">
{() => value.value} // {() => value.value}
</VariableBox> // </VariableBox>
); // );
case SqValueTag.ArrayString: case SqValueTag.ArrayString:
return ( return (
<VariableBox value={value} heading="Array String"> <VariableBox value={value} heading="Array String">

View File

@ -14,7 +14,7 @@ let rec evaluate: T.reducerFn = (
expression, expression,
context context
) => { ) => {
Js.log(`reduce: ${expression->Reducer_Expression_T.toString}`) // Js.log(`reduce: ${expression->Reducer_Expression_T.toString}`)
switch expression { switch expression {
| T.EBlock(statements) => { | T.EBlock(statements) => {
let innerContext = {...context, bindings: context.bindings->Bindings.extend} let innerContext = {...context, bindings: context.bindings->Bindings.extend}
@ -25,12 +25,12 @@ let rec evaluate: T.reducerFn = (
} }
| T.EProgram(statements) => { | T.EProgram(statements) => {
Js.log(`bindings: ${context.bindings->Reducer_Bindings.toString}`) // Js.log(`bindings: ${context.bindings->Reducer_Bindings.toString}`)
let res = statements->Js.Array2.reduce( let res = statements->Js.Array2.reduce(
(acc, statement) => statement->evaluate(context), (acc, statement) => statement->evaluate(context),
T.IEvVoid T.IEvVoid
) )
Js.log(`bindings after: ${context.bindings->Reducer_Bindings.toString}`) // Js.log(`bindings after: ${context.bindings->Reducer_Bindings.toString}`)
res res
} }

View File

@ -43,11 +43,14 @@ let makeLambda = (
reducer(body, { bindings: localBindings, environment }) reducer(body, { bindings: localBindings, environment })
} }
LNoFFI({ {
context: bindings, // context: bindings,
body: lambda, body: lambda,
parameters, parameters,
}) }
} }
let makeFFILambda = () => raise(Not_found) let makeFFILambda = (body: Reducer_T.lambdaBody): Reducer_T.lambdaValue => {
body,
parameters: ["..."]
}

View File

@ -11,25 +11,10 @@ zeroOMoreArgumentsBlockOrExpression = innerBlockOrExpression / lambda
outerBlock outerBlock
= statements:array_statements finalExpression: (statementSeparator @expression)? = statements:array_statements finalExpression: (statementSeparator @expression)?
{ if (finalExpression) statements.push(finalExpression) { if (finalExpression) statements.push(finalExpression)
return h.nodeProgram(statements) } return h.nodeProgram(statements) }
// / '{' _nl finalExpression: expression _nl '}' / finalExpression: expression
// { return h.nodeBlock([finalExpression]) } { return h.nodeProgram([finalExpression]) }
// { if (finalExpression != null)
// {
// var newFinalExpression = h.makeFunctionCall('$_endOfOuterBlock_$', [h.nodeVoid(), finalExpression]);
// statements.push(newFinalExpression);
// }
// else
// {
// var newFinalStatement = h.makeFunctionCall('$_endOfOuterBlock_$', [h.nodeVoid(), h.nodeVoid()]);
// statements.push(newFinalStatement);
// }
// return h.nodeBlock(statements) }
// / finalExpression: expression
// {
// var newFinalExpression = h.makeFunctionCall('$_endOfOuterBlock_$', [h.nodeVoid(), finalExpression]);
// return h.nodeBlock([newFinalExpression])}
innerBlockOrExpression innerBlockOrExpression
= quotedInnerBlock = quotedInnerBlock

View File

@ -22,16 +22,13 @@ type rec value =
@genType.opaque and arrayValue = array<value> @genType.opaque and arrayValue = array<value>
@genType.opaque and map = Belt.Map.String.t<value> @genType.opaque and map = Belt.Map.String.t<value>
@genType.opaque and nameSpace = NameSpace(Belt.MutableMap.String.t<value>, option<nameSpace>) @genType.opaque and nameSpace = NameSpace(Belt.MutableMap.String.t<value>, option<nameSpace>)
and lambdaBody = (array<value>, environment, reducerFn) => value
@genType.opaque @genType.opaque
and lambdaValue = and lambdaValue = {
| LNoFFI({
parameters: array<string>, parameters: array<string>,
context: nameSpace, // context: nameSpace,
body: (array<value>, environment, reducerFn) => value, body: (array<value>, environment, reducerFn) => value,
}) }
| LFFI({
body: (array<value>, environment, reducerFn) => value,
})
@genType.opaque and lambdaDeclaration = Declaration.declaration<lambdaValue> @genType.opaque and lambdaDeclaration = Declaration.declaration<lambdaValue>
and expression = and expression =
| EBlock(array<expression>) | EBlock(array<expression>)

View File

@ -49,10 +49,7 @@ and toStringDate = date => DateTime.Date.toString(date)
and toStringDeclaration = d => Declaration.toString(d, r => toString(IEvLambda(r))) and toStringDeclaration = d => Declaration.toString(d, r => toString(IEvLambda(r)))
and toStringDistribution = dist => GenericDist.toString(dist) and toStringDistribution = dist => GenericDist.toString(dist)
and toStringLambda = (lambdaValue: T.lambdaValue) => and toStringLambda = (lambdaValue: T.lambdaValue) =>
switch lambdaValue { `lambda(${Js.Array2.toString(lambdaValue.parameters)}=>internal code)`
| LNoFFI({ parameters }) => `lambda(${parameters->Js.Array2.toString}=>internal code)` // TODO - serialize code too?
| LFFI(_) => `standard function` // TODO - serialize name, etc?
}
and toStringFunction = (lambdaValue: T.lambdaValue) => `function(${Js.Array2.toString(lambdaValue.parameters)})` and toStringFunction = (lambdaValue: T.lambdaValue) => `function(${Js.Array2.toString(lambdaValue.parameters)})`
and toStringNumber = aNumber => Js.String.make(aNumber) and toStringNumber = aNumber => Js.String.make(aNumber)
and toStringRecord = aMap => aMap->toStringMap and toStringRecord = aMap => aMap->toStringMap

View File

@ -1,4 +1,34 @@
let internalStdLib: Reducer_Bindings.t = let internalStdLib: Reducer_Bindings.t = {
Reducer_Bindings.makeEmptyBindings() let res = Reducer_Bindings.makeEmptyBindings()
->SquiggleLibrary_Math.makeBindings ->SquiggleLibrary_Math.makeBindings
->SquiggleLibrary_Versions.makeBindings ->SquiggleLibrary_Versions.makeBindings
let _ = res->Reducer_Bindings.set("multiply", Reducer_Expression_Lambda.makeFFILambda(
(arguments, _, _) => {
switch arguments {
| [IEvNumber(x), IEvNumber(y)] => IEvNumber(x *. y)
| _ => raise(Not_found)
}
}
)->Reducer_T.IEvLambda)
FunctionRegistry_Library.registry.fnNameDict->Js.Dict.keys->Js.Array2.forEach(
(name) => {
let _ = res->Reducer_Bindings.set(name, Reducer_Expression_Lambda.makeFFILambda(
(arguments, environment, reducer) => {
switch FunctionRegistry_Library.dispatch((name, arguments), environment, reducer) {
| Some(result) => {
switch result {
| Ok(value) => value
| Error(error) => error->Reducer_ErrorValue.ErrorException->raise
}
}
| None => Reducer_ErrorValue.RESymbolNotFound("Not found in registry")->Reducer_ErrorValue.ErrorException->raise
}
}
)->Reducer_T.IEvLambda)
}
)
res
}

View File

@ -193,7 +193,7 @@ let doLinkAndRun = (project: t, sourceId: string): unit => {
// FIXME: fill context with dependencies // FIXME: fill context with dependencies
// let continuation = linkDependencies(project, sourceId) // let continuation = linkDependencies(project, sourceId)
let newItem = project->getItem(sourceId)->ProjectItem.run(context) let newItem = project->getItem(sourceId)->ProjectItem.run(context)
Js.log("after run " ++ newItem.continuation->Reducer_Bindings.toString) // Js.log("after run " ++ newItem.continuation->Reducer_Bindings.toString)
project->setItem(sourceId, newItem) project->setItem(sourceId, newItem)
} }

View File

@ -1,9 +1,9 @@
@module("./MathjsWrapper.js") // @module("./MathjsWrapper.js")
external parseMathExt: string => Js.Json.t = "parseMath" // external parseMathExt: string => Js.Json.t = "parseMath"
let parseMath = (str: string): result<Js.Json.t, string> => // let parseMath = (str: string): result<Js.Json.t, string> =>
switch parseMathExt(str) { // switch parseMathExt(str) {
| exception Js.Exn.Error(err) => Error(Js.Exn.message(err) |> E.O.default("MathJS Parse Error")) // | exception Js.Exn.Error(err) => Error(Js.Exn.message(err) |> E.O.default("MathJS Parse Error"))
| exception _ => Error("MathJS Parse Error") // | exception _ => Error("MathJS Parse Error")
| j => Ok(j) // | j => Ok(j)
} // }