자바의 가장 중요한 OOP!에 대해 설명해보겠다.

🔐 Java 접근 지정자(Access Modifiers) 정리
자바에서는 클래스, 변수, 메서드 등의 접근 범위를 제어하기 위해 네 가지 접근 지정자를 사용한다.
✅ 1. public
- 모든 클래스에서 접근 가능
- 패키지 내부/외부 상관없이 접근 허용
- 주로 외부에서 자주 사용하는 클래스나 메서드에 사용
public int number;
✅ 2. protected
- 같은 패키지에서는 자유롭게 접근 가능
- 다른 패키지라도 상속받은 하위 클래스에서는 접근 가능
- 상속을 고려한 멤버 변수나 메서드에 자주 사용
protected String name;
✅ 3. (default) — 접근 지정자 없음
- 같은 패키지 내에서만 접근 가능
- 패키지를 벗어나면 접근 불가
- 별도의 키워드 없이 선언한 경우 적용됨
int age; // default 접근 지정자
✅ 4. private
- 해당 클래스 내부에서만 접근 가능
- 외부 클래스 또는 다른 객체에서 접근 불가
- 데이터 은닉(캡슐화) 목적으로 자주 사용
private double salary;
📝 정리
- 외부에서 자유롭게 사용해야 한다면 → public
- 상속은 허용하지만 외부 접근은 제한 → protected
- 패키지 내부에서만 사용 → default
- 외부 접근 완전 차단, 캡슐화 → private
🔐 자바 private 키워드와 캡슐화 개념 정리

만약 손님이 카페에서 주문을 한다고 하면 손님은 주문만 하면 된다.
레시피, 그 가게가 바쁜지, 가게매출 이런거는 알 필요가없다. 여기서 캡슐화라는 개념이 등장한다.
private 이용

외부에서 알려고하지마라..
나만 알고싶을 떄 private 사용!
public class Dog {
private int age; // 외부 클래스에서 접근 불가
private void speak() {
System.out.println("Woof!");
}
}
public class DogSchool {
public void makeADog() {
Dog cujo = new Dog();
System.out.println(cujo.age); // ❌ 오류 발생: age는 private
cujo.speak(); // ❌ 오류 발생: speak()도 private
}
}
- Dog 클래스의 age와 speak()는 private이므로 DogSchool에서 접근할 수 없다.
오직 같은 클래스 내부에서만 접근 가능하다.
예: 은행계좌를 관리할 때 외부에서 값에 직접적으로 접근 할 수 없도록 막는다. 내 잔액은 공개하기 시르니까~~~~~~
public class CheckingAccount {
private int balance; // 외부 접근 차단
public void printBalance() {
System.out.println("Account balance is " + balance);
}
}

아,.. 접근지정자 하면 따로 할게 많잖아요.. 귀찮아요 그냥 다 public으로 만들래요..
안돼!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
안됩니다....
3️⃣ 왜 모든 걸 public으로 안 하면 좋은가?
- 보안성 강화: 외부에서 실수로 중요한 필드 값을 변경하는 일을 방지.
- 유지보수 용이: 클래스 내부 구조가 바뀌어도 외부에는 영향이 없도록 설계 가능.
- 모듈화: 클래스는 자신의 역할만 수행하고, 다른 클래스에 내부 로직을 노출하지 않음.
그럼 바로 접근할 수 없으면 어떻게하죠,,?

접근하고시퍼요..
*Getter(), Setter()

