JAVA - 기술면접

홍성우·2023년 2월 5일

JAVA 기술면접

목록 보기
1/3

0.JAVA 특징
JAVA는 객체지향 프로그래밍 언어(Oriented Object Programming)
기본형(primative type) 8개를 제외한 모든 타입을 객체로 표현하며
객체지향 특징

  • 캡슐화/은닉화
  • 상속성
  • 다형성
  • 추상화

각 OS에 맞는 JVM을 설치해야한다.

장점
JVM(컴파일러) 위에서 동작하기 때문에 OS에 독립적이다.
G.C를 통한 자동적인 메모리 관리가 가능
이식성 이좋다.

단점
JVM 위에서 동작하기 때문에 실행 속도가 상대적으로 느리다.

  • 속도가 상대적으로 느리다는 것은?
    C,C++과 달리 JAVA는 JVM을 한번더 거치기 때문에 C,C++보다 느리다.

다중상속이나 타입에 엄격하며, 제약이 많다.

0.1 JVM의 역할
JVM은 스택기반으로 동작하며 Byte code를 os에 맞게 해석을 해주는 역할과 메모리 관리를 해준다.

0.2 JAVA 컴파일 과정
사용자가 소스코드를 작성(.java)
javac -자바 컴파일러가 소스코드를 컴파일한다.(java.class)
Class Loader를 통해 JVM메모리내로 로드한다.
JVM이 컴파일 소스를 해석한다.

0.3 JAVA에서 제공하는 원시 타입에 대한 정보
byte 1 (byte)
short 2 (byte)
char 2 (byte)
int 4 (byte)
long 8 (byte)
double 8 (byte)
float 4 (byte)
boolean 1 (byte)

1.추상클래스와 인터페이스의 차이점

공통점 : 객체의 다형성을 구현하기 위해 사용된다.
직접 객체로 생성할수 없고 구현한 클래스를 통해 객체를 생성해야 한다.

차이점

  • 추상클래스는 abstract 키워드를 사용하며
  • 상속받은 클래스들의 공통적인 로직을 추상화 시키고 기능을 확장하기 위해 사용된다.
  • 다중상속이 불가능하다.

인터페이스는

  • 인터페이스내의 선언된 필드는 static final(상수)로 선언되며 메서드는 모두 추상 매서드 로 선언된다.
  • 구현하는 클래스는 인터페이스의 메서드를 모두 재정의 하도록 강제한다.
  • 다중상속이 가능하다.
  1. 싱글톤 패턴이란
  • 싱글톤 패턴은 단 하나의 인스턴스를 생성해 사용하는 디자인 패턴
  • 인스턴스가 1개만 존재해야 한다는 것을 보당하고 싶은 경우와 동일한 인스턴스를 자주 생성해야 하는 경우에 주로 사용된다(메모리 낭비 방지)

ex) 싱글톤 패턴의 대표적인 예시는 Spring bean 입니다.
스프링의 빈 등록 방식은 기본적으로 싱글톤 scope이고, 스프링 컨테이너는 모든 빈들을 싱글톤으로 관리한다.

싱글톤 scope란 어플리케이션 실행시 인스턴스를 하나만 생성해서 사용하는것

  • 싱글톤 빈 사용시 주의할점
  • 프로퍼티 공유
    싱글톤 객체의 프로퍼티는 thread-safe 하다고 보장 할수 없다.
    멀티 쓰레드 환경에서 싱글톤 객체의 프로퍼티는 여러 쓰레드에 의해 바뀔수 있는데 가령 쓰레드 A에서 프로퍼티 값을 x로 바꾸고 출력하는 과정에서 쓰레드 B가 프로퍼티 값을 y로 바꾸면 쓰레드 A입장에서는 예상치 못한 결과가 나올수 있다.

  • 싱글톤 빈은 모두 기본적으로 어플리케이션 구동시 생성되므로 싱글톤 빈이 많을 수록 구동시간이 증가 할수 있다.

3.Protoype 패턴 인스턴스 생성
프로토 타입 패턴으로 인스턴스를 생성하면 싱글톤 패턴과 달리
어플리케이션 구동시 각각의 인스턴스를 생성할수 있게 된다.

설정 방법

  • Prototype Scope
    빈의 scope 설정은 @Scope 어노테이션으로 설정할수 있다.
    프로토타임 Scope으로 설정하려면 @Scope("prototype")과 같은 문자열로 지정해 준다.

@Scope("prototype")으로 설정하면 IOC에서 빈을 받아올때 매번 인스턴스를 새로 생성한다.

하지만 싱글톤 빈이 프로토타입 빈을 참조하는 경우 문제가 발생할 수 있다.
{ 싱글톤 내부에 프로토타입 빈이 존재할지라도 생성되는 것은 결국 싱글톤 객체이다 }
이것을 해결하고자 Proxy가 등장한다.

  • Proxy란
    해당 빈을 사용하는 또다른 빈이 프록시로 감싼 빈을 사용하게 된다.
    싱글톤 빈이 프로토타입 빈을 사용할때 proxy로 감싸야하는 이유는
    프로토타입 빈을 직접 참조하면 인스턴스를 새로 생성해줄 여지가 없기 때문이다.
    즉 매번 인스턴스를 새로 생성해 줄수 있는 프록시로 감싸주는 것이다.

결과적으로 실제 인스턴스를 감싸는 프록시 인스턴스가 생성되고, 이 프록시 인스턴스가 빈으로 등록된다.
따라서 실직적으로 주입 되는 빈은 프록시 빈이다.

3.Pojo (plan old java object)
등장 배경 ORM(Object Relationship Mapping)이 등장햇을때
ORM 기술을 사용하고 싶다면 ORM을 지원하는 프레임워크를 사용해야 했었다.대표적으로 Hiberate라는 프레임워크가 있다.
만약 객체가 ORM기술을 사용하기 위해 hibernate프레임워크를 직접 의존하는 순간 pojo라고 할수 없다.

즉 특정 기술을 의존하지 않고 자바코드로 객체 관계를 설정하는 것이 pojo이다.

  • 스프링에서 POJO를 유지하면서 hibernate를 사용하는 법
    특정기술에 종속적이면 POJO가 아니라면서 스프링에서는 어떻게 사용이 가능한가?
    바로 스프링에서 정한 표준 인터페이스(JPA)가 있기 때문이다.
    JPA구현하게 되면 POJO형식을 유지하며 개발할수 있다 이것을 (PSA)라고 한다.
  1. 가비지 컬렉션(G.C)
    가비지 컬렉션은 어플리케이션에서 동적으로 할당된 heap영역 대해 필요없어진 객체를 자동으로 관리해준다.

과정
GC작업을 수행하기 위해 JVM이 어플리케이션의 실행을 잠시 멈추고,
GC를 실행하는 쓰레드를 제외한 모든 쓰레드의 작업을 중단 후(STOP THE WOLRD 과정) 사용하지 않는 메모리를 제거(Mark and Sweep 과정)하고 작이 재개 된다.

즉 , 모든 프로세스 중단후 -> gc영역 쓰레드만 재개 후 heap영역제거 ->
다시 프로세스 재개

  1. 객체 지향 설계원칙
    객체지향(Oriented Object Programming)특징
    모든 데이터를 객체 취급하며 처리요청을 받은 객체를 객체안의 기능를 사용해 처리한다.
    특징으로는 추상화,캡슐화,다형성,상속이 존재하며 모듈의 재사용성과 유지보수에 효과적 입니다.
  • SRP : 단일 책임 원칙 - 한 클래스는 하나의 책임만 가져야한다.
  • OCP : 개방 폐쇄 원칙 - 확장에는 열려있고, 수정에는 닫혀 있어야한다.
  • LSP : 리스코프 치환 원칙 - 상위 타입은 항상 하위 타입으로 대체할수 있어야한다.
  • ISP : 인터페이스 분리 원칙 - 인터페이스 내에는 메서드는 최소한 일수록 좋다.
  • DIP : 의존관계 역전원칙 - 구체적인 클래스보다 인터페이스,추상클래스를 통해 관계를 맺어라
  1. SerialVersionUID
    JVM은 직렬화와 역직렬화를 하는 시점의 클래스에 대한 버전 번호를 부여한다. 만약 그 시점에 클래스이 정의가 바뀌었다면 새로운 버전 번호를 할당한다.
    그래서 직렬화할때 역직렬화를 하면 번호가 다르게 해석된다. 이런문제를 해결하기 위해 SerialVersionUID를 사용한다.

만약 직렬화할때 사용한 SerialVersionUID의 값과 역직렬화 하기 위해 사용했던 SVUID가 다르면 InvaildClassException이 발생한다.

ex) 클래스1(1001) <-> 역직렬화 된 클래스1(0110)
클래스1 수정(1002) 역직렬화화면 (0110)클래스가 아니게 된다.
이때 SerialVersionUID를 사용한다.

  1. SET 과 Map 타입이 Wrapper Class가 아닌 Object를 받을때 중복 검사는 어떻게 하는가?
    먼저 hashcode() 메서드를 오버라이딩하여 비교 후 값이 다르면 다른객체
    해쉬코드 값이 같으면 equals() 메서드를 오버라이딩하여 다시 비교
    이 두개가 모두 맞은면 중복 객체

8.Generic
Generic이란 데이터 타입을 하나로 지정하지 않고, 사용할때 마다 범용적이고 포괄적으로 지정한다

제네릭 타입을 사용하므로써 잘못된 형식의 데이터 타입을 컴파일과정에서 확인 할 수 있다.

9.final과 finally/finalize 차이

  • final - 불변객체를 만들때 사용 (한번 초기화되면 그 이후 변경 x)
  • fianl메서드는 다른 클래스가 이 클래스를 상속할때 메서드를 오버라이딩을 금지한다.

아래 그림을 보며 이해


B클래스 메서드를 상속받은 A클래스에서 print()함수는 재정의가 불가능하다.

  • final클래스는 다른 클래스에서 이 클래스를 상속 할수 없다.

  • fianlly
    try~catch문과 함께 사용되며 try~catch문에서 예외처리 여부와 관꼐 없이 반드시 실행해야하는 문을 기재한다.

ex)

try{
 	int n = br.readLine(); // 에러 발생
    
	System.out.println("yes") // 실행되지 않음
}catch(Exception e){

}fianlly{
  br.close() ; // bufferedReader는 실행여부와 관계 없이 반드시 닫                   아줘야한다.
}
  • fianlize는 Oject클래스에 정의되어 있는 메서드 이며, GC에 의해 호출되는 메서드로 절대 호출해서는 안되는 메서드 이다.
    G.C가 발생하는 시점이 불분명하기 때문에 해당 메서드가 실행되는 보장이 없고,finalize 메소드가 오버라이딩 되어 잇으면 GC가 이루어질때 Garbage Collecting되지 않습니다.
  1. 직렬화(Serialize)에 대해 설명하시오
    직렬화란 시스템 내부에 잇는 데이터를 외부에서 사용할수 있게
    byte형태로 변환하는 기술

직렬화란 시스템 내부에 있는 데이터를 외부에서 사용할수 있게 byte형태로 변환하는 기술이다.

반대로 byte형태 데이터를 시스템 내부 데이터 타입으로 변환하는 기술을
'역직렬화'라고 함.

객체를 파일로 저장하거나 다른 서버의 객체를 읽어야하는 경우
Serialize를 사용한다.

Serialize을 구현하면 JVM이 해당객체를 저장하거나 외부로 전송할수있게 도와준다.

Serialize의 인터페이스를 살펴보면 해당 추상메서드는 존재하지 않는다.
이러한 매서드가 필요한 이유가 뭘가?
객체를 파일로 저장, 다른 서버의 데이터를 읽어들일때 사용한다.

시스템적으로는 JVM이 STACK와 HEAP영역의 데이터를 BYTE형태로 변환하여 제공한다.

  1. 자바 메모리 영역
  • Method - 전역 변수 ,static 붙은 클래스,변수,메서드가 생성되는 영역이며 런타임시 초기 메모리에 올라간다.

  • stack - primarytype(기본형) 데이터,매개변수,지역변수가 생성되는 영역으로 메서드 호출시 stack영역에 올라가고 메서드 종료시 해제된다.
    LIFO 특성으로 새로 들어온 데이터로 덮어쓰기 된다.

  • heap - 동적으로 할당되는 영역이며 G.C 관리대상 영역이다.

  1. 클래스와 객체
    클래스는 객체의 설계도
    필드,메서드,생성자를 가지고 있다.

