java 106

[TIL] 객체지향은 ‘생성’과 ‘사용’의 책임을 분리하는 것에서 시작

전자제품 목록을 출력하는 간단한 커머스 플랫폼 과제를 진행하다가 문득 이런 의문이 들었다.public class CommerceSystem { private List products = new ArrayList();}그냥 CommerceSystem 안에서 List를 직접 생성하면 되는 거 아닌가?왜 굳이 아래처럼 밖에서 만들어서 전달받는 걸까?List products = ...CommerceSystem system = new CommerceSystem(products);처음에는 명확하게 설명하기 어려웠지만, 곰곰이 생각해 보니 ‘역할 분리’와 관련이 있다는 생각이 들었다.CommerceSystem의 책임은 무엇인가?객체지향에서는 항상 이런 질문을 던져야 한다.“이 객체는 무슨 일을 해야..

TIL 2026.06.22

자바 instanceof 쉽게 이해하기 : 타입 검사보다 중요한 진짜 사용 목적

instanceof는 타입 검사 연산자일까, 값을 꺼내기 위한 도구일까?instanceof를 처음 배울 때는 보통 이렇게 배운다.“객체가 특정 타입의 인스턴스인지 검사하는 연산자”실제로 정의만 놓고 보면 맞는 말이다.예를 들어,if (obj instanceof Person) { ...}이 코드는 “obj가 Person 타입인가?”를 검사하는 코드이다.그런데 생각해 보면, 실제로는 단순히 타입이 궁금해서 instanceof를 사용하는 경우가 거의 없다.예를 들어 if (obj instanceof Person) { Person p = (Person) obj; System.out.println(p.getName());}여기서 내가 정말 궁금했던 것은“이 객체가 Person인가?” 가 아니다.사..

TIL 2026.06.19

자바 Class 객체란? 리플렉션(Reflection) 개념과 사용 이유

리플렉션(Reflection)과 Class 객체리플렉션을 처음 봤을 때 가장 헷갈렸던 부분은 Class 객체였다.Class cls = Person.class;처음에는 이 코드가 Person 객체를 생성하는 코드인 줄 알았다. 그런데 아니다.Person p = new Person();이건 Person 객체를 생성하는 코드이고,Class cls = Person.class;이건 Person 클래스 자체의 정보를 담고 있는 Class 객체를 얻는 코드이다.쉽게 말하면,Person 객체= 실제 집Class 객체= 집의 설계도정도로 생각하면 이해하기 편하다.Class 객체에는 무엇이 들어 있을까?Class 객체는 클래스의 메타데이터(클래스에 대한 정보)를 가지고 있다.예를 들어 다음과 같은 정보를 얻을 수 있다.클..

TIL 2026.06.18

자바 프로그램은 어떻게 실행될까? - JRE, JVM, main() 메서드가 실행되기까지

자바 프로그램의 실행과정보통 다음과 같은 간단한 프로그램을 작성하고 실행한다.public class Start { public static void main(String[] args) { System.out.println("Hello OOP!!"); }}코드는 단 한 줄을 출력하지만, 실제로는 이 한 줄이 실행되기까지 JRE와 JVM이 뒤에서 상당히 많은 일을 처리한다.1. 프로그램 실행 버튼을 누르면 가장 먼저 JRE가 움직인다.자바 프로그램을 실행하면 가장 먼저 JRE(Java Runtime Environment)가 실행된다.JRE의 역할은 쉽게 말해 자바 프로그램을 실행하기 위한 관리자라고 생각하면 된다.JRE는 먼저 프로그램 안에 main() 메서드가 존재하는지 확인한다.p..

TIL 2026.06.17

객체와 메모리, 메서드 개념 확인

[Java] 객체와 메모리, 메서드 개념 확인왜 메서드 안에서 객체의 필드는 변경될 수 있는가?참조형 매개변수는 객체 자체가 아니라 객체를 가리키는 참조값(주소값)이 복사된다. 따라서 원본 참조변수와 매개변수가 같은 객체를 바라보게 되고, 메서드 안에서 객체의 필드를 변경하면 원본 객체의 상태도 함께 변경된다. Heap, Stack, Method Area는 각각 무엇인가?Stack은 메서드 호출 정보와 지역변수, 참조변수가 저장되는 공간이고, Heap은 new로 생성한 객체가 저장되는 공간이다. Method Area는 클래스 정보와 메서드 정보, static 변수 등이 저장되는 공간이다. 자바는 왜 Call By Value인가?자바는 메서드를 호출할 때 항상 값을 복사해서 전달한다. 기본형은 실제 값이 ..

TIL 2026.06.16

