본문 바로가기
프로그래밍/기타

기술면접 대비 질문목록

by 돌및쓰고 2020. 3. 25.

1. Android

 1. Handler.post, runOnUiThread View.post

                                                                         이미지 출처 : http://itmining.tistory.com/16

- Handler

Hander는 Looper로 부터 메시지를 받아 처리하거나 메시지를받아 MessageQueue에 넣는역할을한다
위 그림처럼 전달하는 것을 담당하고 Lopper에 의존적이다
기본 생성자로 생성 시 MainThread에 MessageQueue와 Lopper에 연결됨

- Lopper 

기본적으로 MainThread는 Looper를 가지며
Thread당 한 개만 가질 수 있고 기본적으로 MessageQueue를 가지고 있다.
Handler에서 messageQueue에 메시지를 받으면 handlemessage를 호출한다

- runOnUiThread, View.post

public final void runOnUiThread(Runnable action) { 
    if (Thread.currentThread() != mUiThread) {
    	mHandler.post(action); 
    } else { 
      	action.run(); 
    } 
 }
 
 //View.post
 public boolean post(Runnable action) {
 	final AttachInfo attachInfo = mAttachInfo;
    if (attachInfo != null) {
     	return attachInfo.mHandler.post(action);
    }

    // Postpone the runnable until we know on which thread it needs to run.
    // Assume that the runnable will be successfully placed after attach.
    getRunQueue().post(action);
    return true;
}
내부적으로 Handler를 사용하여 MainThread에서 Runnable을 사용 
결국 Handler.post를 사용하기 편하게 래핑 한 메서드

추가적으로 View.post는 Attach 되어있을 때만 실행된다

 

2. Layout이 화면에 나오는 과정

Inflate를 통해 xml파일이 java 객체화하며 addview를 함

전위 순회 과정으로 View들을 탐색하고 

onAttachedToWindow->measure -> OnMeasure -> layout -> OnLayout -> dispatchDraw -> draw -> OnDraw 순서로 View를 그리게 된다

measure : view의 크기 지정

layout : view의 위치 지정

invaildate : 다시 Draw

requestLayout : measure부터 다시실행(notifydatachanged 는 이 함수 호출)

 

 

3. Context, Activity 차이

context : 애플리케이션에 대한 포괄 정보를 가지고 있음, 안드로이드 시스템이 제공하는 서비스를 사용할 수 있게 해 준다 
ApplicationContext는 애플리케이션의 생명주기를 따라 사용된다 
ActiviyContext는 Activity의 생명주기에 따라 생기고 사라지는데 이를 static객체에 넘겨주게 되면  생명주기에 따라 사라지지 않고 메모리 Leak을 유발할 수 있음

3. AAC : Android Architecture Components

LiveData, ViewModel, Room, LifeCycle

ROOM : SQLite를 완벽히 활용하여 간단하게 DB사용가능하게 해줍

 

 

4. 행동별 액티비티 생명주기

OnCreate

Activity가 생성될 때 실행되는 것으로 필수적으로 구현해야 함
activity의 생명주기 동안 한 번만 실행되야하는 시작 로직을 넣어야 함
saveInstanceState매개변수를 수신하는데 이전 저장상태가 포함된 Bundle객체이다

 

OnStart는 매우 빠르고 콜백이 완료되면 OnResume를 호출한다

OnResume

재개됨 상태에 들어가면 포그라운드에 표시되고 사용자가 앱을 떠날 때까지 상호작용을 합니다
어떤 이벤트가 발생해 포커스가 변할 때까지 이상태에 머무릅니다
그리고 방해하는 이벤트가 발생하면 OnPause콜 백을호 출합니다

OnPause

activity가 포그라운드에 있지 않다는 의미로, 사용자가 activity를 떠나는 첫 번째 신호입니다 
activity가 일시정지 상태일 때 필요한 작업을 조정합니다(대화 상자, 멀티 윈도) 그러나 안드로이드 7.0부터 지원하는 멀티 윈도 기능을 잘 지원하기 위해 UI 관련 리소스와 작업을 해 재할 때는 OnStop이 바람직하다
OnPause는 아주 잠깐 실행되므로 저장작업을 수행하기에는 시간이 부족하므로 데이터를 저장하거나 네트워크 호출 등은 부적절합니다