객체 : 클래스 정보를 가지고 만들어 지는 것을 의미

인스턴스 : 실제 객체를 의미한다.

12.Wrapper class
primative type -> Object타입으로 변경하는 것
primative type - > wrapper 클래스 타입 (Boxing)
Wrapper class - > primative type (Unboxing)

13.Synchronized
여러개의 쓰레드가 임계영역의 자원을 사용할때 사용된다.
한 쓰레드가 임계영역의 자원을 사용하고 있을때 Synchronized 키워드를 사용하여 다른 쓰레드가 접근 못하도록 한다.

멀티 쓰레드 환경에서 thread-safe를 보장한다.

하지만 Synchronized키워드를 남발하게 되면 프로그램의 성능을 저하한다.
왜?
Synchromized클래스 내부적으로 메서드와 변수에 대해 block/unblock을 처리 하기 때문에

진솔, 온테크 시스템,

  • 불변객체란(Immutable Object)
    한번 초기화되면 변경되지 않는다.
    primative타입일경우 final키워드로 불변객체를 만든다.
    참조타입일 경우 추가적인 작업이 필요하다.

  • 추가적인 작업이이란

불변객체 만들기 전

   
	public class Animal{
    	private final Age age; // 불변객체 만들기 전
        
      
        
        
    }
    
    
    public class Age{
    	private int val;
        
        
    }
    
    // 아직은 불변객체가 아니다.
    

참조 타입 불변객체 만들기 (내부 클래스 변수에 final 붙이기)

   
	public class Animal{
    	private final Age age; // 불변객체 만들기 전
        
      
        
        
    }
    
    
    public class Age{
    	private final int val; // final 키워드 붙이기
        
        
    }
    
    // 아직은 불변객체 생성
    

(2) array인 경우

	public class Animal{
    	private final Age age;
        
    }
    public class Age{
    	private final int val;
     	
        public int getVal(){
           return this.val;
          }
     }
    
    public class ArrayofObject{
    	private Animal array[]
        
        public Amnimal[] getAgeArray(){
        	return array==null? null : array.clone();  //복제 해서 반환
        }
        
    }
    

(3) List인 경우



	public class Animal{
    	private final Age age;
        
       
    }
    class Age{
    	private final int val;
        
        // getter
        public int getVal(){
        	return this.val;
        }
        
    }
    
    public class ListObject{
    	List<Animal> list;
        
        public List<Animal> getAgeList(){
             return Collections.unmodifiableList(animals);
        }
        
    }
    
  1. String,StringBuffer,StringBuilder의 차이점
  • String은 불변속성을 가지며,StringBuffer와 StringBuilder는 가변속성을 가진다.
  • StringBuffer는 동기화를 지원, StringBuilder는 동기화를 지원 x
  • StringBuffer는 멀티 쓰레드 환경에서 주로사용
  • StringBuilder는 단일 쓰레드 환경에서 주로 사용
  1. String 객체가 불변인 이유(immutable)
    • 안전 - 여러 변수가 참조해도 값이 변경되지 않으므로 안전하다.
    • 성능 및 효율 - java heap 영역 안에 String pool 이 존재하고 String 값을 여러 개의변수가 공통으로 참조할 수 있게 설정 하여 메모리 부분에서 효율적이다.
  • String 변수를 다른곳으로 넘겨줄때 String의 원본 레퍼런스값을 그대로 전달해도 된다. (자바에서는 값을 전달할때 복사하여 전달한다(Pass by value)
       하지만 String은 immutable의 특징으로 그대로 전달해도 된다.)

단점

  • String이 immutable객체이므로 A 라는 값에 새로운 문자열 B를 추가한다면 새롭게 String을 만들어야한다.개선하기 위해 StringBuilder,StringBuffer 사용 [참고]
  • Pass-by-value : 전달받은 값을 복사하여 사용 서로 독립적
  • Pass-by-Reference : 전달받은 값의 참조값을 그대로 사용 서로의 영향을 준다.
  1. 접근 제한자(Access Modifier)
    변수 또는 메서드의 접근 범위를 설정할때 사용하며 4가지 종류가 존재
  • public - 모든 패키지에 접근 가능

  • protected - 해당 패키지 접근 + 다른 패키지 상속받은 자식클래스 접근 가능

  • default - 해당 패지지 접근 가능

  • private - 비공개 (해당클래스에서만 접근가능)

  1. 클래스 맴버 변수 초기화 순서
  • static 변수 선언부 : 클래스가 로드 될대 변수가 제일 먼저 초기화된다.

  • instatnce 변수 : 객체가 생성될때 생성자보다 먼저 초기화 된다.

  • 생성자 lock : 객체가 생성될때 JVM이 내부적으로 locking

