liveBook · Manning

Chapter 9: Greedy iterative pretty printing

What you will learn in chapter 9 of Fabulous Adventures in Data Structures and Algorithms

This chapter introduction frames automatic code formatting as a pretty-printing problem and previews a fast nonrecursive greedy solution and its parse-tree transformation design.

After this chapter you will be able to

What it builds on

Section by section

Introduction

This chapter introduction frames automatic code formatting as a pretty-printing problem and previews a fast nonrecursive greedy solution and its parse-tree transformation design.

Key terms: automatic code formatter, pretty printer, greedy algorithm, nonoptimal solution, explicit stacks, directed acyclic graph, visitor pattern, parse tree, separating concerns, pretty-printing logic

9.1 The pretty-printing problem

This section defines pretty printing as formatting a parsed expression tree under competing readability constraints and states the simplified problem used in the chapter.

Key terms: lexer, tokens, parser, parse tree, statements, expressions, line limit, line wrapping, horizontal scrolling, indentation

9.2 Greedy algorithms and making change

This section introduces greedy algorithms through change making, showing why a fast acceptable pretty-printing layout can be preferable to a slow optimal one.

Key terms: greedy algorithm, subproblem, optimal solution, change-making problem, quarter, dime, nickel, penny, pretty printer, IDE

9.3 A greedy pretty-printing algorithm

This section introduces the two-phase greedy pretty-printing approach and the order in which its components will be developed.

Key terms: greedy pretty-printing algorithm, parse tree, doc, phase 1, phase 2, document, concatenation, indentation, grouping, spacing

9.3.1 The doc data structure

This section defines an immutable document representation for expressing formatting choices and illustrates how grouped optional breaks yield a greedy layout.

Key terms: TextDoc, OptBreakDoc, GroupDoc, IndentDoc, ConcatDoc, space break, no-space break, nested group, callfb, foobar

9.3.2 Visualizing a doc: How deep does it get?

This subsection visualizes a doc as a potentially very deep immutable directed graph and motivates iterative implementations of later formatting operations.

Key terms: doc, immutable directed graph, concatenation, Ind, Grp, OptBreak, deep, groups, indentations, Fits(width)

9.3.3 Phase 2: Implementing Fits() without recursion

This section implements the Fits check iteratively so a pretty printer can decide whether a Doc can remain on the current line without risking call-stack overflow.

Key terms: Fits, Doc, TextDoc, GroupDoc, IdentDoc, IndentDoc, work-stack, Stack<Doc>, call stack, nonrecursive

9.3.4 Phase 2 continued: Implementing Pretty() without recursion

This section implements the second phase of pretty printing as an iterative Pretty method that uses explicit state to format docs efficiently.

Key terms: Pretty, StringBuilder, TextDoc, GroupDoc, IndentDoc, OptBreakDoc, (bool, int, Doc) tuple, work stack, optional break, indentation

9.4 Phase 1: Transforming parse trees with the visitor pattern

This section positions phase 1 of pretty printing as a parse-tree-to-doc transformation and motivates the visitor pattern for keeping that transformation separate from the parse-tree hierarchy.

Key terms: Phase 0, Phase 1, Phase 2, parse tree, doc, visitor pattern, parse-tree hierarchy, virtual method, ToDoc, Conway's Law

9.4.1 Implementing the visitor pattern

This section implements the visitor pattern on expression parse-tree nodes so external visitors can perform type-specific operations through double dispatch.

Key terms: visitor pattern, visitor, IExprVisitor<T>, Expr, Id, Paren, Accept, double dispatch, overload resolution, virtual dispatch

9.4.2 From parse tree to doc

This section defines visitor rules that transform each parse-tree expression into a doc with optional breaks, grouping, and indentation for greedy pretty printing.

Key terms: parse tree, doc, optional break, group, indentation, parenthesized expression, call, argument list, comma-separated, space break

9.5 Summary

This summary recaps a two-phase greedy pretty printer and the implementation and design lessons drawn from it.

Concepts explained in this chapter

← Chapter 8: Coloring graphs with backtracking search Chapter 10: Unification and anti-unification →

These guides are generated from the text of Manning books by Manning's knowledge graph and link to the sections they draw on. The full books are available on liveBook and at manning.com.