#refactoring Decompose Conditional

Problem:
You have a complex conditional (if-then/else or switch).

Solution: Decompose the complicated parts of the conditional into separate methods: the condition, then and else.
Covariance and contravariance

Understanding of covariance and contravariance is a key to understanding how generics work in different programming languages.

Variance refers to how subtyping between more complex types relates to subtyping between their components. For example, how should a list of Cats relate to a list of Animals? Or how should a function that returns Cat relate to a function that returns Animal?

Covariance means that the subtyping relation of the simple types is preserved for the complex types.

Contravariance means that the subtyping relation of the simple types is reversed for the complex types.

Java explanation: https://dzone.com/articles/covariance-and-contravariance
Why Is Contravariance in Scala so Hard: https://dzone.com/articles/why-is-contravariance-in-scala-so-hard
Variance, Immutability, and Strictness in Kotlin: https://kotlinlang.org/docs/reference/generics.html
Wikipedia: https://en.wikipedia.org/wiki/Covariance_and_contravariance_(computer_science)
Liskov Substitution Principle is the third of Robert C. Martin's SOLID design principles. It extends the Open/Closed principle and enables you to replace objects of a parent class with objects of a subclass without breaking the application. This requires all subclasses to behave in the same way as the parent class.

To achieve that, your subclasses need to follow these rules:

- Don't implement any stricter validation rules on input parameters than implemented by the parent class.
- Apply at the least the same rules to all output parameters as applied by the parent class.

Details and Java examples: https://dzone.com/articles/solid-design-principles-explained-the-liskov-subst
.NET explanation (and ducks example): https://blog.ndepend.com/solid-design-the-liskov-substitution-principle/
Event Bus Pattern

Imagine having a large scale application containing a lot of components interacting with each other, and you want a way to make your components communicate while maintaining loose coupling and separation of concerns principles, the Event Bus pattern can be a good solution for your problem.

The idea of an Event bus: you have some kind of pipeline and computers connected to it, and whenever one of them sends a message, it’s dispatched to all of the others. Then, they decide if they want to consume the given message or just discard it.

Read more: https://dzone.com/articles/design-patterns-event-bus
Сommand pattern is a behavioral design pattern in which an object is used to encapsulate all information needed to perform an action or trigger an event at a later time. This information includes the method name, the object that owns the method and values for the method parameters.

Four terms always associated with the command pattern are command, receiver, invoker and client.

Using command objects makes it easier to construct general components that need to delegate, sequence or execute method calls at a time of their choosing without the need to know the class of the method or the method parameters.

Java example: https://bit.ly/3mc3I9h
Scala example: https://bit.ly/2FdcrXz
Wikipedia: https://en.wikipedia.org/wiki/Command_pattern
Domain-Driven Design (DDD) is an approach to software development that centers the development on programming a domain model that has a rich understanding of the processes and rules of a domain. The name comes from a 2003 book by Eric Evans that describes the approach through a catalog of patterns. Since then a community of practitioners have further developed the ideas, spawning various other books and training courses. The approach is particularly suited to complex domains, where a lot of often-messy logic needs to be organized.

DDD by Martin Fowler: https://martinfowler.com/bliki/DomainDrivenDesign.html

Getting started with DDD: https://dzone.com/refcardz/getting-started-domain-driven
Replace Type Code with Subclasses #refactoring

Problem
:
You have a coded type that directly affects program behavior (values of this field trigger various code in conditionals).

Solution:
Create subclasses for each value of the coded type. Then extract the relevant behaviors from the original class to these subclasses. Replace the control flow code with polymorphism.

https://sapanparikh18.github.io/Refactoring-Part-2/
High availability (HA) is a characteristic of a system which aims to ensure an agreed level of operational performance, usually uptime.

Availability refers to the ability of the user to obtain a service, access the system, whether to submit new work, update or alter existing work, or collect the results of previous work.

If a user cannot access the system, it is unavailable. The term downtime is used to refer to periods when a system is unavailable.

What is High Availability: https://do.co/2RHh4fD
Wikipedia: https://en.wikipedia.org/wiki/High_availability
Daily Pattern (Software Architecture and Design, Refactoring)
Сommand pattern is a behavioral design pattern in which an object is used to encapsulate all information needed to perform an action or trigger an event at a later time. This information includes the method name, the object that owns the method and values…
Command Pattern vs Strategy Pattern

