evaluateIter method

EvaluateOutput evaluateIter(
  1. EvaluateInput input
)

Implementation

EvaluateOutput evaluateIter(EvaluateInput input) {
  final iter = input.expr.iter;
  final forPos = iter.posIdent;
  final forElem = iter.elemIdent;
  final inVal =
      evaluateExpr(EvaluateInput(defStack: input.defStack, expr: iter.col));

  switch (inVal.value.type) {
    case Value_Type.STR:
      final result = <Value>[];
      for (final (i, c) in inVal.value.str.runes.indexed) {
        final st = input.defStack
            .register(newDefinition(
                input.expr.path, forPos, numValue(i.toDouble())))
            .register(newDefinition(
                input.expr.path, forElem, strValue(String.fromCharCode(c))));
        if (iter.hasIf_5()) {
          final ifVal =
              evaluateExpr(EvaluateInput(defStack: st, expr: iter.if_5));
          if (ifVal.status != EvaluateOutput_Status.OK) {
            return ifVal;
          }
          if (ifVal.value.type != Value_Type.BOOL) {
            return _errorUnexpectedType(
                iter.if_5.path, ifVal.value.type, [Value_Type.BOOL]);
          }
          if (!ifVal.value.bool_2) {
            continue;
          }
        }
        final v = evaluateExpr(EvaluateInput(defStack: st, expr: iter.do_4));
        if (v.status != EvaluateOutput_Status.OK) {
          return v;
        }
        result.add(v.value);
      }
      return EvaluateOutput(value: arrValue(result));
    case Value_Type.ARR:
      final result = <Value>[];
      for (final (i, elemVal) in inVal.value.arr.indexed) {
        final st = input.defStack
            .register(newDefinition(
                input.expr.path, forPos, numValue(i.toDouble())))
            .register(newDefinition(input.expr.path, forElem, elemVal));
        if (iter.hasIf_5()) {
          final ifVal =
              evaluateExpr(EvaluateInput(defStack: st, expr: iter.if_5));
          if (ifVal.status != EvaluateOutput_Status.OK) {
            return ifVal;
          }
          if (ifVal.value.type != Value_Type.BOOL) {
            return _errorUnexpectedType(
                iter.if_5.path, ifVal.value.type, [Value_Type.BOOL]);
          }
          if (!ifVal.value.bool_2) {
            continue;
          }
        }
        final v = evaluateExpr(EvaluateInput(defStack: st, expr: iter.do_4));
        if (v.status != EvaluateOutput_Status.OK) {
          return v;
        }
        result.add(v.value);
      }
      return EvaluateOutput(value: arrValue(result));
    case Value_Type.OBJ:
      final result = <String, Value>{};
      for (final key in _sortedKeys(inVal.value.obj)) {
        final st = input.defStack
            .register(newDefinition(input.expr.path, forPos, strValue(key)))
            .register(newDefinition(
                input.expr.path, forElem, inVal.value.obj[key]!));
        if (iter.hasIf_5()) {
          final ifVal =
              evaluateExpr(EvaluateInput(defStack: st, expr: iter.if_5));
          if (ifVal.status != EvaluateOutput_Status.OK) {
            return ifVal;
          }
          if (ifVal.value.type != Value_Type.BOOL) {
            return _errorUnexpectedType(
                iter.if_5.path, ifVal.value.type, [Value_Type.BOOL]);
          }
          if (!ifVal.value.bool_2) {
            continue;
          }
        }
        final v = evaluateExpr(EvaluateInput(defStack: st, expr: iter.do_4));
        if (v.status != EvaluateOutput_Status.OK) {
          return v;
        }
        result[key] = v.value;
      }
      return EvaluateOutput(value: objValue(result));
    default:
      return _errorUnexpectedType(iter.col.path, inVal.value.type,
          [Value_Type.STR, Value_Type.ARR, Value_Type.OBJ]);
  }
}