OnStop

activity가  사용자에게 더 이상 표시되지 않으면 중단됨 상태에 들어간다
화면에 보이지 않을 때 실행할 필요가 없는 기능을 정지할 수 있다. 
가령 UI 업데이트를 멈출 때 onPause대신 onStop을 사용하면 멀티 윈도 모드에서 UI를 계속 업데이트할 수 있습니다.
데이터베이스를 저장하는 적절한 시기를 찾지 못한다면 OnStop에서 하는 것도 괜찮다

OnDestroy

시스템은 activity를 닫거나 finish를 호출할 때나 기기 회전, 멀티 윈도 모드를 실행해 일시적으로 activity를 소멸시킬 때
호출된다

 

일반 실행

2020-03-27 17:57:46.834 10426-10426/? D/asd: Create
2020-03-27 17:57:46.838 10426-10426/? D/asd: Start
2020-03-27 17:57:46.841 10426-10426/? D/asd: Resume

화면 회전 

2020-03-27 21:56:10.859 16748-16748/com.psplog.scrollviewtest D/asd: Pause
2020-03-27 21:56:10.872 16748-16748/com.psplog.scrollviewtest D/asd: Stop
2020-03-27 21:56:10.872 16748-16748/com.psplog.scrollviewtest D/asd: Destroy
2020-03-27 21:56:10.981 16748-16748/com.psplog.scrollviewtest D/asd: Create
2020-03-27 21:56:10.984 16748-16748/com.psplog.scrollviewtest D/asd: Start
2020-03-27 21:56:10.997 16748-16748/com.psplog.scrollviewtest D/asd: Resume

멀티태스킹(액티비티 전환)

홈으로
2020-03-27 21:57:08.651 16748-16748/com.psplog.scrollviewtest D/asd: Pause
2020-03-27 21:57:08.730 16748-16748/com.psplog.scrollviewtest D/asd: Stop
다시 앱으로
2020-03-27 21:57:49.365 16748-16748/com.psplog.scrollviewtest D/asd: Restart
2020-03-27 21:57:49.375 16748-16748/com.psplog.scrollviewtest D/asd: Start
2020-03-27 21:57:49.377 16748-16748/com.psplog.scrollviewtest D/asd: Resume

종료

2020-03-27 21:58:13.400 16748-16748/com.psplog.scrollviewtest D/asd: Pause
2020-03-27 21:58:14.023 16748-16748/com.psplog.scrollviewtest D/asd: Stop
2020-03-27 21:58:14.023 16748-16748/com.psplog.scrollviewtest D/asd: Destroy

2. 데이터베이스

1. SQL vs NoSQL

SQL (Mysql)

정해진 데이터 스키마에 따라 테이블에 저장되고 관계를 통해 여러 테이블에 분산 저장한다
데이터 스키마를 사전에 계획하기 때문에 구조변경이 어렵고 복잡한 쿼리가 만들어질 수 있다
그리고 데이터의 중복이 없기 때문에 수정이 간단

NoSQL (firebase realtime database)

NoSQL에서는 레코드를 문서(Documents)라부르고 Json과 비슷한 형태로 가지고 있다
RDB와 다르게 여러 테이블에 나누어 담지 않고 관련한 데이터를 동일한 컬렉션에 넣는다

2. INDEX

Table의 Column을 파일로 색인화하여 검색 속도를 빠르게 한다

하지만 파일의 용량이 많아지고 데이터 변경이 일어날 때마다 Index를 새로 만들어하므로 성능에 영향을 미친다

 

3. 트랜잭션

트랜잭션이란 데이터베이스의 상태를 변화시키기 위해 수행하는 작업 단위 (SQL 문의 모음)

ACID는 트랜잭션의 특징이다

-Atomicity(원자성) : 트랜잭션은 DB에 모두 반영되거나 아예 반영되지 않아야 한다.

-Consistency(일관성) : 트랜잭션의 작업 처리 결과는 항상 일관성 있어야 한다.

-Isolation(독립성) : 둘 이상의 트랜잭션이 병행 실행되고 있을 때, 어떤 트랜잭션도 다른 트랜잭션 연산에 영향을 주면 안 된다

-Durability(지속성) : 트랜잭션이 성공적으로 완료되었으면, 결과는 영구적으로 반영되어야 한다.

 

Commit : 트랜잭션이 성공했고 DB가 일관성 있는 상태일 때 이를 알려주기 위한 연산

Rollback : 하나의 트랜잭션이 정상적으로 수행되지 않았을 때 이전 단계로 롤백 

 

 Isolation Level 

트랜잭션에서 일관성 없는 데이터를 허용하도록 하는 수준

하지만 무조건적인 일관성 유지는 데이터베이스의 성능에 영향을 주기 때문에

이를 완화하기 위한 수준이다

0 Level Read uncommitted : 트랜잭션이 처리 중이거나 아직 Commit 되지 않은 데이터를 다른 트랜잭션이 읽는 것을 허용

1 Level Read committed : commit이 이루어진 트랜잭션만 조회가 가능하고 Default 레벨이다.

2 Level Repeatable Read : 트랜잭션 영역에 해당하는 데이터는 수정이 불가능

3 Level Serializable : 트랜잭션 영역에 해당하는 데이터는 수정, 입력이 불가능

 

낮은 Isolation Level의 을 사용 시 수정 중이 데이터를 다른 트랜잭션이 보게 되거나, 일관성이 꺠지거나, 없던 데이터가 갑자기 생기는 현상이 생길 수 있다. 

 

3. 운영체제

1. Process vs Thread

프로세스 : 메모리상에서 작업 중인 프로그램

프로세스는 최소 1개의 스레드를 가지고 있고 Code, Data, Heap, Stack(Thread) 영역을 가지고 있다
Code : 프로그램을 구성하는 메모리 영역
Data : 전역 변수, 정적 변수, 배열등 ( 초기화된 데이터 )
Heap : 동적할당 데이터
Stack : 지역변수 매개변수 리턴값

스레드 : 프로세스 안에서 실행되는 흐름단위

스레드는 Stack을 하나씩 할당받고 나머지영역은 공유한다

세마포어 & 뮤텍스

 

임계 구역 (Critical Section)

여러 프로세스가 데이터를 공유하며 수행될 때, 각 프로세스에서 공유데이터를 접근하는 부분

 

세마포어 P,V 연산

P: 임계구역에 들어가기전에 수행(프로세스 진입을 자원 개수(S)를 통해 결정)

V: 임계구역에서 나올 때 수행(자원 반납 알림)

 

S=1일때 A, B가 임계구역에 접근하게되면

1. A가 접근 P실행 (S= S-1)

2. B가 접근 하지만 S가 0이므로 1일때까지 대기

3. 데이터 처리후 A가 V실행 (S= S+1)

4. B가 S=1이되었으므로 P실행(S = S-1)

5. B가 V실행  (S= S-1)

 

뮤텍스는 이진 세마포어 라고도 불리며

한 Key을 가진 프로세스(스레드)만 임계구역에 접근할수있는 상호배제기법

 

데드락 

발생조건

1. 상호 배제( Mutual Exclusion ): 자원은 한번에 한 프로세스만 사용할 수 있음

- 여러 프로세스가 공유자원 사용

2. 점유 대기( Hold and Wait ) : 최소한 하나의 자원을 점유하고 있으면서 다른 프로세스에 할당되어 사용하고 있는 자원을 추가로 점유하기 위해 대기하는 프로세스가 존재해야함

- 실행전 모든 자원 할당

