# Feature: Descriptor Computation

## Description
Compute global location descriptors using DINOv2 + VLAD aggregation. Supports both single-image descriptors and aggregate chunk descriptors for robust matching. DINOv2 features are semantic and invariant to season/texture changes, critical for UAV-to-satellite domain gap.

## Component APIs Implemented
- `compute_location_descriptor(image: np.ndarray) -> np.ndarray`
- `compute_chunk_descriptor(chunk_images: List[np.ndarray]) -> np.ndarray`

## External Tools and Services
- **F16 Model Manager**: Provides DINOv2 inference engine via `get_inference_engine("DINOv2")`
- **DINOv2**: Meta's foundation vision model for semantic feature extraction
- **numpy**: Array operations and L2 normalization

## Internal Methods

### `_preprocess_image(image: np.ndarray) -> np.ndarray`
Resizes and normalizes image for DINOv2 input (typically 224x224 or 518x518).

### `_extract_dense_features(preprocessed: np.ndarray) -> np.ndarray`
Runs DINOv2 inference, extracts dense feature map from multiple spatial locations.

### `_vlad_aggregate(dense_features: np.ndarray, codebook: np.ndarray) -> np.ndarray`
Applies VLAD (Vector of Locally Aggregated Descriptors) aggregation using pre-trained cluster centers.

### `_l2_normalize(descriptor: np.ndarray) -> np.ndarray`
L2-normalizes descriptor vector for cosine similarity search.

### `_aggregate_chunk_descriptors(descriptors: List[np.ndarray], strategy: str) -> np.ndarray`
Aggregates multiple descriptors into one using strategy: "mean" (default), "vlad", or "max".

## Unit Tests

### compute_location_descriptor

#### Test: Output Dimensions
- Input: UAV image (any resolution)
- Verify: Returns 4096-dim or 8192-dim vector

#### Test: Normalization
- Input: Any valid image
- Verify: Output L2 norm equals 1.0

#### Test: Deterministic Output
- Input: Same image twice
- Verify: Identical descriptors (no randomness)

#### Test: Season Invariance
- Input: Two images of same location, different seasons
- Verify: Cosine similarity > 0.7

#### Test: Location Discrimination
- Input: Two images of different locations
- Verify: Cosine similarity < 0.5

#### Test: Domain Invariance
- Input: UAV image and satellite image of same location
- Verify: Cosine similarity > 0.6 (cross-domain)

### compute_chunk_descriptor

#### Test: Empty Chunk
- Input: Empty list
- Verify: Raises ValueError

#### Test: Single Image Chunk
- Input: List with one image
- Verify: Equivalent to compute_location_descriptor

#### Test: Multiple Images Mean Aggregation
- Input: 5 images from chunk
- Verify: Descriptor is mean of individual descriptors

#### Test: Aggregated Normalization
- Input: Any chunk
- Verify: Output L2 norm equals 1.0

#### Test: Chunk More Robust Than Single
- Input: Featureless terrain chunk (10 images)
- Verify: Chunk descriptor has lower variance than individual descriptors

## Integration Tests

### Test: Model Manager Integration
- Verify: Successfully retrieves DINOv2 from F16 Model Manager
- Verify: Model loaded with correct TensorRT/ONNX backend

### Test: Performance Budget
- Input: FullHD image
- Verify: Single descriptor computed in ~150ms

### Test: Chunk Performance
- Input: 10 images
- Verify: Chunk descriptor in <2s (parallelizable)

