개요
3. 종합 요약 – det_head 관점에서 Sparse4DHead
- det_head로서의 Sparse4DHead는
- InstanceBank를 통한 후보 생성,
- 고차원 임베딩(Anchor Encoder),
- 다단계 정제(Transformer 모듈 및 Refine Layer),
- GT 매칭(Sampler),
- 그리고 후처리(Decoder)를 통해,
- 최종적으로 3D 객체 검출 결과를 산출하는 역할을 수행
입력/출력 요약:
- 입력:
- Feature Maps: List[Tensor] with shape [B, N, C, H, W]
- 메타 정보: projection matrix, GT 박스, GT 레이블 등
- 출력 (det_head 결과):
- Classification: [B, 900, 10]
- Regression (Prediction): [B, 900, output_dim]
- instance_feature, anchor_embed: [B, 900, 256]
- 최종 Decoder 결과:
- List[dict] with keys "boxes_3d", "scores_3d", "labels_3d" (각 이미지에 대해 top-k 결과, 예: 300개)
전체 흐름:
1. InstanceBank (900 anchors):
- 입력: GT와 메타 정보, 외부에서 로드된 초기 anchor (900개)
- 출력: instance_feature [B, 900, 256] 및 anchor [B, 900, D]
-
Anchor Encoder (SparseBox3DEncoder):
- 입력: 원시 anchor, Shape [B, 900, D]
- 출력: anchor_embed, Shape [B, 900, embed_dims] (예: [B, 900, 256])
-
Transformer 기반 정제 (operation_order):
- 여러 모듈("gnn", "norm", "deformable", "ffn", "refine" 등)을 순차적으로 적용하여,
- instance_feature와 anchor_embed가 업데이트됨. 최종 “refine” 단계에서, refine_layer (SparseBox3DRefinementModule)가
- Classification: [B, 900, num_classes (예: 10)]
- Regression: [B, 900, output_dim (예: 11 또는 설정에 따라)]
를 산출함.
-
Sampler (SparseBox3DTarget):
- 예측과 GT 간의 비용(cost) 기반 할당을 수행하여, 학습 시 필요한 target 값을 생성함.
-
Decoder (SparseBox3DDecoder):
- 학습 혹은 추론 후, 예측 결과를 후처리하여 최종
3D bounding box, 점수, 클래스 등의 정보를 포함하는 결과를 반환함.
1. 전체 구조 개요 – Sparse4DHead (det_head)
Sparse4DHead는 3D 객체 검출 파이프라인의 최종 예측 헤드로서,
- 인스턴스 후보 생성:
- InstanceBank를 통해 이미지에서 후보 객체(인스턴스)의 초기 특징과 초기 앵커 정보를 생성합니다.
- 후속 정제 및 임베딩:
- Anchor Encoder를 통해 초기 앵커(예: k-means로 생성된 3D 박스 후보)를 고차원 표현으로 변환하고,
- Transformer 또는 Graph 기반 모듈(여러 operation_order 내 "gnn", "norm", "deformable", "ffn" 등)을 사용해 인스턴스 특징과 앵커 임베딩을 정제합니다.
- 최종 예측 (Refinement):
- Refine Layer를 통해 각 후보에 대한 분류(클래스 점수)와 회귀(3D 박스 좌표 등) 값을 산출합니다.
- 후처리:
- Sampler를 통해 GT와의 매칭을 수행하고, 최종 손실 계산에 필요한 target을 생성하며,
- Decoder를 통해 후처리(decode)하여 최종 3D bounding box 등 실제 출력 결과로 변환합니다.
2. 세부 구성 요소 및 역할, 입력/출력 명세
(1) InstanceBank (with anchor_handler)
역할 및 특징:
- 목적:
InstanceBank는 이미지에서 후보 객체를 미리 정의된 anchor 집합(여기서는 900개) 기반으로 생성하고, 각 후보에 대해 초기 특징(instance_feature)와 원시 앵커(anchor)를 제공합니다.
- anchor_handler:
- 여기서는 "SparseBox3DKeyPointsGenerator"가 anchor_handler로 지정되어 있습니다.
- 이 모듈은 원시 anchor에 대해 추가적인 위치 보정이나 키포인트를 생성하여, 3D 박스 후보의 기하학적 정보를 보강합니다.
입력/출력:
- 입력:
- 배치 크기 B (예: B) 및 메타 정보(metas: 포함하는 타임스탬프, projection matrix 등).
- 초기 anchor 데이터는 외부 파일
"data/kmeans/kmeans_det_900.npy"에서 로드되며, 보통 NumPy 배열로 제공됨.
- 출력:
- instance_feature: Shape → [B, 900, embed_dims]
(예: [B, 900, 256])
- anchor: 원시 anchor 값, 초기 shape는 [B, 900, D] (D는 원래 anchor 차원, 예를 들어 8~10 차원)
이후, 이 값은 anchor_encoder에서 고차원 임베딩되어 [B, 900, embed_dims]로 사용됨.
(2) Anchor Encoder (SparseBox3DEncoder)
역할 및 특징:
- 목적:
- 원시 anchor 정보를 3D 박스의 기하학적 속성(위치, 크기, 방향, 속도 등)을 반영하여 고차원 feature로 변환합니다.
- 설정:
vel_dims=3와 embed_dims=[128, 32, 32, 64] (decouple_attn 사용 시 "cat" 방식) 또는 단일 값 256 (decouple_attn 미사용)으로 구성됩니다.
- "cat" 모드인 경우, 각 속성별 임베딩 결과를 concatenate 하여 풍부한 정보를 보존합니다.
입력/출력:
- 입력:
- 원시 anchor, Shape: [B, 900, D]
- D는 3D 박스의 기본 정보 차원 (예: [X, Y, Z, log(W), log(L), log(H), SIN_YAW, COS_YAW, ...])
- 출력:
- anchor_embed: Shape → [B, 900, embed_dims]
(예: [B, 900, 256])
- 이 임베딩된 정보는 후속 transformer 모듈에서 query_pos 등으로 사용되어, 인스턴스 간의 관계를 학습하는 데 활용됩니다.
(3) Refine Layer (SparseBox3DRefinementModule)
역할 및 특징:
- 목적:
- 후보 인스턴스의 최종 예측 단계로, 정제된 instance_feature와 anchor_embed를 결합하여 최종 회귀 및 분류 예측을 수행합니다.
- 회귀(branch)는 3D 박스의 위치, 크기, 방향 (refine_yaw=True이면 yaw 관련 정보 포함) 등을 출력하며, 분류(branch)는 각 후보 객체에 대한 클래스 확률을 출력합니다.
- 설정:
num_cls=num_classes (여기서 num_classes는 10, 예: car, truck, 등)
with_quality_estimation 옵션에 따라 품질 점수도 예측할 수 있습니다.
입력/출력:
- 입력:
- 정제 이전의 instance_feature와 anchor_embed (각각 [B, 900, embed_dims])
- 추가적으로, 시간 간격(time_interval) 등(옵션)도 입력될 수 있음.
- 출력:
- Regression 결과:
- Shape: [B, 900, output_dim]
- output_dim은 보통 11 혹은 설정에 따라 달라지며, 보통 [X, Y, Z, exp(W), exp(L), exp(H), refined SIN_YAW, refined COS_YAW, …] 등으로 구성됨.
- Classification 결과:
- Shape: [B, 900, num_classes]
(예: [B, 900, 10])
- (옵션) Quality Score:
- 추가적으로 예측되는 경우, Shape: [B, 900, ?] (보통 2차원 등)
(4) Sampler (SparseBox3DTarget)
역할 및 특징:
- 목적:
- 예측된 후보와 GT 간의 매칭(cost 할당)을 수행하여, 손실 계산을 위한 target (분류, 회귀 타겟)을 생성합니다.
- 또한, denoising 학습을 위한 noisy instance 생성 및 부정적(noisy) anchor 처리를 수행합니다.
- 설정:
- 다양한 hyperparameter (dn_noise_scale, max_dn_gt, reg_weights, cls_weight 등)가 설정되어, 각 항목의 상대적 비용을 조절합니다.
입력/출력:
- 입력:
- cls_pred: 후보 객체에 대한 예측 분류 점수, Shape: [B, num_pred, num_cls]
(여기서 num_pred ≈ 900, num_cls = 10)
- box_pred: 후보 객체에 대한 회귀 예측 값, Shape: [B, num_pred, output_dim]
- cls_target, box_target: Ground Truth 정보, 각각 적절한 shape (보통 각 이미지의 GT 수가 다르므로 list 형태로 관리)
- 출력:
- output_cls_target: 최종 분류 target, Shape: [B, num_pred] (각 원소는 GT 클래스 인덱스, 없는 경우 기본값)
- output_box_target: 최종 회귀 target, Shape: [B, num_pred, output_dim]
- output_reg_weights: 회귀 가중치, Shape: [B, num_pred, output_dim]
(5) Decoder (SparseBox3DDecoder)
역할 및 특징:
- 목적:
- 학습 혹은 추론 후, Sparse4DHead의 예측 결과(분류, 회귀)를 실제 3D 박스 좌표로 변환합니다.
- 후처리 단계에서, 후보 중 top-k (설정에 따라 num_output, 예: 300개)를 선택하고, score threshold에 따라 필터링합니다.
- 변환:
- 회귀 예측 값은 로그 스케일로 예측된 크기(exp 처리)와, sin/cos 값으로 예측된 방향을 이용해 실제 3D 박스로 복원됩니다.
decode_box() 함수를 통해, sin/cos 값에서 atan2를 적용하여 yaw(회전 각도)를 복원한 후, 최종 박스 벡터로 결합합니다.
입력/출력:
- 입력:
- cls_scores: 분류 예측, List 또는 Tensor 형태, 최종적으로 [B, num_pred, num_cls]에서 추출됨
- box_preds: 회귀 예측, List 또는 Tensor 형태, 최종적으로 [B, num_pred, output_dim]
- (옵션) instance_id, quality: 추가 정보 (추후 후처리에 사용)
- 출력:
- List[dict] 각 dict에는:
"boxes_3d": 최종 3D 박스 좌표 (Tensor, Shape: [num_output, D_final], D_final는 실제 박스 출력 차원)
"scores_3d": 예측 신뢰도 (Tensor, Shape: [num_output, 1])
"labels_3d": 예측 클래스 인덱스 (Tensor, Shape: [num_output, 1])
- (옵션)
"instance_ids" 및 "cls_scores" 등
부록
instance_feature / anchor_embed
요약
-
instance_feature:
- 역할:
후보 인스턴스의 appearance 및 semantic 정보를 내포하는 feature vector
- Shape: [B, num_instances, embed_dims] (예: (B, 900, 256))
-
anchor_embed:
- 역할:
초기 앵커(3D 박스 후보) 정보를 기하학적, 위치 정보를 반영하는 고차원 feature로 임베딩한 값
- Shape: [B, num_instances, embed_dims] (예: (B, 900, 256))
(
instance_feature,
anchor,
temp_instance_feature,
temp_anchor,
time_interval,
) = self.instance_bank.get(
batch_size, metas, dn_metas=self.sampler.dn_metas
)
anchor_embed = self.anchor_encoder(anchor)
for i, op in enumerate(self.operation_order):
if self.layers[i] is None:
continue
elif op == "temp_gnn":
instance_feature = self.graph_model(
i,
instance_feature,
temp_instance_feature,
temp_instance_feature,
query_pos=anchor_embed,
key_pos=temp_anchor_embed,
attn_mask=attn_mask
if temp_instance_feature is None
else None,
)
1. instance_feature
-
개념:
- instance_feature는 인스턴스 뱅크(instance_bank)가 생성한
각 후보 인스턴스(후보 객체)에 대한 특징 벡터
- 이 특징 벡터는 이미지 백본과 넥에서 추출한 다중 스케일 feature maps를 기반으로, 각 후보 객체의 지역적 및 전역적 정보를 집약하여 표현
- 즉, instance_feature는 후보 인스턴스의 appearance, context, semantic 정보 등을 내포하며, 후속 transformer 연산(예: graph 모델, ffn, norm 등)을 통해 정제되고 강화
-
생성 위치:
- Sparse4DHead의 forward 메서드에서,
(instance_feature, anchor, temp_instance_feature, temp_anchor, time_interval) = self.instance_bank.get(...)
호출을 통해 인스턴스 뱅크로부터 생성됩니다.
- 이후 이 feature들은 transformer 모듈을 거치면서, 인스턴스의 위치와 상태를 정제하는 데 사용됩니다.
-
Shape:
- 일반적으로 instance_feature의 shape는
[B, num_instances, C]
여기서
- B: 배치 크기
- num_instances: 인스턴스 뱅크에서 생성된 후보 객체의 수 (예: 900 등, 설정에 따라 다름)
- C: 임베딩 차원, 보통 설정 파일에서 정의한 embed_dims (예: 256)
- 예를 들어, 배치 크기가 B이고 후보 인스턴스 수가 900, embed_dims가 256이면, instance_feature의 shape는 (B, 900, 256)가 됩니다.
2. anchor_embed
-
개념:
- anchor_embed는
- 각 후보 인스턴스의 초기 앵커(예측 박스 후보) 정보를,
- anchor_encoder라는 POSITIONAL_ENCODING 모듈을 통해 임베딩한 결과
- 이 임베딩은 3D 박스의 위치, 크기, 방향 등의 기하학적 정보를 효과적으로 표현할 수 있도록 설계되어 있습니다.
- 즉, anchor_embed는 단순한 좌표 값(anchor)을 더 높은 차원의 feature로 변환하여, 인스턴스 특징과 결합(예를 들어, attention 연산을 수행할 때)하여, 더욱 정밀한 객체 표현을 만드는 데 도움을 줍니다.
-
생성 위치:
-
Shape:
- 원래 anchor의 shape는 일반적으로 [B, num_instances, D] (D는 원래의 앵커 정보 차원)인데,
- anchor_encoder를 통과한 후 anchor_embed의 shape는
[B, num_instances, embed_dims]
로 맞춰집니다. (설정 파일에서 embed_dims가 예를 들어 256으로 정의되어 있다면, anchor_embed의 마지막 차원은 256입니다.)
- 예를 들어, 배치 크기 B, 후보 인스턴스 수가 900, embed_dims가 256이면, anchor_embed의 shape는 (B, 900, 256)가 됩니다.
3. 결합 및 활용