3. 비선점 (No preemeption) : 다른 프로세스에 할당된 자원은 사용이 끝날때 까지 강제로 뺏을 수 없음

- 다른 프로세스가 자원 요구시 임의로 락을 해제 할 수 있게한다

4. 순환 대기(Circular wait) :  T1(A -> B), T2(B -> C), T3(C -> D), T4(D -> A) 로 되어 있고, 서로가 물려 있는 상태를 뜻합니다.

- 자원의 할당 순서를 매겨 자원을 할당

 

데드락 방지 기법

1. 탐지: 자원 할당 그레프를 통해 교착상태 탐지, 오버헤드 발생

2. 회복: 데드락 프로세스를 종료하거나 강제로 자원을 해제시킨다

3. 회피 : 은행원 알고리즘 

 

IPC(inter process communication)

 

4. 네트워크

TCP vs UDP

TCP : Transmission Control Protocol
ip와 같이 사용하며 ip가 배달을 처리한다면 tcp는 추적 관리한다
흐름 제어와 혼잡 제어를 제공하는데
흐름 제어는 수신 측에서 데이터를 감당할 수 있는 수준으로 데이터를 전송하는 것
ex) Stop and Wait, sliding window
혼잡 제어는 네트워크망의 처리량에 따라 데이터를 전송해 혼잡을 방지하는 것
AIMD : 패킷이 성공적으로 도착하면 window크기를 늘리고 실패하면 속도를 절반으로 줄인다
Slow Start : AIMD와 비슷하지만 지수함수처럼 증가되고 혼잡하면 window크기를 1로 줄인다
Fast Restansmit : 중복된 순번의 패킷을 3개 받으면 재전송한다 약간의 혼잡한 상황이 므로 window사이즈를 줄인다
Fast Recorvery : 혼잡한 상태가되면 window크기를 반으로 줄이고 선형증가시킨다
UDP : User Datagram Protocol
데이터를 데이터그램 단위로 처리하는 프로토콜이다.
비연결형 서비스로 이로인해 패킷은 다른경로로 전송되고 순서를 보장하지 않는다.
이런 특성으로 인해 데이터가 일부 손실되어도 문제없는 스트리밍, 게임같은 서비스에서 사용한다.

 

[TCP] 3 way HandShake

연결을 수립할 때 사용

 

A ---------SYN(X)----------> B 연결 수립을 위해 squenceNum 전송

 

A <--SYN(Y), ACK(X+1)------ B 

 

A ------ACK(Y+1)----------> B

 

[TCP] 4 way HandShake

연결을 끊을 때 사용

fin_wait    A ---------FIN----------> B

 

fin_wait    A <--------ACK--------- B

 

time_wait  A <---------FIN---------- B

 

              A ---------ACK----------> B close

5. Java

JAVA실행 구조

1. JAVA코드를 컴파일러를 통해 JAVA 바이트코드로 컴파일한다

2. 컴파일된 바이트 코드를  JVM의 클래스 로더에게 전달할당

3. 클래스 로더는 동적로딩을 통해 필요한 클래스들을 로딩 및 링크하여 Runtime Data Area 즉 JVM 메모리에 올린다

4. 실행엔진은 JVM에 올라온 바이트 코드들을 명령어 단위로 하나씩 가져와서 실행한다

 

클래스 로더

 

부트 스트랩 클래스로더

-최상위 클래스로더로 유일하게 JAVA가 아닌 네이티브 코드로 구현되어있다.

-JVM이 실행될 때 같이 메모리에 올란간다

-Object 클래스를 비롯하여 JAVA API를 로드한다

 

익스텐션 클래스 로더

-기본 JAVA API를 제외한 확장 클래스들을 로드한다 (다양한 보안 확장기능 로드)

 

시스템 클래스 로더

-부트스트랩과 익스텐션 클래스로더가 JVM 자체의 구성요소들을 로드한다면, 시스템 클래스 로더는 어플리케이션의 클래들을 로드하고, 사용자가 지정한 $classpath내의 클래스들을 로드한다.

 

사용자 정의 클래스로더

-어플리케이션 사용자가 직접 코드상에서 생성하여 사용하는 클래스 로더이다

 

위임모델

위임모델은 처음 바이트코드를 넘겨받은 클래스 로더가 필요한 클래스를 로드할 때 다음 순서대로 클래스가 있는지 확인한다

1. 클래스 로더 캐시

2. 상위 클래스 로더

3. 자기자신

이전에 로드 했던 클래스인지 캐시를 확인하고 없으면 클래스 로더를 하나씩 올라가며 확인 하는데 이때 중요한점은 올라가는 도중에 클래스를 발견하더라도 더 상위 로더에 해당 클래스가 존재하면 상위 클래스를 불러온다는 점이다

 

가시성 제한

클래스 로더 캐시를 확인하고 없으면 상위 클래스 로더를 확인하는데 이 때 하위 클래스로더에 있는 클래스는 확인이 불가능하다

 

언로드 불가

클래스를 로드할수는 있지만 언로드는 불가능하다

 

네임 스페이스

네임스페이스란 각 클래스 로더들이 가지고 있는 공간으로써 클래스를 보관하는 공간이다, 위임모델을 통해 상위 로더를 확인할때 활용하는 공간이 바로 네임스페이스다 

 

로드과정

1. 로드 : 클래스파일을 JVM의 메모리에 로드한다

2. 검증 : 클래스 로드 전과정중 가장 복잡하고 오래걸리는 과정으로 클래스가 JAVA, JVM명세에 맞게 구성되어있는지 확인한다

3. 준비 : 클래스가 필요로하는 메모리를 할당한다 클래스에 정의된 필드, 메서드, 인터페이스들을 나타내는 데이터 구조를 말한다.

4. 분석 : 클래스의 상수 풀 내 모든 심볼릭레퍼런스를 다이렉트 레퍼런스로 변경한다

5. 초기화 : 클래스 변수들을 적절한 값으로 초기화한다 (static 필드 같은)

 

JAVA Runtime Data Area

JVM의 메모리구조는 (* 모든스레드공유, * 각스레드마다 생성)

Method Area : 클래스 멤버변수의 이름, 데이터타입, 접근제어자같은, 상수풀, static 변수등이 생성되는 영역이다.

Heap Area : new 키워드로 생성된 객체와 배열이 생성되는 영역이다 메소드영역에 로드된 클래스만 생성이 가능하고 GC가 이루어지는 영역이다

Stack Area : 지역변수 파라미터 리턴값, 연산에 사용되는 임시 값등이 생성되는 영역이다.

PC Register : 스레드가 생성될 때마다 생성되는 영역으로 Program Counter즉 현재 스레드가 실행되는 부분의 주소와 명령을 저장하고있는영역이다 (Cpu의 레지스터와 다름)

Native Method Stack : 자바 외의 언어로 작성된 네이티브 코드를 위한 메모리 영역이다 보통 jni의 영역이다

 

Garbage Collection

 

C/C++ 언어와 달리 JAVA는 사용자가 직접 메모리를 할당할수 없다 그래서 할당된 메모리를 돌려받기 위해 GC가 사용하지 않는 객체를 제거하고 메모리를 확보합니다.

 

GC에 대해 알아보기 전에 Stop-the-world라는 용어를 알아야한다. Stop-the-world란 GC를 하기위해 어플리케이션이 멈추는 것을 말하고, 어떤 GC를 사용해도 Stop-the-world는발생한다

GC튜닝의 경우 대게 Stop-the-world시간을 줄이는 것을 의미한다

GC를 해도 사용가능한 메모리가 없는경우가 Out of memory 를 발생하게된다

 

일반적으로 GC의 대상은

1. 객체가 NULL인경우

2. 블록 실행종료후 블럭안에서 생성된 객체

3. 부모객체가 null인경우 포함하는 자식객체

 

GC의 기본 프로세스는 Mark & Sweep이라 할 수 있다.

사용하지 않는 객체를 확인하는 Mark

사용하지 않는 객체를 삭제하는 Sweep

추가적으로 Sweep후 분산되어있는 객체들을 Heap의 시작 주소로 모아 정리하는 Compact과정은 Stop-the-world를 유발한다

자바의 Heap메모리는 3가지 영역으로 나누어 관리하는데

Young generation : 새로운 객체들이 이 영역에 할당된다. Eden과 2개의 Survival영역으로 나누어지며 Young 영역에서 일어나는 GC를 Minor GC라고 한다

 

Old generation : Young 영역에서 오랫동안 살아남은 객체가 여기로 이동하며, 대부분 Young영역 보다 크게 할당한다 그래서 Young영역보다 GC가 적게 발생하고 이영역의 GC를 Major GC, Full GC라고 한다

 

Permanet : Method 영역이라고도 하고 JVM이 클래스들과 메소드를 설명하기 위해 필요한 메타데이터를 포함하고 있습니다. JDK8부터는 MetaSpace로 교체됩니다

 

GC과정

1. 새로운 객체가 들어오면 Eden Space에 할당한다.

2. Eden Space가 가득하면 Minor GC를 시작합니다

3. 참조되는 객체는 S0으로 이동되고 비참조 객체는 사라집니다.

4. 다음 Minor GC 떄도 같은 일이 일어나나 이번에는 두번째 Survivor 로 이동하고 객체들의 age도 증가합니다 

5. 이후 에도 3,4 를 반복하며 Survivor를 바꿔가며 객체를 정리하고 각각 Age가 증가합니다.

6. Minor GC를 반복하며 객체의 age가 특정 Threshhold를 넘어가면 Old영역으로 이동합니다. 이를 Promotion이라 한다

7. Old영역이 가득차면 모든 객체를 검사하고 heap영역을 정렬하는 Major GC가 일어난다, 시간이 오래걸리고 gc를 제외한 모든 스레드가 중지한다

 

GC의 종류

 

Serial Gc

JAVA se 5,6에서의 기본 가비지 콜렉터이다. 실글스레드 환경에 맞게 설계되었다 싱글스레드로 작동하기때문에 다른 GC에 비해 Stop The World시간이 길다

 

Parallel GC 

Serial GC와 달리 Young영역의 GC과정을 멀티 스레드로 수행해 Stop-the-world시간이 줄어들었다

 

 

 

 

6. 자료구조  

Collections의 Thread-safe

Thread-safe O : Vector, Hashtable
Thread-safe X : ArrayList, HashMap, HashSet

 

Array vs ArrayList vs LinkedList

Array : 배열은 이미정 해진 메모리 안에서 index를 통해 접근하기 때문에 빠른 데이터 접근이 가능하지만 크기가 정해져 있어 삽입이나 삭제가 어렵다
ArrayList : 내부적으로 데이터를 배열로 관리하기 때문에 추가, 삭제를 임시 배열을 통해 진행하기 때문에 자주 수정되는 경우 성능이 나쁘다
LinkedList : 노드의 앞 뒤를 연결해 둔 형태이기 때문에 추가 삭제를 할 때 앞뒤 노드만 수정하기 때문에 빠르게 할 수 있다.

HashMap vs Hashtable

두 클래스 모두 Map인터페이스 계열이고
HashMap과 Haschtable 은 동기화 여부를 빼면 차이가 거의 없다 

Hash 함수

특정한 알고리즘을 통해 문자열을 정해진 크기의 hash값으로 만드느 함수

"안녕?" -> kf82hnswowsy

"안녕!" -> 24ijnf08uhf3

?에서 !로 바뀌었을뿐이지만 전체적인 값이 바뀌고

단방향연산으로 출력길이 일정하므로 복호화가 불가능함 

하지만 아주 낮은 확률로 다른 문자열이 동일한 hash값을 만들 수 도 있음

이런 충돌문제를 해결하기 위해 체이닝, 오픈어드레스, 선형탐사라는 기법을 사용함

 

 

 

 

댓글