전체 글
자바는 Call by reference ? Call by value ?
자바의 Call by Value / Call by Reference 프로그래밍을 하다보면 반드시 마주치는 것이 바로 call by value / call by reference 개념이다. 함수의 매개변수에서 값을 복사하느냐 주소값을 참조하느냐에 따라 반환 결과가 달라지기 때문에 대부분의 프로그래밍 교육과정에선 중요시 하게 여긴다. (필자도 학부 시절에 C언어 쪽에서 접했던 기억이 있다.) 자바에서도 역시 call by value 와 call by reference 동작 차이가 존재한다. 자바의 데이터형을 알아보면 크게 두가지로 나뉘게 된다. 기본형(primitive type) - Boolean Type(boolean), Numeric Type(short, int, long, float, double, c..
LSP (리스코프 치환 원칙) 이해하기
리스코프 치환 원칙 - LSP (Liskov Substitution Principle) 리스코프 치환 원칙은 1988년 바바라 리스코프(Barbara Liskov)가 올바른 상속 관계의 특징을 정의하기 위해 발표한 것으로, 서브 타입은 언제나 기반 타입으로 교체할 수 있어야 한다는 것을 뜻한다. 교체할 수 있다는 말은, 자식 클래스는 최소한 자신의 부모 클래스에서 가능한 행위에 대한 수행이 보장되어야 한다는 의미이다. 즉, 부모 클래스의 인스턴스를 사용하는 위치에 자식 클래스의 인스턴스를 대신 사용했을 때 코드가 원래 의도대로 작동해야 한다는 의미이다. 이것을 부모 클래스와 자식 클래스 사이의 행위가 일관성이 있다고 말한다. 무슨 논문 같이 설명했지만, 그냥 우리가 지금까지 자바 프로그래밍을 하면서 질리..
OCP (개방 폐쇄 원칙) 이해하기
개방 폐쇄 원칙 - OCP (Open Closed Principle) 개방 폐쇄의 원칙(OCP)이란 기존의 코드를 변경하지 않으면서, 기능을 추가할 수 있도록 설계가 되어야 한다는 원칙을 말한다. 보통 OCP를 확장에 대해서는 개방적(open)이고, 수정에 대해서는 폐쇄적(closed)이어야 한다는 의미로 정의한다. 여기서 확장이란 새로운 기능이 추가됨을 의미한다. 따라서 해석하자면, 기능 추가 요청이 오면 클래스를 확장을 통해 손쉽게 구현하면서, 확장에 따른 클래스 수정은 최소화 하도록 프로그램을 작성해야 하는 설계 기법을 말한다고 보면 된다. ※ 참고 [ 확장에 열려있다 ] - 모듈의 확장성을 보장하는 것을 의미한다. - 새로운 변경 사항이 발생했을 때 유연하게 코드를 추가함으로써 애플리케이션의 기능..
[Java] synchronized 키워드란?
Synchronized Java는 크게 3가지 메모리 영역을 가지고 있다. static 영역 (Static 영역은 Class Area, Code Area, method Area로 불려지며, 의미상 공유 메모리 영역이라고도 불린다) heap 영역 stack 영역 자바 멀티 스레드 환경에서는 스레드끼리 static 영역과 heap 영역을 공유하므로 공유 자원에 대한 동기화 문제를 신경 써야 한다. 이전 글에서 소개했듯이, 원자성 문제를 해결하기 위한 방법 중 하나인 synchronized 키워드에 대해 설명하려고 한다. synchronized는 lock을 이용해 동기화를 수행하며 4가지의 사용 방법이 존재한다. synchronized method static synchronized method synchro..
[Java] volatile 키워드란?
이전 글에서는 가시성 문제를 해결하기 위해 volatile 키워드를 사용한다고 하였다. 이번 글에서는 volatile 키워드를 통해 가시성을 보장하는 방법을 간단한 예시와 함께 설명하려고 한다. 가시성을 보장하지 못한 예제 public class Volatile { private static boolean stopRequested; public static void main(String[] args) throws InterruptedException { Thread backgroundThread = new Thread(() -> { int i = 0; while (!stopRequested) { i++; } }); backgroundThread.start(); Thread.sleep(1000); stop..
[JAVA] 자바의 동시성 이슈
자바에서 동시성(공유자원 접근)으로 인해 발생할 수 있는 문제점과 이를 해결할 수 있는 방법에 대해 살펴보려 한다. 동시성 프로그래밍에서 발생할 수 있는 문제점 컴퓨터의 CPU와 RAM의 관계도를 그려보면 다음과 같은 그림이 될 것이다. 설명의 편의를 위해 최대한 간단한 예로 들겠다. CPU가 어떤 작업을 처리하기 위해 데이터가 필요할 때, CPU는 RAM의 일부분을 고속의 저장 장치인 CPU Cache Memory로 읽어들인다. 이 읽어들인 데이터로 명령을 수행하고 이 데이터를 다시 RAM에 저장하기 위해서는 데이터를 읽어들일 때의 과정을 역순으로 밟는다. 즉, 적절한 시점에 CPU Cache Memory에서 RAM으로 쓰기 작업을 하게 된다. 그러나 CPU가 캐시에 쓰기 작업을 수행했다고 해서 바로 ..
[JAVA] 자바 NULL 에 관하여...
NULL...Null...null... null 이라는 단어는 프로그래밍을 배워보면 빠르나 늦나 반드시 접하게 되는 녀석이다. 프로그래밍을 갓 접한 사람들은 null을 그저 '값이 없는 것' 으로 외우고 넘어가버린다. 심지어 null을 부정의 뜻으로 0 이나 공백 그리고 false 와 동일선상에 놓고 생각하기도 한다. 당연히 이는 잘못된 정의 이다. 그저 값이 없다는 표현일 뿐인데 개발자의 영원한 숙제 라니 뭐니 라는 표현을 쓰는 이유는, 개발자들이 null을 마주하는 경우가 프로그램 실행중에 에러 메세지(NullPointerException) 로 인해 잘동작 하던 프로그램이 죽어버려 원인을 찾느라 심한 고생을 하기 때문이다. 우선 NULL 이라는 개념은, 영국의 컴퓨터 과학자인 토니 호어(Tony Ho..
[JAVA] 자바 역직렬화 방어 기법
Serializable 구현은 보안에 구멍이 생길 수 있다 보통 자바에서 인스턴스는 생성자를 이용해 만드는 것이 기본이다. 하지만 역직렬화는 언어의 기본 메커니즘을 우회하여 객체를 바로 생성하도록 한다. 직렬화된 파일이나 데이터만 있다면 readObject() 를 통해 생성자 없이 곧바로 인스턴스를 만들수 있기 때문이다. 즉, 역직렬화는 보이지 않은 생성자 이기도 한 것이다. 문제는 만일 어느 객체가 생성자를 통해 인스턴스화 할때 불변식이나 허가되지 않은 접근을 설정하였을 경우 이를 무시하고 생성된다는 점이다. 예를들어 아래 Member 클래스는 생성자로 나이 입력값을 음수를 넣으면 이를 걸러내는 로직이 있다. class Member implements Serializable { private stati..
[JAVA] 자바 직렬화(Serializable)
앞서 자바 직렬화 & 역직렬화에 대해 간단하게 정리된 부분을 좀 더 상세하게 정리하고자 한다. JAVA] 직렬화와 역직렬화 - 간단 정리 자바의 직렬화 & 역직렬화 직렬화(serialize)란 자바 언어에서 사용되는 Object 또는 Data를 다른 컴퓨터의 자바 시스템에서도 사용 할수 있도록 바이트 스트림(stream of bytes) 형태의 연속전인(serial) 데이터로 변환하는 포맷 변환 기술을 일컫는다. 그 반대 개념인 역직렬화는(Deserialize)는 바이트로 변환된 데이터를 원래대로 자바 시스템의 Object 또는 Data로 변환하는 기술이다. 이를 시스템적으로 살펴보면, JVM의 힙(heap) 혹은 스택(stack) 메모리에 상주하고 있는 객체 데이터를 직렬화를 통해 바이트 형태로 변환하..
[JAVA] 직렬화와 역직렬화 - 간단 정리
데이터 직렬화와 역직렬화 데이터 직렬화 메모리를 디스크에 저장하거나, 네트워크 통신에 사용하기 위한 형식으로 변환하는 것이다. 데이터 역직렬화 디스크에 저장한 데이터를 읽거나, 네트워크 통신으로 받은 데이터를 메모리에 쓸 수 있도록 변환하는 것이다. 직렬화는 데이터를 저장 혹은 통신에 사용하기 위한 것은 알겠는데, 왜 데이터를 그냥 사용하면 안 되고 직렬화라는 과정을 거쳐야 하는 것일까? 직렬화가 필요한 이유 개발 언어를 무엇을 선택하든, 사용하는 데이터의 메모리 구조는 크게 2가지로 나뉜다. 값 형식 데이터 int, float, char 등 값 형식 데이터는 스택 메모리 쌓이고 직접 접근이 가능하다. 참조 형식 데이터 객체와 같은 참조 형식 변수를 선언하면 힙 메모리에 할당되고, 스택에서는 이 힙 메모..