Entity Node는 GEUL 스트림에서 개체(사람, 장소, 사물, 조직, 개념 등)를 식별하는 고정 길이 4워드(64비트) 패킷이다.

SIDX 본질

특성설명
Non-unique같은 SIDX에 여러 개체 가능
Multi-SIDX한 개체가 여러 SIDX 가능 (시점/역할별)
비트 = 의미비트 위치 자체가 속성을 나타냄
추상/구체 연속Mode와 Attributes 채움 정도로 구분

예시:

  • 트럼프 (부동산 사업가) → SIDX_A
  • 트럼프 (대통령) → SIDX_B (다른 SIDX)
  • “Human + Male + Korea” → 추상적 “한국 남자”
  • “Human + Male + Korea + 1946 + Business + …” → 거의 특정 인물

설계 원칙

Q아이디 내재 포기:

  • 순수 의미정렬에 비트 전체 투자
  • WMS SIMD 필터링 성능 극대화
  • Q아이디는 트리플로 별도 연결: (Entity_SIDX, P-외부ID, "Q12345")

Serial 비트 불필요:

  • WMS 쿼리는 2단계: SIMD 범위 좁히기 → 범위 내 디테일 체크
  • Serial은 의미 없는 숫자라 SIMD에 기여 안 함
  • 그 비트를 의미정렬에 투자하면 1단계에서 더 좁혀짐

비트 레이아웃 (4워드 = 64비트)

1st WORD (16비트)
┌─────────┬──────┬────────────┐
│ Prefix  │ Mode │ EntityType │
│  7bit   │ 3bit │   6bit     │
└─────────┴──────┴────────────┘

2nd WORD (16비트)
┌─────────────────────────────┐
│     Attributes 상위 16비트   │
└─────────────────────────────┘

3rd WORD (16비트)
┌─────────────────────────────┐
│     Attributes 중위 16비트   │
└─────────────────────────────┘

4th WORD (16비트)
┌─────────────────────────────┐
│     Attributes 하위 16비트   │
└─────────────────────────────┘
필드비트크기설명
Prefix1-770001001 (Entity Node)
Mode8-1038가지 양화/수 모드
EntityType11-16664개 상위 타입
Attributes17-6448타입별 가변 스키마

Mode (3비트)

Mode는 개체의 **양화(Quantification)와 수(Number)**를 3비트로 통합 표현한다.

코드이진의미예시
0000등록 개체이순신, 삼성전자, BTS
1001특정 단수“그 사람”
2010특정 소수“그 몇몇”
3011특정 다수“그 사람들”
4100전칭“모든 ~”
5101존재“어떤 ~”
6110불특정“아무 ~”
7111총칭“~ 일반”

등록 개체 (Mode=0)

  • 위키데이터 Q아이디, 워드넷 Synset 등 외부 ID와 매핑된 개체
  • Q아이디 자체는 트리플로 연결: (Entity_SIDX, P-외부ID, "Q12345")
  • 수(Number) 개념과 무관: 삼성전자는 “하나"지만 단수라 하기 애매, BTS는 그룹이지만 하나의 개체

대명사/추상 (Mode=1~7)

  • EntityType + Attributes로 의미 범위 지정
  • 비트가 채워질수록 구체적
  • 예: Human(Type) + Male(Attr) + Korea(Attr) = “한국 남자”

EntityType (6비트 = 64개)

위키데이터 P31(instance of) 빈도 통계 기반으로 64개 상위 타입을 배정한다. 세부 분류는 Attributes 내 소분류 비트로 처리한다.

범위카테고리타입 수대표 타입
0x00-0x07생물/인물8Human, Taxon, Gene, Protein
0x08-0x0B화학/물질4Chemical, Compound, Mineral, Drug
0x0C-0x13천체8Star, Galaxy, Asteroid, Planet
0x14-0x1B지형/자연8Mountain, River, Lake, Island
0x1C-0x23장소/행정8Settlement, Village, Street, Park
0x24-0x2B건축물8Building, Church, School, Bridge
0x2C-0x2F조직4Organization, Business, PoliticalParty
0x30-0x3B창작물12Painting, Document, Film, Album
0x3C-0x3F이벤트/기타4SportsSeason, Event, Election, Other

