GPU indices¶
Present only when the extension was built with GPU support, which is the default. See GPU for the three things that differ from the CPU estimators.
gpu
¶
GPU estimators, present only when the extension was built with them.
ann_search.gpu_available() is the check worth making: it says whether this
machine has an adapter, which is the part that varies. The ordinary wheel has
GPU support compiled in, so importing this module only fails on a build made
with --no-default-features.
Three things differ from the CPU estimators, all of them consequences of the backend rather than choices:
- float32 only. WGSL has no float64, so
fitcasts rather than letting a float64 array fail somewhere inside a kernel. That is a narrowing conversion, and the only one this package performs silently. - No persistence. These indices hold device buffers and sit outside the
crate's
serialisefeature, sosave,loadandpickleraise. Rebuild. - Manhattan is unavailable on all three.
ExhaustiveGpuIndex
¶
Bases: _BaseGpuIndex
Brute-force exact search on the device.
Recall is 1 by construction, and on a dataset too large to score on the CPU this is the cheapest way to get ground truth. No build-time knobs: the data goes up, the norms get recorded, and that is the index.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
n_neighbors
|
int
|
Neighbours per query, and the default |
15
|
metric
|
str
|
|
'euclidean'
|
verbose
|
bool
|
Progress to the process stdout, not |
False
|
IvfGpuIndex
¶
IvfGpuIndex(
n_neighbors: int = 15,
metric: str = "euclidean",
nlist: int | None = None,
nprobe: int | None = None,
nquery: int | None = None,
kmeans_iters: int | None = None,
kmeans_balanced: bool = False,
quantise_to_f16: bool = False,
seed: int = 42,
verbose: bool = False,
)
Bases: _BaseGpuIndex
Inverted file with k-means and the vectors both on the device.
Trains and queries without a readback, which is what makes it quick, and
also what bounds it: the reordered vectors stay resident, so the dataset has
to fit in device memory. nquery caps how many queries stage per batch if
the upload is what does not fit.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
n_neighbors
|
int
|
Neighbours per query, and the default |
15
|
metric
|
str
|
|
'euclidean'
|
nlist
|
int | None
|
Number of Voronoi cells to cut the space into. |
None
|
nprobe
|
int | None
|
Cells visited per query, the recall knob. |
None
|
nquery
|
int | None
|
Queries staged on the device per batch. |
None
|
kmeans_iters
|
int | None
|
Lloyd iterations when training the cells. |
None
|
kmeans_balanced
|
bool
|
Reseed starved centroids each iteration, RAFT-style. Evens out the posting lists, which matters more here than on the CPU because a straggler cell serialises its whole workgroup. |
False
|
quantise_to_f16
|
bool
|
Hold the resident data buffer at fp16. Halves its
memory and lifts effective bandwidth on the assignment kernels, at
the cost of needing |
False
|
seed
|
int
|
Fixes k-means initialisation. |
42
|
verbose
|
bool
|
Progress to the process stdout, not |
False
|
CagraGpuIndex
¶
CagraGpuIndex(
n_neighbors: int = 15,
metric: str = "euclidean",
graph_degree: int | None = None,
build_k: int | None = None,
max_iters: int | None = None,
n_trees: int | None = None,
delta: float | None = None,
rho: float | None = None,
refine_knn: int | None = None,
retain_gpu: bool = True,
beam_width: int | None = None,
max_beam_iters: int | None = None,
n_entry_points: int | None = None,
expand_per_iter: int | None = None,
seed: int = 42,
verbose: bool = False,
)
Bases: ExtractKnnMixin, _BaseGpuIndex
CAGRA graph: NN-Descent on the device, pruned, then beam-searched.
The fastest route to a kNN graph here when a GPU is present. beam_width is
the recall knob; leaving it None sizes the beam as 2 * max(k, 16),
which is usually the right answer.
extract_knn hands back the kNN graph the descent converged on, taken
before the CAGRA prune. No kernel runs, and it is capped by graph_degree
rather than by the beam.
Unlike every other index in this package, a fitted handle is not safe to
query from two threads at once: the beam search memoises its upload of the
navigational graph behind a mutable borrow, so concurrent calls serialise.
extract_knn is exempt.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
n_neighbors
|
int
|
Neighbours per query, and the default |
15
|
metric
|
str
|
|
'euclidean'
|
graph_degree
|
int | None
|
Neighbours stored per node in the final graph. |
None
|
build_k
|
int | None
|
Working degree the descent keeps before pruning. |
None
|
max_iters
|
int | None
|
Descent iteration cap. |
None
|
n_trees
|
int | None
|
Random projection trees used to seed the initial graph.
|
None
|
delta
|
float | None
|
Convergence threshold. Descent stops once the fraction of
updated edges falls below it. |
None
|
rho
|
float | None
|
Local-join sampling rate. |
None
|
refine_knn
|
int | None
|
Two-hop refinement sweeps after the main loop. |
None
|
retain_gpu
|
bool
|
Upload the navigational graph at build time rather than on the first query. On by default, because the first query would otherwise pay for it. |
True
|
beam_width
|
int | None
|
Beam width at query time, the recall knob. Search-time. |
None
|
max_beam_iters
|
int | None
|
Iteration cap on the beam search. Search-time. |
None
|
n_entry_points
|
int | None
|
Entry points into the graph per query. Search-time. |
None
|
expand_per_iter
|
int | None
|
Extra neighbours explored per beam iteration, usually 1 to 4. Search-time. |
None
|
seed
|
int
|
Fixes the seed graph and the sampling. |
42
|
verbose
|
bool
|
Progress to the process stdout, not |
False
|
Note
The four beam parameters are all-or-nothing. Leave every one of them
None and the beam is sized from k: beam_width =
2 * max(k, 16) and max_beam_iters = 3 * beam_width, with 8 entry
points and 3 expansions per iteration. Set any one of them and that
scaling is off for all four, and the ones still None fall back to
flat constants: beam_width = 16, max_beam_iters = 48,
n_entry_points = 8, expand_per_iter = 3. So asking for
n_entry_points=16 alone on a k=50 query quietly narrows the beam
from 100 to 16. If you touch one, set beam_width too.