\chapterimage{chapter_head_2.pdf}

\chapter{Classes}

\section{Classes Should Be Small!}\index{Classes!Classes Should Be Small!}

The fact that classes should be small is not an issue to be discusses, the question, during review, process is \textit{how small should it be?} With functions we measured size by counting physical lines. With classes we use a different measure. We count \textit{responsibilities}.

The name of a class should describe what responsibilities it fulfills. If we cannot derive a concise name for a class, then it's likely too large and has too many responsibilities.

We should also be able to write a brief description of the class in about 25 words,
without using the words "if", "and", "or", or "but".

\begin{marker}
A class's single responsibility should be shown by a self-descriptive name and a short class description.
\end{marker}

\subsection{The Single Responsibility Principle}

\begin{definition}[Single Responsibility Principle (SRP)]
A class or module should have one and only one, reason to change.
\end{definition}

Trying to identify responsibilities (reasons to change) often helps us recognize and
create better abstractions in our code. During code review, you could ask author to break a class into separate ones by methods

\begin{marker}
Review to make sure classes satisfies SRP and ask the author to break classes into multiples if not.
\end{marker}

\subsubsection{Why Do We Often Violate SRP?}

Getting software to work and making software clean are two very different activities. Most of us have limited room in our heads, so we focus on getting our code to work more than organization and cleanliness. This is wholly appropriate. Maintaining a separation of concerns is just as important in our programming activities as it is in our programs

The problem is that too many of us think that we are done once the program works. We fail to switch to the other concern of organization and cleanliness.

\textbf{This is an important reason we do code review - Once we review to make sure code works, we would want to do a second review to make sure code is also clean}

\begin{marker}
There should be at least 2 review process:

\begin{enumerate}
    \item make sure code works
    \item make sure code is clean
\end{enumerate}
\end{marker}

\subsection{Cohesion}

\textbf{Classes should have a small number of instance variables}. Each of the methods of a class should manipulate one or more of those variables. In general the more variables a method manipulates the more cohesive that method is to its class. A class in which each variable is used by each method is maximally cohesive.

In general it is neither advisable nor possible to create such maximally cohesive classes; on the other hand, we would like cohesion to be high. When cohesion is high, it means that the methods and variables of the class are co-dependent and hang together as a logical whole.

Since a class should have small number of instance variables, the strategy of keeping functions small and keeping parameter lists short can sometimes lead to a proliferation of instance variables that are used by a subset of methods. When this happens, it almost always means that there is at least one other class trying to get out of the larger class. You should try to separate the variables and methods into two or more classes such that the new classes are more cohesive.

\begin{marker}
Keep the number of instance variables small and breaks a class apart when there are many
\end{marker}

\subsubsection{Application of Cohesion - Keeping Classes Small}

Consider a large function with many variables declared within it. Let's say you
want to extract one small part of that function into a separate function. However, the code you want to extract uses four of the variables declared in the function. Must you pass all four of those variables into the new function as arguments?

Not at all! If we promoted those four variables to instance variables of the class, then we could extract the code without passing any variables at all. It would be easy to break the function up into small pieces.

Unfortunately, this also means that our classes lose cohesion because they accumulate more and more instance variables that exist solely to allow a few functions to share them. But wait! If there are a few functions that want to share certain variables, doesn't that make them a class in their own right? Of course it does. When classes lose cohesion, split them!

So breaking a large function into many smaller functions often gives us the opportunity to split several smaller classes out as well. This gives our program a much better organization and a more transparent structure.

\begin{marker}
During review process, see if splitting methods could lead to smaller classes.
\end{marker}

\section{Organizing for Change}\index{Classes!Organizing for Change}