들어가며서비스를 개발하다 보면 거의 모든 데이터에 ID가 필요하다.예를 들어 다음과 같은 데이터들은 대부분 고유한 식별자를 가진다.회원 ID주문 ID게시글 ID댓글 ID결제 ID단일 서버와 단일 데이터베이스만 사용하는 환경에서는 ID 생성이 비교적 단순하다. 데이터베이스의 AUTO_INCREMENT나 SEQUENCE를 사용하면 된다.User Tableid | name---|------1 | Kim2 | Lee3 | Park하지만 시스템 규모가 커지면 상황이 달라진다.서버가 여러 대로 늘어나고, 데이터베이스가 샤딩되고, 여러 지역의 데이터센터에서 동시에 요청을 처리해야 한다면 단순히 숫자를 1씩 증가시키는 방식만으로는 충분하지 않을 수 있다.Server A ─┐Server B ─┼──> ID 생성Se..
어떤 값이 집합에 "있을 수도 있음 / 없음은 확실함"을 매우 빠르고 메모리 효율적으로 판단하기 위한 확률적 자료 구조이다.1. 목적존재 여부 검사를 빠르게 하기 위함정확성보다 속도와 메모리 효율을 우선대표적인 사용 목적캐시 Penetration 방지존재 가능한 키만 Bloom Filter에 미리 등록요청 키가 Bloom Filter에서 없음이면 Cache / DB 접근 자체를 차단존재하지 않는 ID에 대한 반복 DB 조회 방지 및 봇·악성 트래픽 방어중복 요청 차단이미 처리된 요청 ID를 Bloom Filter에 기록하여 요청이 다시 들어올 경우 "이미 처리됨"으로 간주멱등성 보조 수단 및 결제, 메세지 발송 중복 방지 (정확성이 중요한 경우 단독 사용은 부적합) 크롤러의 URL 중복 방문 방지방문한 ..
Redis는 클라이언트 요청을 이벤트 루프 기반으로 처리하고, Redis 자료구조를 직접 읽고 쓰는 명령 실행은 메인 쓰레드 중심으로 동작한다. 하지만 파일 닫기, AOF fsync, 메모리 해제 같은 일부 느린 작업은 백그라운드 쓰레드로 넘긴다.그래서 Redis를 정확히 이해하려면 다음 두 가지를 구분해야 한다.1. Redis 명령 실행 경로 - GET, SET, INCR, HSET 같은 명령 실행 - 메인 쓰레드 중심2. Redis 프로세스 전체 - 메인 쓰레드 외에도 백그라운드 쓰레드 존재 - 파일 닫기, AOF fsync, lazy free 등 처리1. Redis가 싱글 쓰레드라는 말의 의미Redis가 싱글 쓰레드라고 할 때 핵심은 데이터를 읽고 쓰는 명령 실행 경로가 기본적으로 하..
실행 계획을 보다 보면 range, ref, ALL 같은 접근 방식과 함께DBMS에 따라 인덱스 풀스캔에 가까운 동작이 등장한다.이름만 보면 비효율적으로 느껴질 수 있지만, 실제로는 상황에 따라 꽤 합리적인 선택이 된다.중요한 건 “인덱스를 일부만 읽는 스캔이 아니라, 인덱스 전체를 읽는 스캔” 이라는 점이다.1. 인덱스 풀스캔이 무엇이며, 어떻게 동작하는가인덱스 풀스캔은 말 그대로 인덱스의 처음부터 끝까지 전체를 읽는 방식이다.보통 인덱스는 특정 값을 빠르게 찾기 위해 사용한다고 배운다.예를 들어 where id = 10 같은 조건에서는 인덱스의 일부만 읽으면 된다.그런데 어떤 쿼리는 조건 검색보다도 정렬된 순서나 인덱스에 담긴 컬럼 자체가 더 중요하다.이럴 때 옵티마이저는 테이블 전체를 읽는 대신 인..
설치 1. github에서 tar.gz 파일 다운로드 (https://github.com/yahoo/CMAK) 2. 압축 해제 후 설치한 폴더 내에서 ./sbt clean dist 명령어 실행 Cannot use JVMCI compiler: No JVMCI compiler found 명령어 실행 시 위 에러가 발생한 경우, 링크 참고 3. target/universal 경로에 생성된 .zip 파일을 원하는 위치에 압축 해제 4. conf/application.conf 파일 수정 (로컬에 주키퍼를 띄웠기 때문에 아래와 같이 수정) 5. ./bin/cmak 명령어 실행 후, localhost:9000 접속 ! @7jn3njc8f - Internal server error, for (GET) [/assets..
기수 정렬 (Radix Sort) ? 기수 정렬은 각 자리 위치를 하나씩 증가시키면서 숫자들을 정렬하는 방법이다. 안정 정렬에 속하며, 카운팅 정렬과 마찬가지로 값의 비교연산 없이 정렬한다. 기수 정렬의 단점은 다음과 같다. 제자리 정렬이 아니기 때문에 추가적인 메모리가 필요하다. 동일한 길이를 가진 숫자나 문자열이여야 한다. 정렬하는 숫자 자릿수 \(k\) 에 따라 \(O(kn)\) 의 시간 복잡도를 가진다. 기수 정렬 과정은 다음과 같다. 1의 자리 숫자를 비교해서 오름차순 또는 내림차순으로 정렬한 뒤, 큐 버킷에 삽입한 뒤 순서대로 뽑아 정렬한다. 그 다음, 10의 자리 숫자를 비교해서 동일하게 수행한다. 가장 큰 숫자의 자릿 수만큼 반복해서 수행한다. Code public static void r..
Proxy 클라이언트가 프록시 서버를 통해서 다른 네트워크 서비스에 간접적으로 접속할 수 있게 해주는 컴퓨터 시스템 또는 응용 프로그램 프록시 (Proxy) : 서버와 클라이언트 사이에서 대리로 통신을 수행하는 것 프록시 서버 (Proxy Server) : 중계 기능을 수행하는 서버 1. Forward Proxy 클라이언트가 인터넷에 접근하는 것이 아니라 프록시 서버가 요청을 받고 인터넷에 연결하여 결과를 클라이언트에 전달 (Forward) 해준다. 장점 보안 : 프록시 서버에서 In / Out Bound 패킷에 대한 보안 정책 (Content Filtering 등) 을 적용할 수 있다. 성능 : 프록시 서버 내부에 캐시를 유지하며 한 번 통신한 외부 서버의 이미지, 파일 등을 저장할 수 있다. 캐시에 ..
count(*) VS count(1) 차이가 없다. count(*) VS count(컬럼) count(*) : null을 포함하여 모든 Row 수를 카운트한다. count(컬럼명) : null을 제외한 Row 수를 카운트한다. Reference https://dev.mysql.com/doc/refman/8.0/en/aggregate-functions.html#function_count https://asktom.oracle.com/pls/apex/f?p=100:11:0::NO::P11_QUESTION_ID:1156159920245