예제 #1
0
파일: makers.go 프로젝트: Immortalin/gisp
func makeIfStmtFunc(node *parser.CallNode) ast.Expr {
	var elseBody ast.Stmt
	if len(node.Args) > 2 {
		elseBody = makeBlockStmt(h.S(makeReturnStmt(h.E(EvalExpr(node.Args[2])))))
	} else {
		elseBody = makeBlockStmt(h.S(makeReturnStmt(h.E(ast.NewIdent("nil")))))
	}

	cond := EvalExpr(node.Args[0])
	ifBody := makeBlockStmt(h.S(makeReturnStmt(h.E(EvalExpr(node.Args[1])))))

	ifStmt := makeIfStmt(cond, ifBody, elseBody)
	fnBody := makeBlockStmt(h.S(ifStmt))

	returnList := makeFieldList([]*ast.Field{makeField(nil, anyType)})
	fnType := makeFuncType(returnList, nil)

	fn := makeFuncLit(fnType, fnBody)

	return makeFuncCall(fn, h.EmptyE())
}
예제 #2
0
파일: makers.go 프로젝트: Immortalin/gisp
func makeLetFun(node *parser.CallNode) ast.Expr {
	bindings := makeBindings(node.Args[0].(*parser.VectorNode), token.DEFINE)

	body := append(bindings, wrapExprsWithStmt(EvalExprs(node.Args[1:]))...)
	body[len(body)-1] = makeReturnStmt(h.E(body[len(body)-1].(*ast.ExprStmt).X))

	fieldList := makeFieldList([]*ast.Field{makeField(nil, anyType)})
	typ := makeFuncType(fieldList, nil)
	fn := makeFuncLit(typ, makeBlockStmt(body))

	return makeFuncCall(fn, h.EmptyE())
}
예제 #3
0
파일: makers.go 프로젝트: Immortalin/gisp
func makeBindings(bindings *parser.VectorNode, assignmentType token.Token) []ast.Stmt {
	assignments := make([]ast.Stmt, len(bindings.Nodes))

	for i, bind := range bindings.Nodes {
		b := bind.(*parser.VectorNode)
		idents := b.Nodes[:len(b.Nodes)-1]

		vars := make([]ast.Expr, len(idents))

		for j, ident := range idents {
			vars[j] = makeIdomaticSelector(ident.(*parser.IdentNode).Ident)
		}

		assignments[i] = makeAssignStmt(vars, h.E(EvalExpr(b.Nodes[len(b.Nodes)-1])), assignmentType)
	}

	return assignments
}