왜 equals()와 hashCode()를 함께 재정의해야 할까?

자바를 공부하다 보면 equals()와 hashCode()는 항상 같이 오버라이드하라는 말을 많이 듣는다.처음에는 “둘 다 객체 비교와 관련 있나 보다.” 정도로만 생각했는데, 실제로는 둘의 역할이 완전히 다르다.이번 글에서는 간단한 예제를 통해 왜 두 메서드를 함께 재정의해야 하는지 알아보자.자바는 기본적으로 객체의 주소를 비교한다다음 코드를 보자.// Money는 사용자가 정의한 클래스이다.Money m1 = new Money(5000);Money m2 = new Money(5000);System.out.println(m1.equals(m2));결과는 무엇일까?false대부분의 사람은 5000원과 5000원이니까 true를 예상한다.하지만 자바는 기본적으로 객체의 값을 비교하지 않는다.m1 -> 메모..

TIL 2026.06.15

[Java] Map.Entry 인터페이스 쉽게 이해하기

Map.Entry는 Map에 저장된 key-value 한 쌍을 표현하는 인터페이스이다.Map은 데이터를 다음과 같이 저장한다.Map map = new HashMap();map.put("사과", 3);map.put("바나나", 5);map.put("포도", 2);이 Map 안에는 다음과 같은 데이터가 들어 있다.사과 → 3바나나 → 5포도 → 2여기서 "사과" → 3 같은 key-value 한 쌍을 자바에서는 Map.Entry라고 부른다.왜 Map.Entry가 필요할까?Map을 순회할 때 key만 필요하다면 keySet()을 사용하면 된다.for (String key : map.keySet()) { System.out.println(key);}하지만 key와 value를 둘 다 사용하고 싶다면 보통 ..

[TIL] 객체지향 설계가 어려운 이유: 문법이 아니라 도메인 이해의 문제

좋은 프로젝트는 기술이 아니라 도메인 이해에서 시작된다프로젝트를 만들 때 가장 중요한 것은 내가 만들고자 하는 서비스의 도메인을 얼마나 깊이 이해하고 있는가이다.많은 사람들이 포트폴리오를 만들 때 새로운 기술을 사용하거나 복잡한 기능을 구현하는 것에 집중한다. 하지만 실제 면접에서는 “이 기술을 써봤습니다”보다 “왜 이런 구조로 설계했는가”, “서비스를 얼마나 이해하고 있는가”를 더 중요하게 본다.자바 문법이나 프레임워크 사용법은 개발자라면 갖추어야 할 기본기일 뿐이다. 결국 회사가 궁금한 것은 다음과 같다.이 사람이 우리 서비스의 도메인을 이해하고, 비즈니스 요구사항을 코드에 자연스럽게 녹여낼 수 있는가?따라서 개발 과정에서는 단순히 기술을 적용하는 것이 아니라, 지금 내가 만드는 기능이 서비스에서 어..

TIL 2026.06.09

[Java] 조건문과 반복문

📍 if문에 중괄호를 생략하면 생길 수 있는 실수자바에서 if문에 중괄호({})를 생략하면 조건문에 속하는 코드는 단 한 줄뿐이다.따라서 들여쓰기가 같아 보이더라도 두 번째 줄부터는 if문과 무관하게 항상 실행된다.int age = 15;if (age >= 19) System.out.println("성인입니다."); System.out.println("영화 예매가 가능합니다.");위 코드를 보면 두 문장 모두 if문에 속한 것처럼 보이지만 실제로는 첫 번째 출력문만 조건문의 대상이다.실행 결과영화 예매가 가능합니다.의도대로라면 다음과 같이 중괄호를 사용해야 한다.if (age >= 19) { System.out.println("성인입니다."); System.out.println("..

[Troubleshooting] 자바 제네릭 T 타입으로 사칙연산이 불가능한 이유

문제 상황계산기 프로젝트를 진행하며 정수뿐만 아니라 실수도 연산할 수 있도록 기능을 확장해야 했다.요구사항에서는 단순히 int를 double로 변경하는 것이 아니라, 제네릭을 활용하여 여러 숫자 타입을 받을 수 있도록 구현할 것을 요구했기 때문에 다음과 같이 ArithmeticCalculator를 제네릭 클래스로 변경하였다.public class ArithmeticCalculator {}그리고 계산 메서드를 구현하려고 했다.public T calculate(T num1, T num2) { return num1 + num2;}하지만 컴파일 오류가 발생하였다.원인 분석처음에는 제네릭으로 선언했기 때문에 Integer, Double 등 다양한 숫자 타입이 모두 연산 가능할 것이라고 생각했다.하지만 자바의..

TIL 2026.06.08