✔️ 단일 책임 원칙(SRP)과 개방-폐쇄 원칙(OCP)
단일 책임 원칙과 개방-폐쇄 원칙은 객체지향 설계의 5가지 원칙인 SOLID 원칙의 'S'와 'O'에 해당한다.
참고로 SOLID 원칙은 다음과 같다.
- SRP(Single Responsibility Principle): 단일 책임의 원칙
- OCP(Open/Closed Principle) : 개방/폐쇄의 원칙
- LSP(Liskov’s Substitution Principle) : 리스코브 치환의 원칙
- ISP(Interface Segregation Principle) : 인터페이스 분리의 원칙
- DIP(Dependency Inversion Principle) : 의존성 역전의 원칙
단일 책임 원칙(Single Responsibility Principle, SRP)
"하나의 클래스는 하나의 책임만 가져야 한다."
하나의 클래스가 하나의 책임만을 가져야 한다는 원칙이다. 이때 책임이란 변경의 사유라고 생각하면 이해하기 쉽다. 즉, 하나의 클래스가 변경되는 이유는 단 하나여야 한다는 원칙이다. 이를 통해 클래스의 목적을 분명히 함으로써 유지보수와 확장성에 기여할 수 있다.
// SRP 적용 전
class UserSettings {
void changeUsername(String name) { /* 이름 변경 로직 */ }
void saveToDatabase() { /* DB 저장 로직 */ }
}
한 클래스가 이름 변경과 DB 저장이라는 두 가지 책임을 가지고 있다.
// SRP 적용 후
class User {
void changeUsername(String name) { /* 이름 변경 로직 */ }
}
class UserRepository {
void save(User user) { /* DB 저장 로직 */ }
}
SRP 원칙을 적용하면 다음과 같이 클래스를 분리해 각각의 클래스가 하나의 책임만을 갖도록 설계할 수 있다.
개방-폐쇄 원칙(Open/Closed Principle, OCP)
"확장에는 열려있고, 수정에는 닫혀 있어야 한다. "
기존의 코드를 수정하지 않고도 새로운 기능을 추가할 수 있어야 한다는 원칙이다. 주로 추상화를 통해 달성한다. 확장과 수정을 분리함으로써 적은 비용으로 유지보수가 가능해지며, 확장을 용이하게 해 기능 추가 시 발생하는 오류를 줄일 수 있다.
// OCP 적용 전
class AnimalService {
void makeSound(String animalType) {
if (animalType.equals("Dog")) {
System.out.println("멍멍");
} else if (animalType.equals("Cat")) {
System.out.println("야옹");
}
}
}
새로운 동물이 추가될 때마다 makeSound 메서드 내부의 if-else 문을 계속 수정해야 한다.
// OCP 적용 후
// 1. 공통 인터페이스 정의
interface Animal {
void speak();
}
// 2. 클래스
class Dog implements Animal {
public void speak() { System.out.println("멍멍"); }
}
class Cat implements Animal {
public void speak() { System.out.println("야옹"); }
}
// 3. 새로운 동물(Sheep)이 추가되어도 기존 코드는 수정 안 함
class Sheep implements Animal {
public void speak() { System.out.println("매~"); }
}
// 4. 클라이언트 코드: 수정에 닫혀 있음
class AnimalService {
void makeSound(Animal animal) {
// 어떤 동물이 들어오든 이 코드는 절대 변하지 않음
animal.speak();
}
}
새로운 동물이 필요하면 기존 코드의 수정 없이 Animal 인터페이스를 상속받는 새로운 클래스를 만들기만 하면 된다.
✔️ 정리
SRP는 클래스를 깨끗하고 단순하게 만들어 내실을 다지는 것이고, OCP는 클래스 간의 관계를 유연하게 만들어 미래의 변화에 대비하는 것이라고 할 수 있다. 이러한 원칙들을 적용하다 보면 초기 설계 시간은 조금 더 걸릴 수 있지만, 유지보수와 확장성의 면에서 프로젝트의 규모가 커질수록 그 진가가 발휘된다.
'codeit sprint backend > weekly paper' 카테고리의 다른 글
| [4] Spring (0) | 2026.02.09 |
|---|---|
| [3-2] 알고리즘과 자료구조: 시간 복잡도 (0) | 2026.01.26 |
| [3-1] 알고리즘과 자료구조: HashSet (0) | 2026.01.26 |
| [2-2] Java 고급과정: map vs flatMap (0) | 2026.01.22 |
| [1] Git: git rebase vs git merge | git fetch vs git pull (0) | 2026.01.12 |