코드 테이블 (64개 전체)

코드타입Q-ID개체수
0x00HumanQ512.5M
0x01TaxonQ165213.8M
0x02GeneQ71871.2M
0x03ProteinQ80541.0M
0x04CellLineQ21014462154K
0x05FamilyNameQ101352662K
0x06GivenNameQ202444128K
0x07FictionalCharacterQ1563261798K
0x08ChemicalQ1131451711.3M
0x09CompoundQ111731.1M
0x0AMineralQ794662K
0x0BDrugQ1214045K
0x0CStarQ5233.6M
0x0DGalaxyQ3182.1M
0x0EAsteroidQ3863249K
0x0FQuasarQ83373178K
0x10PlanetQ63415K
0x11NebulaQ120578K
0x12StarClusterQ1688455K
0x13MoonQ25373K
0x14MountainQ8502518K
0x15HillQ54050321K
0x16RiverQ4022427K
0x17LakeQ23397292K
0x18StreamQ47521194K
0x19IslandQ23442153K
0x1ABayQ3959425K
0x1BCaveQ3550920K
0x1CSettlementQ486972580K
0x1DVillageQ532245K
0x1EHamletQ5084148K
0x1FStreetQ79007711K
0x20CemeteryQ39614298K
0x21AdminRegionQ15284100K
0x22ParkQ2269845K
0x23ProtectedAreaQ47397235K
0x24BuildingQ41176292K
0x25ChurchQ16970286K
0x26SchoolQ9842242K
0x27HouseQ3947235K
0x28StructureQ811979216K
0x29SportsVenueQ1076486145K
0x2ACastleQ2341342K
0x2BBridgeQ1228038K
0x2COrganizationQ43229531K
0x2DBusinessQ4830453242K
0x2EPoliticalPartyQ727835K
0x2FSportsTeamQ84701795K
0x30PaintingQ33052131.1M
0x31DocumentQ4984845M
0x32LiteraryWorkQ7725634395K
0x33FilmQ11424335K
0x34AlbumQ482994303K
0x35MusicalWorkQ105543609195K
0x36TVEpisodeQ21191270177K
0x37VideoGameQ7889172K
0x38TVSeriesQ539842685K
0x39PatentQ43305660289K
0x3ASoftwareQ739713K
0x3BWebsiteQ3512712K
0x3CSportsSeasonQ27020041183K
0x3DEventQ165668210K
0x3EElectionQ4023111K
0x3FOther-확장용

Attributes (48비트)

EntityType마다 다른 의미로 해석되는 타입별 가변 스키마이다. 고빈도 속성에 더 많은 비트를 할당하며, WMS SIMD 필터링에 직접 활용한다.

Human (0x00) Attributes

┌──────────┬────────┬────────┬──────┬────────┬────────┬─────────┬──────────┬────────────┬──────────┐
│ 소분류   │ 직업   │ 국적   │ 시대 │ 10년대 │ 성별   │ 저명도  │ 언어     │ 출생지역   │ 활동분야 │
│  5bit    │  6bit  │  8bit  │ 4bit │  4bit  │  2bit  │  3bit   │  6bit    │   6bit     │   4bit   │
└──────────┴────────┴────────┴──────┴────────┴────────┴─────────┴──────────┴────────────┴──────────┘
offset:  0        5       11      19     23      27      29        32         38          44

Star (0x0C) Attributes

┌────────────┬────────────┬──────────┬──────────┬────────┬────────┬──────────┬──────────┬────────┬────────┐
│ 별자리     │ 분광형     │ 광도등급 │ 겉보기   │ 적경   │ 적위   │ 플래그   │ 시선속도 │ 적색편이│ 시차   │
│   7bit     │    4bit    │   3bit   │  4bit    │  4bit  │  4bit  │   6bit   │   5bit   │  5bit  │  4bit  │
└────────────┴────────────┴──────────┴──────────┴────────┴────────┴──────────┴──────────┴────────┴────────┘

