1 // Copyright 2012 The Go Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style
3 // license that can be found in the LICENSE file.
16 // This example demonstrates how to inspect the AST of a Go program.
17 func ExampleInspect() {
18 // src is the input for which we want to inspect the AST.
25 // Create the AST by parsing src.
26 fset := token.NewFileSet() // positions are relative to fset
27 f, err := parser.ParseFile(fset, "src.go", src, 0)
32 // Inspect the AST and print all identifiers and literals.
33 ast.Inspect(f, func(n ast.Node) bool {
35 switch x := n.(type) {
42 fmt.Printf("%s:\t%s\n", fset.Position(n.Pos()), s)
58 // This example shows what an AST looks like when printed for debugging.
60 // src is the input for which we want to print the AST.
64 println("Hello, World!")
68 // Create the AST by parsing src.
69 fset := token.NewFileSet() // positions are relative to fset
70 f, err := parser.ParseFile(fset, "", src, 0)
81 // 2 . Name: *ast.Ident {
85 // 6 . Decls: []ast.Decl (len = 1) {
86 // 7 . . 0: *ast.FuncDecl {
87 // 8 . . . Name: *ast.Ident {
88 // 9 . . . . NamePos: 3:6
89 // 10 . . . . Name: "main"
90 // 11 . . . . Obj: *ast.Object {
91 // 12 . . . . . Kind: func
92 // 13 . . . . . Name: "main"
93 // 14 . . . . . Decl: *(obj @ 7)
96 // 17 . . . Type: *ast.FuncType {
97 // 18 . . . . Func: 3:1
98 // 19 . . . . Params: *ast.FieldList {
99 // 20 . . . . . Opening: 3:10
100 // 21 . . . . . Closing: 3:11
103 // 24 . . . Body: *ast.BlockStmt {
104 // 25 . . . . Lbrace: 3:13
105 // 26 . . . . List: []ast.Stmt (len = 1) {
106 // 27 . . . . . 0: *ast.ExprStmt {
107 // 28 . . . . . . X: *ast.CallExpr {
108 // 29 . . . . . . . Fun: *ast.Ident {
109 // 30 . . . . . . . . NamePos: 4:2
110 // 31 . . . . . . . . Name: "println"
111 // 32 . . . . . . . }
112 // 33 . . . . . . . Lparen: 4:9
113 // 34 . . . . . . . Args: []ast.Expr (len = 1) {
114 // 35 . . . . . . . . 0: *ast.BasicLit {
115 // 36 . . . . . . . . . ValuePos: 4:10
116 // 37 . . . . . . . . . Kind: STRING
117 // 38 . . . . . . . . . Value: "\"Hello, World!\""
118 // 39 . . . . . . . . }
119 // 40 . . . . . . . }
120 // 41 . . . . . . . Ellipsis: -
121 // 42 . . . . . . . Rparen: 4:25
125 // 46 . . . . Rbrace: 5:1
129 // 50 . FileStart: 1:1
131 // 52 . Scope: *ast.Scope {
132 // 53 . . Objects: map[string]*ast.Object (len = 1) {
133 // 54 . . . "main": *(obj @ 11)
136 // 57 . Unresolved: []*ast.Ident (len = 1) {
137 // 58 . . 0: *(obj @ 29)
142 // This example illustrates how to remove a variable declaration
143 // in a Go program while maintaining correct comment association
144 // using an ast.CommentMap.
145 func ExampleCommentMap() {
146 // src is the input for which we create the AST that we
147 // are going to manipulate.
149 // This is the package comment.
152 // This comment is associated with the hello constant.
153 const hello = "Hello, World!" // line comment 1
155 // This comment is associated with the foo variable.
156 var foo = hello // line comment 2
158 // This comment is associated with the main function.
160 fmt.Println(hello) // line comment 3
164 // Create the AST by parsing src.
165 fset := token.NewFileSet() // positions are relative to fset
166 f, err := parser.ParseFile(fset, "src.go", src, parser.ParseComments)
171 // Create an ast.CommentMap from the ast.File's comments.
172 // This helps keeping the association between comments
174 cmap := ast.NewCommentMap(fset, f, f.Comments)
176 // Remove the first variable declaration from the list of declarations.
177 for i, decl := range f.Decls {
178 if gen, ok := decl.(*ast.GenDecl); ok && gen.Tok == token.VAR {
179 copy(f.Decls[i:], f.Decls[i+1:])
180 f.Decls = f.Decls[:len(f.Decls)-1]
185 // Use the comment map to filter comments that don't belong anymore
186 // (the comments associated with the variable declaration), and create
187 // the new comments list.
188 f.Comments = cmap.Filter(f).Comments()
190 // Print the modified AST.
191 var buf strings.Builder
192 if err := format.Node(&buf, fset, f); err != nil {
195 fmt.Printf("%s", buf.String())
198 // // This is the package comment.
201 // // This comment is associated with the hello constant.
202 // const hello = "Hello, World!" // line comment 1
204 // // This comment is associated with the main function.
206 // fmt.Println(hello) // line comment 3