네 이걸 한번 거쳐서 오시면 됩니다!!
getter/setter는 캡슐화를 유지하면서도 제한된 접근을 허용하는 방법이다.
public class CheckingAccount {
private int balance;
public int getBalance() {
return balance; // 읽기만 허용
}
public void setBalance(int newBalance) {
if (newBalance >= 0) { // 조건을 통해 데이터 보호
balance = newBalance;
}
}
}
*자바 변수의 스코프(Scope)
지역변수,, 전역변수 개념
✅ 1. 인스턴스 변수 (멤버 변수)
- 클래스 내부, 모든 메서드 외부에서 선언된 변수.
- 클래스의 모든 메서드, 생성자 내부에서 사용 가능하다.
public class Dog {
public String name;
public int age;
public Dog() {
name = "Winston"; // 사용 가능
}
public void speak() {
System.out.println("My name is " + name); // 사용 가능
}
}
🧠 인스턴스 변수는 객체가 생성될 때마다 독립적으로 존재하며, 클래스 내 어디서든 접근 가능하다.
✅ 2. 로컬 변수 (Local Variable)
- 메서드나 생성자, 조건문, 반복문 등 블록 내부에서 선언된 변수.
- 선언된 블록({}) 내부에서만 사용 가능하다.
- public, private 같은 접근제어자를 쓰지 않는다.
public void speak() {
String sound = "Woof!";
System.out.println(sound); // ✅ 가능
}
System.out.println(sound); // ❌ 불가. 메서드 바깥에서는 sound가 없음
✅ 3. 매개변수(Parameter)의 스코프
- 메서드에 전달되는 인자(parameter) 도 로컬 변수와 마찬가지로 해당 메서드 내에서만 사용 가능하다.
public void greet(String name) {
System.out.println("Hello " + name); // ✅ 가능
}
System.out.println(name); // ❌ 불가
✅ 4. 조건문 / 반복문 안의 변수 스코프
조건문(if, else, switch)이나 반복문(for, while) 안에서 선언된 변수는 해당 블록 내부에서만 유효하다.
for (int i = 0; i < 5; i++) {
System.out.println(i); // ✅ 사용 가능
}
System.out.println(i); // ❌ 에러: i는 for문 블록 안에서만 존재함
⚠️ 자주 하는 실수
{} 안에서 선언한 변수를 바깥에서 쓰려고 함 | ❌ 컴파일 에러 |
다른 메서드에서 선언한 로컬 변수를 참조하려고 함 | ❌ 불가능 |
인스턴스 변수와 로컬 변수가 이름이 같을 때 혼동 | this 키워드로 구분 가능 |
👉 기억할 점:
- 변수는 선언된 블록 안에서만 쓸 수 있다.
- 접근 제어자(public, private)는 클래스 간의 접근 여부를 결정한다.
- 스코프는 {}로 구분된다. 새로운 블록이 생기면 새로운 스코프가 시작된다고 보면 된다!
- 자바에서는 클래스 내부에서 지역 변수(local variable) 와 인스턴스 변수(instance variable) 의 이름이 겹치는 경우가 자주 발생한다. 이때 어떤 값이 사용되는지 명확히 이해하고, 필요한 경우 this 키워드를 적절히 사용해야 혼란을 줄일 수 있다.
public class Dog {
public String name;
public void speakNewName(String name) {
System.out.println("Hello, my new name is " + name);
}
}
여기서 name이라는 메서드 매개변수가 존재하므로, System.out.println()에서 사용된 name은 인스턴스 변수 name이 아니라 매개변수 name이다. 즉, 지역 변수가 우선된다.
여기서 해결 방법: this 키워드
public void speakNewName(String name) {
System.out.println("Hello, my new name is " + this.name);
}
여기서 this.name은 현재 객체의 인스턴스 변수 name을 의미한다. this는 "현재 객체 자신" 을 가리키는 참조다.
생성자에서 자주 사용됨
public class Dog {
public String name;
public Dog(String name) {
this.name = name;
}
}
this.name = name; 이 문장은 "이 객체의 name에, 매개변수로 전달된 name을 넣어줘" 라는 뜻이다.
자바 this 키워드 메서드 호출에도 쓰인다
하지만 this는 메서드를 호출할 때, 그리고 자기 자신을 인자로 넘길 때도 유용하게 쓰인다.
public class Computer {
public int brightness;
public int volume;
public void setBrightness(int inputBrightness) {
this.brightness = inputBrightness;
}
public void setVolume(int inputVolume) {
this.volume = inputVolume;
}
public void resetSettings() {
this.setBrightness(0); // ✅ this로 메서드 호출
this.setVolume(0); // ✅ this로 메서드 호출
}
}
resetSettings()는 내부에서 setBrightness()와 setVolume()을 호출해야 하는데,
this를 이용해서 현재 객체의 메서드를 호출한다.
this를 메서드 인자로 넘기기
this는 현재 객체 자신이기 때문에, 같은 타입의 매개변수를 받는 메서드에 인자로 넘길 수 있다.
public class Computer {
public void pairWithOtherComputer(Computer other) {
System.out.println("Pairing with another computer...");
}
public void setUpConnection() {
this.pairWithOtherComputer(this); // ✅ 현재 객체를 자기 자신에게 넘김
}
}
📌 이게 왜 유용할까?
- 객체가 자기 자신을 다른 객체에게 전달해야 할 때
- 예: 게임에서 player1.attack(player2) 같은 구조에서 player1.attack(this)처럼 사용 가능
this는 인스턴스 메서드 안에서만 사용 가능
static 메서드 안에서는 this를 쓸 수 없음. (static은 객체 없이 실행되니까!)
결론:
this는 단순히 변수 참조 도우미가 아니라,
자기 자신을 지칭하는 강력한 키워드
메서드를 호출할 때나, 인자로 넘길 때 적극 활용하면 가독성과 유지보수성이 올라간다!
static은 객체에 의존하지 않아!!

