diff --git a/go/src/miller/dsl/cst/evaluable.go b/go/src/miller/dsl/cst/evaluable.go index 09940c8a6..f79c55e43 100644 --- a/go/src/miller/dsl/cst/evaluable.go +++ b/go/src/miller/dsl/cst/evaluable.go @@ -4,6 +4,7 @@ import ( "errors" "miller/dsl" + "miller/lib" ) // ================================================================ @@ -36,6 +37,8 @@ func BuildEvaluableNode(astNode *dsl.ASTNode) (IEvaluable, error) { case dsl.NodeTypeArraySliceAccess: return BuildArraySliceAccessNode(astNode) + case dsl.NodeTypeIndirectFieldName: + return BuildIndirectFieldNameNode(astNode) } // xxx if/while/etc @@ -46,3 +49,38 @@ func BuildEvaluableNode(astNode *dsl.ASTNode) (IEvaluable, error) { "CST BuildEvaluableNode: unhandled AST node type " + string(astNode.Type), ) } + +// ---------------------------------------------------------------- +type IndirectFieldNameNode struct { + fieldNameEvaluable IEvaluable +} + +func BuildIndirectFieldNameNode(astNode *dsl.ASTNode) (*IndirectFieldNameNode, error) { + lib.InternalCodingErrorIf(astNode.Type != dsl.NodeTypeIndirectFieldName) + lib.InternalCodingErrorIf(astNode.Children == nil) + lib.InternalCodingErrorIf(len(astNode.Children) != 1) + fieldNameEvaluable, err := BuildEvaluableNode(astNode.Children[0]) + if err != nil { + return nil, err + } + return &IndirectFieldNameNode{ + fieldNameEvaluable: fieldNameEvaluable, + }, nil +} +func (this *IndirectFieldNameNode) Evaluate(state *State) lib.Mlrval { // xxx err + fieldName := this.fieldNameEvaluable.Evaluate(state) + // xxx handle int-index too. needs a centralized place for that. + if fieldName.IsAbsent() { + return lib.MlrvalFromAbsent() + } + if !fieldName.IsString() { + return lib.MlrvalFromError() // xxx needs err-return? + } + skey := fieldName.String() + value := state.Inrec.Get(&skey) + if value == nil { + return lib.MlrvalFromAbsent() + } else { + return *value + } +} diff --git a/go/src/miller/dsl/cst/leaves.go b/go/src/miller/dsl/cst/leaves.go index 97828a662..dca4fd732 100644 --- a/go/src/miller/dsl/cst/leaves.go +++ b/go/src/miller/dsl/cst/leaves.go @@ -46,12 +46,6 @@ func BuildLeafNode( case dsl.NodeTypePanic: return BuildPanicNode(), nil break - - // xxx more - // case NodeTypeIndirectFieldName: - // return lib.MlrvalFromError(), errors.New("unhandled1") - // break - } return nil, errors.New( diff --git a/go/todo.txt b/go/todo.txt index 111e50cb7..ad907a748 100644 --- a/go/todo.txt +++ b/go/todo.txt @@ -2,9 +2,8 @@ TOP OF LIST: * tuesday: - o indexed-lvalue assignment ops - ! Execute -> error not void o computed/braced srec on both sides + o indexed-lvalue assignment ops -- need ints too o oosvars at state -- easy mlrmap now o $[1] is easier now; needn't $[[1]] o $[[[ ]]] ... ? diff --git a/go/u/try-cst b/go/u/try-cst index 08ead0d6a..85544c58a 100755 --- a/go/u/try-cst +++ b/go/u/try-cst @@ -145,3 +145,5 @@ echo; run_mlr --from u/s.dkvp --idkvp --ojson put '$* = {"s": 7, "t": 8}' echo; run_mlr --from u/s.dkvp --idkvp --ojson put '$*["st"] = 78' echo; run_mlr --from u/s.dkvp --idkvp --ojson put '$*["a"] = 78' echo; run_mlr --from u/s.dkvp --idkvp --ojson put '$*["a"] = {}' +echo; run_mlr --from u/s.dkvp --idkvp --opprint put -v '$new = $["a"]' +echo; run_mlr --from u/s.dkvp --idkvp --opprint put -v '$["new"] = $a' diff --git a/go/u/try-cst.out b/go/u/try-cst.out index 846234b7c..06d1bfd48 100644 --- a/go/u/try-cst.out +++ b/go/u/try-cst.out @@ -1417,3 +1417,39 @@ mlr --from u/s.dkvp --idkvp --ojson put $*["a"] = {} "x": 0.38139939387114097, "y": 0.13418874328430463 } + + +---------------------------------------------------------------- +mlr --from u/s.dkvp --idkvp --opprint put -v $new = $["a"] +DSL EXPRESSION: +$new = $["a"] +RAW AST: +* StatementBlock + * Assignment "=" + * DirectFieldName "new" + * IndirectFieldName "$[" + * StringLiteral "a" + +a b i x y new +pan pan 1 0.3467901443380824 0.7268028627434533 pan +eks pan 2 0.7586799647899636 0.5221511083334797 eks +wye wye 3 0.20460330576630303 0.33831852551664776 wye +eks wye 4 0.38139939387114097 0.13418874328430463 eks + + +---------------------------------------------------------------- +mlr --from u/s.dkvp --idkvp --opprint put -v $["new"] = $a +DSL EXPRESSION: +$["new"] = $a +RAW AST: +* StatementBlock + * Assignment "=" + * IndirectFieldName "$[" + * StringLiteral "new" + * DirectFieldName "a" + +a b i x y new +pan pan 1 0.3467901443380824 0.7268028627434533 pan +eks pan 2 0.7586799647899636 0.5221511083334797 eks +wye wye 3 0.20460330576630303 0.33831852551664776 wye +eks wye 4 0.38139939387114097 0.13418874328430463 eks