클래스 변수 초기화 : 클래스가 로드 될때 처음 단 한번 초기화 된다.

인스턴스 변수 초기화 : 객체가 생성될때마다 인스턴스를 초기화한다.

  1. static 에 대해 설명
  • static 키워드를 사용한 변수나 메소드는 클래스가 메모리에 올라갈때 자동으로 생성되며 클래스 로딩이 끝나면 객체 생성없이 바로 사용할수 있다.

    모든 객체가 자원을 공유할수 있으며, GC영역 밖이므로 프로그램이 종료 될때까지 메모리에 유지된다.

  1. new String()과 리터럴 차이
    new () 동적할당자로 생성시 heap영역에 새로 생성하며, “”리터럴로 생성시 String pool 영역에 생성합니다.
  1. static을 사용하는 이유
    프로그램 로딩시 처음 메모리 영역에 생성되며 공용자원으로 사용된다.
    static은 자주 변하지 않는 값을 선언하는 것이 효율적이다.
    인스턴스 객체 없이 바로 사용이 가능하다.
    그 이유? 메모리에 처음 static 메서드와 변수가 로딩 되기때문에
    이미 사용하는 시점에 이미 메모리 영역에 존재한다.

19.Inner class(내부 클래스)
장점

  • 서로 연관되는 클래스를 논리적으로 묶어서 표현하여, 코드의 캡슐화를 증가 시킨다.
  • 외부에서 내부 클래스에 접근 할수 없으므로 코드의 복잡성을 줄일수 있다.
  1. 리플렉션(Reflection)
    리플렉션이란 구체적인 클래스 타입을 알지 못해도 , 그 클래스이 메서드와 변수에 접근이 가능하도록 돕는 자바 API이다.

EX)
프레임워크,IDE에서 이런 동적 바인딩을 이용한 기능을 제공한다.
자동완성 기능 , 스프링 어노테이션이 리플렉션을 이용한 기능이라고 할수 있다.

ALT + ENTER 를 통해 정확한 라이브러리를 몰라도 완성해준다.

  1. Error와 Exception 차이
    Error - 컴파일 시점에 체크 할수 없고, 오류가 발생하면 프로그램은 비정상 종료되며
    예측 불가능한 UncheckedException에 속한다.

치명적인 오류로 보통 프로그래머가 대처 할수 없습니다.

Exception - 프로그래머가 대체 할수 있는 에러로
try~catch를 이용하거나 throws, throw를 통해 프로그램의 비정상 종료를 막을수 있습니다.

throws - 발생할수 있는 에러를 명시적으로 선언할때 사용
throw - 프로그래머가 발생시키는 에러

21.checkedException 과 UncheckedException
checkedException - 실행하기전 알수 있는 에러 즉 컴파일러가 에러를 잡아준다.
대표적인 예외 : IOException, ClassNotFoundException

UncheckedException : 실행하고 난 후 알수 잇는 에러
대표적인 예외 : NPE,ArrayIndexOutOfBoundException

RuntimeException은 UncheckedException을 상속한 클래스이다.
나머지 예외들은 checkedException을 상속한 클래스이다.

  1. 컬렉션 프레임워크란
    다수의 데이터를 쉽고 효과적으로 관리할 수 있는 표준화된 방법을 제공하는 클래스들의 집합

Collection framework종류
List,set,queue

단 Map은 Collection framework가 아니다.
map의 val값들을 List로 바꾸는 메서드 values()가 있다.

  1. HashTable vs HashMap차이
    초기 버전 HashTable
    HashMap 2세대 버전

HashTable은 thread-safe를 보장하고, key 값의 null을 허용하지 x
HashMap은 thread-safe를 보장하지 않습니다, key값의 null 값을 허용

profile
제 블로그를 방문해 주셔서 감사합니다

0개의 댓글