static 메서드
static 메서드는 객체 없이 불러내서 사용할 수 있다.
그럼 이걸 언제 사용할까??
1. 객체상태와 무관할 때!
public class MathUtils {
public static int add(int a, int b) {
return a + b;
}
}
int result = MathUtils.add(3, 5); // 객체 없이 바로 사용
2. 클래스 전체에서 공유되는 기능일 때
예를 들어, 프로그램 전체에서 공통적으로 접근해야 하는 설정값을 반환하거나 업데이트하는 기능:
public class Config {
private static int maxUsers = 100;
public static int getMaxUsers() {
return maxUsers;
}
public static void setMaxUsers(int value) {
maxUsers = value;
}
}
3. 메인메서드
자바의 시작점인 main 메서드는 객체 없이 실행되니까 static으로 되어있다.
4. 싱글톤이나 팩토리 메서드 등 객체 생성 제어할 때
public class UserFactory {
public static User createUser(String name) {
return new User(name);
}
}
자바에서는 객체없이 쓰는 static 변수가 존재한다.
- 여기서 static method는 math 같은게 쓰이기 때문에 이해가 갔는데
- 어? static 변수는 언제 쓰이는거지?? 의문이 생겼다. ]
1. 모든 객체가 공유해야 할 값이 있을 때!
public class Dog {
public static int count = 0;
public Dog() {
count++; // 객체가 만들어질 때마다 count 증가
}
}
이 경우 Dog.count는 모든 객체가 공유하기 때문에 new Dog() 할때마다 누적된다.
2. 공통 설정값 저장할 때
예: 게임 전체 설정값, 세금율
public class Config {
public static double TAX_RATE = 0.1;
}
어디서든 접근 가능하고, 객체없이 바로 사용 가능하다.
3. 유틸리티 클래스 만들 때
- 객체 없이 쓰는 도구들
예: 수학 계산기, 문자열 처리기
public class MathUtil {
public static int square(int x) {
return x * x;
}
}
MathUtil.square(5)처럼 사용 가능. 객체 만들 필요 없음.
마무리

이 내용이 그냥 쉽다고 생각하고 ,, 그랬는데 ㅣ자바의 OOP의 기본이 되는 너무너무 중요한 내용 같다!!
복습하면서 아 내가 만드려는 이 구조에는 이렇게 사용해야되겠구나 라는 생각이 들었다...
아 이래서 프로젝트나 프로그램을 직접 설계하고 만들어보는 과정이 필요하구나 라는 생각이 들었따.