Changes for the 2nd Edition of Refactoring

A short summary of the changes between the first and second editions of Refactoring

05 September 2018

At the broadest level, the second edition's structure follows that of the first edition. That shouldn't be too surprising, since the first edition was so successful, I might as well continue with what worked.

The first edition opened with four narrative chapters, these all appear the second edition too. All of these follow the broad forms of the original book.

The opening example shifts its domain, as not that many people are familiar with a video store any more. The flow of the refactorings is pretty much the same: break into functions, separate calculation from formatting, organize calculations by type using polymorphism.

The principles and smells chapter both had a thorough overhaul. There's much that survived and much that changed. I'm guessing about three-quarters of it changed, but that's a gut feel rather than based on a realistic measurement. The testing chapter had to be completely redone, particularly due to change from Java to JavaScript.

After those introductory chapters, I continue with the catalog, which I've always seen as the heart of the book. I'll go into the catalog changes in more detail in a moment, but one notable structural change is I put together an initial chapter of refactorings that contains what I judge to be a good set of refactorings to learn about first.

I dropped the later chapters, which explored some more tangential issues. I think they worked in the first edition, but these days I think it's better to publish essays like this on my website. That's the same reason why I also dropped the four "big refactorings" from the catalog. The big refactorings were always a bit different to the majority of the refactorings, and I do feel these examples work better through essays on my website.

Changes to the catalog

So what happened to the catalog? Here's a table that shows the fate of the original 68 refactorings. [1]

Fate of the refactorings in the first edition
namepagefatereplacement
Add Parameter275replaced➜ Change Function Declaration
Change Bidirectional Association to Unidirectional200absent
Change Reference to Value183kept
Change Unidirectional Association to Bidirectional197absent
Change Value to Reference179kept
Collapse Hierarchy344kept
Consolidate Conditional Expression240kept
Consolidate Duplicate Conditional Fragments243replaced➜ Slide Statements
Decompose Conditional238kept
Duplicate Observed Data189absent
Encapsulate Collection208kept
Encapsulate Downcast308absent
Encapsulate Field206replaced➜ Encapsulate Variable
Extract Class149kept
Extract Interface341absent
Extract Method110replaced➜ Extract Function
Extract Subclass330replaced➜ Replace Type Code with Subclasses
Extract Superclass336kept
Extract Variable124kept
Form Template Method345absent
Hide Delegate157kept
Hide Method303absent
Inline Class154kept
Inline Method117replaced➜ Inline Function
Inline Temp119replaced➜ Inline Variable
Introduce Assertion267kept
Introduce Foreign Method162absent
Introduce Local Extension164absent
Introduce Null Object260replaced➜ Introduce Special Case
Introduce Parameter Object295kept
Move Field146kept
Move Method142replaced➜ Move Function
Parameterize Method283replaced➜ Parameterize Function
Preserve Whole Object288kept
Pull Up Constructor Body325kept
Pull Up Field320kept
Pull Up Method322kept
Push Down Field329kept
Push Down Method328kept
Remove Assignments to Parameters131replaced➜ Split Variable
Remove Control Flag245replaced†➜ Replace Control Flag with Break
Remove Middle Man160kept
Remove Parameter277replaced➜ Change Function Declaration
Remove Setting Method300kept
Rename Method273replaced➜ Change Function Declaration
Replace Array with Object186absent
Replace Conditional with Polymorphism255kept
Replace Constructor with Factory Method304replaced➜ Replace Constructor with Factory Function
Replace Data Value with Object175replaced➜ Replace Primitive with Object
Replace Delegation with Inheritance355absent
Replace Error Code with Exception310kept†
Replace Exception with Test315replaced†➜ Replace Exception with Precheck
Replace Inheritance with Delegation352replaced➜ Replace Superclass with Delegate
Replace Magic Number with Symbolic Constant204replaced†➜ Replace Magic Literal
Replace Method with Method Object135replaced➜ Replace Function with Command
Replace Nested Conditional with Guard Clauses250kept
Replace Parameter with Explicit Methods285replaced➜ Remove Flag Argument
Replace Parameter with Method292replaced➜ Replace Parameter with Query
Replace Record with Data Class217replaced➜ Encapsulate Record
Replace Subclass with Fields232replaced➜ Remove Subclass
Replace Temp with Query120kept
Replace Type Code with Class218replaced➜ Replace Primitive with Object
Replace Type Code with State/Strategy227replaced➜ Replace Type Code with Subclasses
Replace Type Code with Subclasses223kept
Self Encapsulate Field171replaced➜ Encapsulate Variable
Separate Query from Modifier279kept
Split Temporary Variable128replaced➜ Split Variable
Substitute Algorithm139kept

† web edition only

Refactorings marked as kept are present in the second edition under the same name. Those marked as absent, aren't in the new edition. There are various reasons I dropped refactorings from the new edition, and I may extend this article to discuss some of these in the future. Those marked replaced have a refactoring with a different name in the new editions. Some of these are little more than a rename, for example I changed "Split Temporary Variable" with "Split Variable". Most are minor generalizations, such as changing "Extract Method" to "Extract Function". Many of these generalizations reflect the less object-centric nature of the rewrite. In some cases a few first edition refactorings are combined: eg Add Parameter, Remove Parameter, and Rename Method are all replaced by Change Function Declaration. As with the ones that I left out, I may extend this article in the future to discuss some individual cases. [2]

The new edition contains fifteen refactorings that are completely new, in that they aren't generalizations or renaming of existing refactorings. These are:

Combine Functions into Class
Combine Functions into Transform
Move Statements into Function
Move Statements to Callers
Remove Dead Code
Rename Field
Rename Variable
Replace Command with Function
Replace Derived Variable with Query
Replace Inline Code with Function Call
Replace Loop with Pipeline
Replace Query with Parameter
Replace Subclass with Delegate
Return Modified Value
Split Phase

I realize that the names alone don't convey that much about what these new refactorings do, or how the generalized refactorings differ from what's in the first edition. In due course I'll be updating the online catalog to give more information on this.


Footnotes

1: The 68 does not include the four "big refactorings" from the original book. As I indicated earlier, I think these kinds of topic are best captured as essays which can appear on the web.

2: Whether I do this depends on whether there seems to be interest in this from readers, and how I prioritize this against other things I'll want to write about in the coming months.