Command
pattern is used to make an object out of what needs to be done — to take an operation and its arguments and wrap them up in an object to be logged, held for undo, sent to a remote site, etc.

Strategy pattern, on the other hand, is used to specify how something should be done, and plugs into a larger object or method to provide a specific algorithm.

Details: https://miafish.wordpress.com/2015/01/16/command-pattern-vs-strategy-pattern/
Split Temporary Variable #refactoring

Problem
You have a local variable that’s used to store various intermediate values inside a method (except for cycle variables).

Solution
Use different variables for different values. Each variable should be responsible for only one particular thing.

Why Refactor

If you’re reusing variables inside a function for various unrelated purposes, you’re sure to encounter problems as soon as you need to make changes to the code containing the variables. You will have to recheck each case of variable use to make sure that the correct values are used.

Benefits

- Each component of the program code should be responsible for one and one thing only.

- Code becomes more readable.

- This refactoring technique is useful if you anticipate using Extract Method later.

P. S. In Scala and Kotlin it's best practice to use val (final in Java) instead of var as much and possible so you will never have this problem.
CQRS Architectural Pattern

CQRS
is an acronym for Command and Query Responsibility Segregation. The central concept of this pattern is that an application has read operations and write operations that must be totally separated. This also means that the model used for write operations (commands) will differ from the read models (queries). Furthermore, the data will be stored in different locations. In a relational database, this means there will be tables for the command model and tables for the read model. Some implementations even store the different models in totally different databases, e.g. SQL Server for the command model and MongoDB for the read model.

Martin Fowler explanation: https://martinfowler.com/bliki/CQRS.html
Understanding From First Principles: https://blog.ndepend.com/cqrs-understanding-first-principles/
CQRS: What? Why? How? https://medium.com/@sderosiaux/cqrs-what-why-how-945543482313
The Builder pattern solves the issue when you need to construct a complicated object step by step without complicating the construction code.

It is one of the GoF design patterns that describe how to solve recurring design problems in object-oriented software.

The Builder design pattern solves problems like:

- How can a class create different representations of a complex object?
- How can a class that includes creating a complex object be simplified?

Details in Java: https://dzone.com/articles/design-patterns-the-builder-pattern
Wikipedia: https://en.wikipedia.org/wiki/Builder_pattern
Scala example: https://levelup.gitconnected.com/demystify-builder-pattern-in-scala-3a5f561ab62c
Extract Variable #refactoring

Problem: you have an expression that’s hard to understand.

Solution: place the result of the expression or its parts in separate variables that are self-explanatory.
Visitor Design Pattern

Allows for one or more operation to be applied to a set of objects at runtime, decoupling the operations from the object structure. It is one way to follow the Open/Closed principle.

Shopping in the supermarket is a common example, where the shopping cart is your set of elements. When you get to the checkout, the cashier acts as a visitor, taking the disparate set of elements (your shopping), some with prices and others that need to be weighed, in order to provide you with a total.

It's a difficult pattern to explain in the real world, but things should become clearer as we go through the pattern definition, and take a look at how to use it in code: https://dzone.com/articles/design-patterns-visitor

Wikipedia: https://en.wikipedia.org/wiki/Visitor_pattern
#SOLID Interface-Segregation Principle

The interface-segregation principle (ISP) states that no client should be forced to depend on methods it does not use.

ISP splits interfaces that are very large into smaller and more specific ones so that clients will only have to know about the methods that are of interest to them.

Details: https://dzone.com/articles/solid-principles-interface-segregation-principle
Wikipedia: https://en.wikipedia.org/wiki/Interface_segregation_principle
Factory Method vs Abstract Factory (again?)

Factory method: define an interface for creating an object, but let subclasses decide which class to instantiate. factory method lets a class defer instantiation to subclasses.

Abstract factory: provide an interface for creating families of related or dependent objects without specifying their concrete classes.

Explanation: https://dzone.com/articles/factory-method-vs-abstract
What Is Loose Coupling?

Loose coupling is when two objects can interact with each other but have very limited knowledge about what the other object can do.

Some advantages of making your code loosely coupled include:

- better testability
- easy-to-understand code
- swappable components
- scalability
- isolated code/features

Details: https://dzone.com/articles/what-is-loose-coupling
2024/05/02 22:22:52
Back to Top
HTML Embed Code: