Coupling and Cohesion
Cohesion measures how closely class elements relate; coupling measures dependency between classes.
Introduction
Cohesion measures how closely class elements relate; coupling measures dependency between classes. High cohesion + low coupling is the LLD sweet spot — classes focused internally, connected through narrow interfaces.
Interviewers infer maintainability from your diagram density: spaghetti arrows between every class signals high coupling. A BookingService talking to PaymentGateway interface signals healthy boundary coupling.
SOLID principles largely aim at improving cohesion and reducing coupling.
Understanding the topic
Key concepts
- High cohesion: methods support one class purpose.
- Low coupling: minimal knowledge of other classes' internals.
- Tight coupling: concrete dependencies, shared mutable globals.
- Loose coupling: interfaces, events, DTOs at boundaries.
- Law of Demeter: don't talk to strangers.
- Cohesion types: functional best, coincidental worst.
Step-by-step explanation
- Review class diagram for crisscross dependencies.
- Group related fields and methods; split unrelated ones.
- Replace concrete refs with interfaces at boundaries.
- Pass DTOs not entity graphs across layers.
- Avoid bidirectional associations unless necessary.
- Measure change ripple: one change should not touch ten classes.
Informative example
Loose coupling via interface; high cohesion inside service:
public final class MovieBookingService {private final SeatRepository seats;private final PaymentGateway payments;private final Notifier notifier;public MovieBookingService(SeatRepository seats, PaymentGateway payments, Notifier notifier) {this.seats = seats;this.payments = payments;this.notifier = notifier;}public BookingResult book(BookingCommand cmd) {if (!seats.lock(cmd.showId(), cmd.seatIds())) {return BookingResult.failed("seats unavailable");}var pay = payments.charge(cmd.userId(), cmd.total());if (pay instanceof PaymentResult.Failure f) {seats.release(cmd.showId(), cmd.seatIds());return BookingResult.failed(f.reason());}notifier.send(new Notification(cmd.email(), "Booked " + cmd.showId()));return BookingResult.success(cmd.showId());}}
MovieBookingService cohesive on booking orchestration; coupled loosely to three interfaces only.
Real-world use
Real-world applications
- Evaluating class diagram quality in reviews.
- Refactoring god services into modules.
- Explaining why interface extraction helps testing.
Best practices
- Prefer unidirectional dependencies.
- Keep domain entities free of infrastructure imports.
- Introduce facades only when simplifying many deps.
- Monitor package cycles in larger codebases.
- High cohesion often enables SRP naturally.
Common mistakes
- Every class knows every other class.
- Shared mutable singleton state coupling all tests.
- Feature envy — method uses other class fields excessively.
- Low cohesion utility dumping unrelated helpers.
Advanced interview questions
Q1BeginnerWhat is cohesion?
Q2BeginnerWhat is coupling?
Q3IntermediateGoal for LLD?
Q4IntermediateHow interfaces reduce coupling?
Q5AdvancedDetect high coupling in diagram.
Summary
High cohesion, low coupling = maintainable LLD. Interfaces and DTOs soften boundaries. Avoid spaghetti dependencies on diagrams. SOLID principles improve both metrics. Law of Demeter limits reach into strangers.