# Code Smell 161 - Abstract/Final/Undefined Classes

> TL;DR: If your language has the right tool, your classes should be either abstract or final.

# Problems

- Subclassification for [Code Reuse](https://maximilianocontieri.com/code-smell-11-subclassification-for-code-reuse)

- Classes with [just one](https://maximilianocontieri.com/code-smell-136-classes-with-just-one-subclass) concrete subclass

- Liskov Substitution Violation

- [Yo-Yo](https://maximilianocontieri.com/code-smell-58-yo-yo-problem) Problem

# Solutions

1. Declare all your leaf classes as *final* and the rest of them *abstract*.

# Context

Managing hierarchies and composition is the main task of a good software designer.

Keeping hierarchies healthy is crucial to favor cohesion and avoid [coupling](https://maximilianocontieri.com/coupling-the-one-and-only-software-design-problem).

# Sample Code

## Wrong

[Gist Url]: # (https://gist.github.com/mcsee/580be250747d29d198fe4bbf9db41c8e)
```java
public class Vehicle
{
  // class is not a leaf. Therefore it should be abstract 
  
  //an abstract method that only declares, but does not define the start 
  //functionality because each vehicle uses a different starting mechanism
  abstract void start();
}

public class Car extends Vehicle
{
  // class is leaf. Therefore it should be final
}

public class Motorcycle extends Vehicle
{
  // class is leaf. Therefore it should be final
}
```

## Right

[Gist Url]: # (https://gist.github.com/mcsee/712df5f99ec232c4e4d2cdaf1bdf62c0)
```java
abstract public class Vehicle
{
  // class is not a leaf. Therefore it is abstract
   
  //an abstract method that only declares, but does not define the start 
  //functionality because each vehicle uses a different starting mechanism
  abstract void start();
}

final public class Car extends Vehicle
{
  // class is leaf. Therefore it is final
}

final public class Motorcycle extends Vehicle
{
  // class is leaf. Therefore it is final
}
```

# Detection

[X] Automatic 

Since this is enforced by static analysis, we can't do it with most available tools.

# Tags

- Subclassification

# Conclusion

We should look back at our classes and start qualifying them either as abstract or final.

There are no valid cases for two concrete classes, one subclassifying the other.

# Relations

%[https://maximilianocontieri.com/code-smell-11-subclassification-for-code-reuse]

%[https://maximilianocontieri.com/code-smell-136-classes-with-just-one-subclass]

%[https://maximilianocontieri.com/code-smell-37-protected-attributes]

%[https://maximilianocontieri.com/code-smell-58-yo-yo-problem]

# More Info

%[https://maximilianocontieri.com/coupling-the-one-and-only-software-design-problem]

[Deep Subclasses](http://www.laputan.org/drc.html)

# Disclaimer

Code Smells are just my [opinion](https://maximilianocontieri.com/i-wrote-more-than-90-articles-on-2021-here-is-what-i-learned).

# Credits

Photo by [William Bossen](https://unsplash.com/@william_bossen) on [Unsplash](https://unsplash.com/s/photos/the-end)
  
* * *

> When the final design seems too simple for the amount of work you've put in, then you know you're done.

_Brady Clark_
 
%[https://maximilianocontieri.com/software-engineering-great-quotes]

* * *

This article is part of the CodeSmell Series.

%[https://maximilianocontieri.com/how-to-find-the-stinky-parts-of-your-code]
