Commit 31de4d4c authored by Robert Griesemer's avatar Robert Griesemer

improved formatting of import declarations and

multi-line expressions with comments

Fixes #414.

R=rsc
https://golang.org/cl/179047
parent 2a52782f
...@@ -141,6 +141,27 @@ const ( ...@@ -141,6 +141,27 @@ const (
) )
// Obtain a (single) token position before the next comment.
// Use this function to correct a token position such that the
// token is placed before the next comment (which may be a line
// comment introducing a newline and possibly introducing a
// semicolon). Use moveCommentsAfter() to move a comment past
// more than a single token. beforeComment() is preferable if
// if can be used as it produces better results.
//
// Remove this after transitioning to new semicolon syntax and
// some reasonable grace period (12/11/09).
func (p *printer) beforeComment(pos token.Position) token.Position {
if p.comment != nil {
p := p.comment.List[0].Position;
if !pos.IsValid() || pos.Offset > p.Offset {
return p
}
}
return pos;
}
// Print a list of expressions. If the list spans multiple // Print a list of expressions. If the list spans multiple
// source lines, the original line breaks are respected between // source lines, the original line breaks are respected between
// expressions. Sets multiLine to true if the list spans multiple // expressions. Sets multiLine to true if the list spans multiple
...@@ -200,7 +221,7 @@ func (p *printer) exprList(prev token.Position, list []ast.Expr, depth int, mode ...@@ -200,7 +221,7 @@ func (p *printer) exprList(prev token.Position, list []ast.Expr, depth int, mode
line = x.Pos().Line; line = x.Pos().Line;
if i > 0 { if i > 0 {
if mode&plusSep != 0 { if mode&plusSep != 0 {
p.print(blank, token.ADD) p.print(blank, p.beforeComment(noPos), token.ADD)
} }
if mode&commaSep != 0 { if mode&commaSep != 0 {
p.print(token.COMMA) p.print(token.COMMA)
...@@ -583,7 +604,7 @@ func (p *printer) binaryExpr(x *ast.BinaryExpr, prec1, cutoff, depth int, multiL ...@@ -583,7 +604,7 @@ func (p *printer) binaryExpr(x *ast.BinaryExpr, prec1, cutoff, depth int, multiL
} }
xline := p.pos.Line; // before the operator (it may be on the next line!) xline := p.pos.Line; // before the operator (it may be on the next line!)
yline := x.Y.Pos().Line; yline := x.Y.Pos().Line;
p.print(x.OpPos, x.Op); p.print(p.beforeComment(x.OpPos), x.Op);
if xline != yline && xline > 0 && yline > 0 { if xline != yline && xline > 0 && yline > 0 {
// at least one line break, but respect an extra empty line // at least one line break, but respect an extra empty line
// in the source // in the source
...@@ -851,9 +872,11 @@ func (p *printer) moveCommentsAfter(pos token.Position) { ...@@ -851,9 +872,11 @@ func (p *printer) moveCommentsAfter(pos token.Position) {
// block prints an *ast.BlockStmt; it always spans at least two lines. // block prints an *ast.BlockStmt; it always spans at least two lines.
func (p *printer) block(s *ast.BlockStmt, indent int, moveComments bool) { func (p *printer) block(s *ast.BlockStmt, indent int, moveComments bool) {
if moveComments { if moveComments {
p.moveCommentsAfter(s.Pos()) p.print(p.beforeComment(s.Pos()))
} else {
p.print(s.Pos())
} }
p.print(s.Pos(), token.LBRACE); p.print(token.LBRACE);
p.stmtList(s.List, indent); p.stmtList(s.List, indent);
p.linebreak(s.Rbrace.Line, 1, maxStmtNewlines, ignore, true); p.linebreak(s.Rbrace.Line, 1, maxStmtNewlines, ignore, true);
p.print(s.Rbrace, token.RBRACE); p.print(s.Rbrace, token.RBRACE);
...@@ -1116,8 +1139,8 @@ func (p *printer) spec(spec ast.Spec, n int, context declContext, multiLine *boo ...@@ -1116,8 +1139,8 @@ func (p *printer) spec(spec ast.Spec, n int, context declContext, multiLine *boo
if s.Name != nil { if s.Name != nil {
p.expr(s.Name, multiLine); p.expr(s.Name, multiLine);
p.print(blank); p.print(blank);
p.moveCommentsAfter(s.Path[0].Pos());
} }
p.moveCommentsAfter(s.Path[0].Pos());
p.expr(&ast.StringList{s.Path}, multiLine); p.expr(&ast.StringList{s.Path}, multiLine);
comment = s.Comment; comment = s.Comment;
......
...@@ -42,8 +42,29 @@ import _ "fmt" ...@@ -42,8 +42,29 @@ import _ "fmt"
// make sure a comment doesn't cause semicolons to be inserted // make sure a comment doesn't cause semicolons to be inserted
import _ "foo" // a comment import _ "foo" // a comment
import // a comment
"bar"
import "foo" // a comment
import "bar" // a comment import "bar" // a comment
import (
_ "foo" + // a comment
// a comment
"bar" +
"foo" + // a comment
"bar"; // a comment
)
// a case that caused problems in the past (comment placement)
import (
. "fmt";
"io";
"malloc"; // for the malloc count test only
"math";
"strings";
"testing";
)
// at least one empty line between declarations of different kind // at least one empty line between declarations of different kind
import _ "io" import _ "io"
...@@ -471,9 +492,11 @@ func _() int { type T struct{} } ...@@ -471,9 +492,11 @@ func _() int { type T struct{} }
// making function declarations safe for new semicolon rules // making function declarations safe for new semicolon rules
func _() { /* one-line func */ } func _() { /* one-line func */ }
func _() { // opening "{" must move up /* one-line func */ } func _() { // opening "{" must move up
/* one-line func */ }
func _() { // opening "{" must move up// multi-line func func _() { // opening "{" must move up
// multi-line func
// in the following declarations, a comment must not // in the following declarations, a comment must not
// introduce a newline and thus cause a semicolon to // introduce a newline and thus cause a semicolon to
......
...@@ -45,6 +45,27 @@ import _ // a comment ...@@ -45,6 +45,27 @@ import _ // a comment
"foo" "foo"
import // a comment import // a comment
"bar" "bar"
import "foo" // a comment
import "bar" // a comment
import (
_ // a comment
"foo"
// a comment
"bar"
"foo" // a comment
"bar" // a comment
)
// a case that caused problems in the past (comment placement)
import (
. "fmt";
"io";
"malloc"; // for the malloc count test only
"math";
"strings";
"testing";
)
// at least one empty line between declarations of different kind // at least one empty line between declarations of different kind
......
...@@ -297,6 +297,18 @@ const ( ...@@ -297,6 +297,18 @@ const (
) )
// Correct placement of operators and comments in multi-line expressions
func _() {
_ = a + // comment
b + // comment
c;
_ = "a" + // comment
"b" + // comment
"c";
_ = "ba0408" + "7265717569726564"; // field 71, encoding 2, string "required"
}
func same(t, u *Time) bool { func same(t, u *Time) bool {
// respect source lines in multi-line expressions // respect source lines in multi-line expressions
return t.Year == u.Year && return t.Year == u.Year &&
......
...@@ -302,6 +302,18 @@ const ( ...@@ -302,6 +302,18 @@ const (
) )
// Correct placement of operators and comments in multi-line expressions
func _() {
_ = a // comment
+ b + // comment
c;
_ = "a" // comment
"b" // comment
"c";
_ = "ba0408" "7265717569726564" // field 71, encoding 2, string "required"
}
func same(t, u *Time) bool { func same(t, u *Time) bool {
// respect source lines in multi-line expressions // respect source lines in multi-line expressions
return t.Year == u.Year && return t.Year == u.Year &&
......
...@@ -297,6 +297,18 @@ const ( ...@@ -297,6 +297,18 @@ const (
) )
// Correct placement of operators and comments in multi-line expressions
func _() {
_ = a + // comment
b + // comment
c;
_ = "a" + // comment
"b" + // comment
"c";
_ = "ba0408" + "7265717569726564"; // field 71, encoding 2, string "required"
}
func same(t, u *Time) bool { func same(t, u *Time) bool {
// respect source lines in multi-line expressions // respect source lines in multi-line expressions
return t.Year == u.Year && return t.Year == u.Year &&
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment