• Robert Griesemer's avatar
    go/printer, gofmt: tuned table alignment for better results · 542ea5ad
    Robert Griesemer authored
    The go/printer (and thus gofmt) uses a heuristic to determine
    whether to break alignment between elements of an expression
    list which is spread across multiple lines. The heuristic only
    kicked in if the entry sizes (character length) was above a
    certain threshold (20) and the ratio between the previous and
    current entry size was above a certain value (4).
    
    This heuristic worked reasonably most of the time, but also
    led to unfortunate breaks in many cases where a single entry
    was suddenly much smaller (or larger) then the previous one.
    
    The behavior of gofmt was sufficiently mysterious in some of
    these situations that many issues were filed against it.
    
    The simplest solution to address this problem is to remove
    the heuristic altogether and have a programmer introduce
    empty lines to force different alignments if it improves
    readability. The problem with that approach is that the
    places where it really matters, very long tables with many
    (hundreds, or more) entries, may be machine-generated and
    not "post-processed" by a human (e.g., unicode/utf8/tables.go).
    
    If a single one of those entries is overlong, the result
    would be that the alignment would force all comments or
    values in key:value pairs to be adjusted to that overlong
    value, making the table hard to read (e.g., that entry may
    not even be visible on screen and all other entries seem
    spaced out too wide).
    
    Instead, we opted for a slightly improved heuristic that
    behaves much better for "normal", human-written code.
    
    1) The threshold is increased from 20 to 40. This disables
    the heuristic for many common cases yet even if the alignment
    is not "ideal", 40 is not that many characters per line with
    todays screens, making it very likely that the entire line
    remains "visible" in an editor.
    
    2) Changed the heuristic to not simply look at the size ratio
    between current and previous line, but instead considering the
    geometric mean of the sizes of the previous (aligned) lines.
    This emphasizes the "overall picture" of the previous lines,
    rather than a single one (which might be an outlier).
    
    3) Changed the ratio from 4 to 2.5. Now that we ignore sizes
    below 40, a ratio of 4 would mean that a new entry would have
    to be 4 times bigger (160) or smaller (10) before alignment
    would be broken. A ratio of 2.5 seems more sensible.
    
    Applied updated gofmt to all of src and misc. Also tested
    against several former issues that complained about this
    and verified that the output for the given examples is
    satisfactory (added respective test cases).
    
    Some of the files changed because they were not gofmt-ed
    in the first place.
    
    For #644.
    For #7335.
    For #10392.
    (and probably more related issues)
    
    Fixes #22852.
    
    Change-Id: I5e48b3d3b157a5cf2d649833b7297b33f43a6f6e
    542ea5ad
Name
Last commit
Last update
..
archive Loading commit data...
bufio Loading commit data...
builtin Loading commit data...
bytes Loading commit data...
cmd Loading commit data...
compress Loading commit data...
container Loading commit data...
context Loading commit data...
crypto Loading commit data...
database/sql Loading commit data...
debug Loading commit data...
encoding Loading commit data...
errors Loading commit data...
expvar Loading commit data...
flag Loading commit data...
fmt Loading commit data...
go Loading commit data...
hash Loading commit data...
html Loading commit data...
image Loading commit data...
index/suffixarray Loading commit data...
internal Loading commit data...
io Loading commit data...
log Loading commit data...
math Loading commit data...
mime Loading commit data...
net Loading commit data...
os Loading commit data...
path Loading commit data...
plugin Loading commit data...
reflect Loading commit data...
regexp Loading commit data...
runtime Loading commit data...
sort Loading commit data...
strconv Loading commit data...
strings Loading commit data...
sync Loading commit data...
syscall Loading commit data...
testing Loading commit data...
text Loading commit data...
time Loading commit data...
unicode Loading commit data...
unsafe Loading commit data...
vendor/golang_org/x Loading commit data...
Make.dist Loading commit data...
all.bash Loading commit data...
all.bat Loading commit data...
all.rc Loading commit data...
androidtest.bash Loading commit data...
bootstrap.bash Loading commit data...
buildall.bash Loading commit data...
clean.bash Loading commit data...
clean.bat Loading commit data...
clean.rc Loading commit data...
cmp.bash Loading commit data...
iostest.bash Loading commit data...
make.bash Loading commit data...
make.bat Loading commit data...
make.rc Loading commit data...
naclmake.bash Loading commit data...
nacltest.bash Loading commit data...
race.bash Loading commit data...
race.bat Loading commit data...
run.bash Loading commit data...
run.bat Loading commit data...
run.rc Loading commit data...