플래그 비트 정의:

  • bit0: IR (적외선원)
  • bit1: Radio (전파원)
  • bit2: X-ray (X선원)
  • bit3: Binary (쌍성)
  • bit4: Variable (변광성)
  • bit5: HighPM (고유운동)

연산

Entity 생성

def make_entity(
    mode: int,           # 3비트
    entity_type: int,    # 6비트
    attrs: int           # 48비트
) -> bytes:
    PREFIX = 0b0001001   # 7비트 (Entity Node)

    word1 = (PREFIX << 9) | (mode << 6) | entity_type
    word2 = (attrs >> 32) & 0xFFFF
    word3 = (attrs >> 16) & 0xFFFF
    word4 = attrs & 0xFFFF

    return (
        word1.to_bytes(2, 'big') +
        word2.to_bytes(2, 'big') +
        word3.to_bytes(2, 'big') +
        word4.to_bytes(2, 'big')
    )

Entity 파싱

def parse_entity(data: bytes) -> dict:
    word1 = int.from_bytes(data[0:2], 'big')
    word2 = int.from_bytes(data[2:4], 'big')
    word3 = int.from_bytes(data[4:6], 'big')
    word4 = int.from_bytes(data[6:8], 'big')

    prefix = (word1 >> 9) & 0x7F
    mode = (word1 >> 6) & 0x7
    entity_type = word1 & 0x3F
    attrs = (word2 << 32) | (word3 << 16) | word4

    return {
        'prefix': prefix,
        'mode': mode,
        'entity_type': entity_type,
        'attrs': attrs
    }

예시

등록 개체: 이순신

# 이순신 (Q211789)
yi_sun_sin = make_entity(
    mode=0,              # 등록 개체
    entity_type=0x00,    # Human
    attrs=(
        (0x06 << 43) |   # 소분류: Military
        (0x01 << 37) |   # 직업: Admiral
        (0x52 << 29) |   # 국적: Korea
        (0x5 << 25) |    # 시대: Early Modern
        (0x0 << 21) |    # 10년대: 1540s
        (0x01 << 19) |   # 성별: Male
        (0x7 << 16)      # 저명도: 1000+
    )
)
# Q아이디 연결: Triple(yi_sun_sin_SIDX, P-외부ID, "Q211789")

추상: “모든 한국 남자”

all_korean_men = make_entity(
    mode=4,              # 전칭 (모든)
    entity_type=0x00,    # Human
    attrs=(
        (0x52 << 29) |   # 국적: Korea
        (0x01 << 19)     # 성별: Male
    )
)

하위 타입 매핑

위키데이터의 많은 타입이 64개 EntityType의 하위 타입이다. 인코더는 P31 값을 보고 적절한 상위 타입으로 라우팅한다.

하위 타입 (P31)상위 타입개체수
Q13442814 (scholarly article)Document (0x31)45.2M
Q67206691 (infrared source)Star (0x0C)2.6M
Q13100073 (village of China)Village (0x1D)592K

커버리지

항목수치
위키데이터 전체 개체117,419,925
Wikimedia 내부 (제외)8,565,353 (7.3%)
SIDX 대상108,854,572 (92.7%)
64개 타입 직접 커버36,295,074 (33.3%)
하위 타입 흡수71,842,429 (66.0%)
Other 폴백717,069 (0.7%)
최종 커버리지100%
충돌률< 0.01%

Q아이디 연결

Entity Node는 Q아이디를 내재하지 않고, 트리플 엣지로 별도 연결한다.

Subject:  Entity_SIDX (64비트)
Property: P-외부ID (예: P-Wikidata)
Object:   "Q12345" (문자열 또는 정수)