动态批处理#
动态批处理允许将小的搜索请求分组为批次,以增加设备占用率和吞吐量,同时将延迟保持在限制范围内。
#include
命名空间 cuvs::neighbors::dynamic_batching
索引构建参数#
-
struct index_params : public cuvs::neighbors::index_params#
- #include <dynamic_batching.hpp>
公共成员
-
int64_t k#
在构建时,搜索的邻居数量是固定的。
-
int64_t max_batch_size = 100#
提交给上游索引的批次的最大大小。
-
size_t n_queues = 3#
独立请求队列的数量。
每个队列都与一个唯一的CUDA流和IO设备缓冲区相关联。如果并发请求的数量很高,使用多个队列可以在其他队列忙碌时填充数据并准备批次。此外,队列是并发提交的;这可以通过隐藏内核启动延迟来更好地利用GPU,从而有助于提高吞吐量。
-
bool conservative_dispatch = false#
默认情况下(
conservative_dispatch = false),第一个将查询提交到批处理的CPU线程会尽快(在批处理未满之前)调度上游搜索函数。在这种情况下,它在调用上游搜索时不知道最终的批处理大小,因此每次都以最大批处理大小运行上游搜索,即使批处理中只有一个有效查询。这减少了延迟,但以浪费GPU资源为代价。替代行为(
conservative_dispatch = true)更为保守:调度线程启动收集输入查询的内核,但等待直到批次填满或等待时间超过。只有在那时,它才会获取实际的批次大小并启动上游搜索。因此,以暴露上游搜索延迟为代价,减少了GPU资源的浪费。经验法则: 对于较大的
max_batch_size,设置conservative_dispatch = true,否则保持禁用状态。
-
int64_t k#
索引搜索参数#
索引#
-
template<typename T, typename IdxT>
struct index : public cuvs::neighbors::index# - #include <dynamic_batching.hpp>
轻量级动态批处理索引包装器。
一个轻量级的动态批处理索引管理一个单一的索引和一个单一的搜索参数集。这个结构应该通过复制语义在多个用户之间共享:对底层实现的访问是通过共享指针管理的,参与者之间的并发搜索是线程安全的。
使用示例
using namespace cuvs::neighbors; // When creating a dynamic batching index, k parameter has to be passed explicitly. // The first empty braces default-initialize the parent `neighbors::index_params` (unused). dynamic_batching::index_params dynb_index_params{{}, k}; // Construct the index by wrapping the upstream index and search parameters. dynamic_batching::index<float, uint32_t> index{ res, dynb_index_params, upstream_index, upstream_search_params }; // Use default search parameters dynamic_batching::search_params search_params; // Search K nearest neighbours auto neighbors = raft::make_device_matrix<uint32_t>(res, n_queries, k); auto distances = raft::make_device_matrix<float>(res, n_queries, k); dynamic_batching::search( res, search_params, index, queries, neighbors.view(), distances.view() );
优先队列
动态批处理索引对优先处理个别请求的支持有限。批处理器中只有一个队列池,并且没有功能可以优先处理一个批次而不是另一个批次。每个请求中传递的
search_params::dispatch_timeout_ms参数在内部聚合,并且批次在任何超时时间之前都会被分发。在这种逻辑下,高优先级请求永远不能比之前提交的低优先级请求更早处理。然而,动态批处理索引是轻量级的,不包含任何全局或静态状态。这意味着很容易组合多个批处理器。例如,您可以为每个优先级类构建一个批处理索引:
using namespace cuvs::neighbors; // Large batch size (128), couple queues (2), // enabled conservative dispatch - all for better throughput dynamic_batching::index_params low_priority_params{{}, k, 128, 2, true}; // Small batch size (16), more queues (4), // disabled conservative dispatch - to minimize latency with reasonable throughput dynamic_batching::index_params high_priority_params{{}, k, 16, 4, false}; // Construct the indexes by wrapping the upstream index and search parameters. dynamic_batching::index<float, uint32_t> low_priority_index{ res, low_priority_params, upstream_index, upstream_search_params }; dynamic_batching::index<float, uint32_t> high_priority_index{ res, high_priority_params, upstream_index, upstream_search_params }; // Define a combined search function with priority selection double high_priority_threshold_ms = 0.1; auto search_function = [low_priority_index, high_priority_index, high_priority_threshold_ms]( raft::resources const &res, dynamic_batching::search_params search_params, raft::device_matrix_view<const float, int64_t> queries, raft::device_matrix_view<uint32_t, int64_t> neighbors, raft::device_matrix_view<float, int64_t> distances) { dynamic_batching::search( res, search_params, search_params.dispatch_timeout_ms < high_priority_threshold_ms ? high_priority_index : low_priority_index, queries, neighbors, distances ); };
- Template Parameters:
T – 数据类型
IdxT – 索引类型
公共函数
-
template<typename Upstream>
index(const raft::resources &res, const cuvs::neighbors::dynamic_batching::index_params ¶ms, const Upstream &upstream_index, const typename Upstream::search_params_type &upstream_params, const cuvs::neighbors::filtering::base_filter *sample_filter = nullptr)# 通过包装上游索引来构建动态批处理索引。
- Template Parameters:
上游 – 上游索引类型
- Parameters:
res – [in] raft资源
params – [in] 动态批处理参数
upstream_index – [in] 执行搜索的原始索引(在动态批处理索引的生命周期内,引用必须保持有效)
upstream_params – [in] 批处理中所有查询的原始索引搜索参数(这些参数在动态批处理索引的生命周期内按值捕获)
sample_filter – [in] 过滤函数,如果有的话,必须对批次中的所有请求相同(指针在动态批处理索引的生命周期内必须保持有效)
索引搜索#
-
void search(raft::resources const &res, cuvs::neighbors::dynamic_batching::search_params const ¶ms, dynamic_batching::index<float, uint32_t> const &index, raft::device_matrix_view<const float, int64_t, raft::row_major> queries, raft::device_matrix_view<uint32_t, int64_t, raft::row_major> neighbors, raft::device_matrix_view<float, int64_t, raft::row_major> distances)#
使用动态批处理索引搜索ANN。
上游索引的搜索参数和可选的过滤函数在动态批处理索引构建时配置。
与许多其他索引一样,动态批处理搜索具有流顺序语义:主机函数可能在结果准备好之前返回控制权。与给定资源对象中的主CUDA流同步,以等待搜索结果的到达。
动态批处理搜索是线程安全的:在多个线程中使用相同索引的副本调用搜索函数,以增加批处理的占用率。
- Parameters:
res – [输入]
params – [in] 查询特定的批处理参数,例如最大等待时间
index – [in] 一个动态批处理索引
queries – [in] 一个设备矩阵视图,指向一个行优先矩阵 [n_queries, dim]
neighbors – [out] 一个设备矩阵视图,指向源数据集中邻居的索引 [n_queries, k]
distances – [out] 一个设备矩阵视图,用于存储到所选邻居的距离 [n_queries, k]
-
void search(raft::resources const &res, cuvs::neighbors::dynamic_batching::search_params const ¶ms, dynamic_batching::index<half, uint32_t> const &index, raft::device_matrix_view<const half, int64_t, raft::row_major> queries, raft::device_matrix_view<uint32_t, int64_t, raft::row_major> neighbors, raft::device_matrix_view<float, int64_t, raft::row_major> distances)#
使用动态批处理索引搜索ANN。
上游索引的搜索参数和可选的过滤函数在动态批处理索引构建时配置。
与许多其他索引一样,动态批处理搜索具有流顺序语义:主机函数可能在结果准备好之前返回控制权。与给定资源对象中的主CUDA流同步,以等待搜索结果的到达。
动态批处理搜索是线程安全的:在多个线程中使用相同索引的副本调用搜索函数,以增加批处理的占用率。
- Parameters:
res – [输入]
params – [in] 查询特定的批处理参数,例如最大等待时间
index – [in] a dynamic batching index
queries – [in] a device matrix view to a row-major matrix [n_queries, dim]
neighbors – [out] 一个设备矩阵视图,指向源数据集中邻居的索引 [n_queries, k]
distances – [out] a device matrix view to the distances to the selected neighbors [n_queries, k]
-
void search(raft::resources const &res, cuvs::neighbors::dynamic_batching::search_params const ¶ms, dynamic_batching::index<int8_t, uint32_t> const &index, raft::device_matrix_view<const int8_t, int64_t, raft::row_major> queries, raft::device_matrix_view<uint32_t, int64_t, raft::row_major> neighbors, raft::device_matrix_view<float, int64_t, raft::row_major> distances)#
使用动态批处理索引搜索ANN。
上游索引的搜索参数和可选的过滤函数在动态批处理索引构建时配置。
与许多其他索引一样,动态批处理搜索具有流顺序语义:主机函数可能在结果准备好之前返回控制权。与给定资源对象中的主CUDA流同步,以等待搜索结果的到达。
动态批处理搜索是线程安全的:在多个线程中使用相同索引的副本调用搜索函数,以增加批处理的占用率。
- Parameters:
res – [输入]
params – [in] 查询特定的批处理参数,例如最大等待时间
index – [in] 一个动态批处理索引
queries – [in] 一个设备矩阵视图,指向一个行优先矩阵 [n_queries, dim]
neighbors – [out] 一个设备矩阵视图,指向源数据集中邻居的索引 [n_queries, k]
distances – [out] 一个设备矩阵视图,用于存储到选定邻居的距离 [n_queries, k]
-
void search(raft::resources const &res, cuvs::neighbors::dynamic_batching::search_params const ¶ms, dynamic_batching::index<uint8_t, uint32_t> const &index, raft::device_matrix_view<const uint8_t, int64_t, raft::row_major> queries, raft::device_matrix_view<uint32_t, int64_t, raft::row_major> neighbors, raft::device_matrix_view<float, int64_t, raft::row_major> distances)#
使用动态批处理索引搜索ANN。
上游索引的搜索参数和可选的过滤函数在动态批处理索引构建时配置。
与许多其他索引一样,动态批处理搜索具有流顺序语义:主机函数可能在结果准备好之前返回控制权。与给定资源对象中的主CUDA流同步,以等待搜索结果的到达。
动态批处理搜索是线程安全的:在多个线程中使用相同索引的副本调用搜索函数,以增加批处理的占用率。
- Parameters:
res – [输入]
params – [in] 查询特定的批处理参数,例如最大等待时间
index – [in] 一个动态批处理索引
queries – [in] 一个设备矩阵视图,指向一个行优先矩阵 [n_queries, dim]
neighbors – [out] 一个设备矩阵视图,指向源数据集中邻居的索引 [n_queries, k]
distances – [out] 一个设备矩阵视图,用于存储到选定邻居的距离 [n_queries, k]
-
void search(raft::resources const &res, cuvs::neighbors::dynamic_batching::search_params const ¶ms, dynamic_batching::index<float, int64_t> const &index, raft::device_matrix_view<const float, int64_t, raft::row_major> queries, raft::device_matrix_view<int64_t, int64_t, raft::row_major> neighbors, raft::device_matrix_view<float, int64_t, raft::row_major> distances)#
使用动态批处理索引搜索ANN。
上游索引的搜索参数和可选的过滤函数在动态批处理索引构建时配置。
与许多其他索引一样,动态批处理搜索具有流顺序语义:主机函数可能在结果准备好之前返回控制权。与给定资源对象中的主CUDA流同步,以等待搜索结果的到达。
动态批处理搜索是线程安全的:在多个线程中使用相同索引的副本调用搜索函数,以增加批处理的占用率。
- Parameters:
res – [输入]
params – [in] 查询特定的批处理参数,例如最大等待时间
index – [in] 一个动态批处理索引
queries – [in] 一个设备矩阵视图,指向一个行优先矩阵 [n_queries, dim]
neighbors – [out] 一个设备矩阵视图,指向源数据集中邻居的索引 [n_queries, k]
distances – [out] 一个设备矩阵视图,用于显示到选定邻居的距离 [n_queries, k]
-
void search(raft::resources const &res, cuvs::neighbors::dynamic_batching::search_params const ¶ms, dynamic_batching::index<half, int64_t> const &index, raft::device_matrix_view<const half, int64_t, raft::row_major> queries, raft::device_matrix_view<int64_t, int64_t, raft::row_major> neighbors, raft::device_matrix_view<float, int64_t, raft::row_major> distances)#
使用动态批处理索引搜索ANN。
上游索引的搜索参数和可选的过滤函数在动态批处理索引构建时配置。
与许多其他索引一样,动态批处理搜索具有流顺序语义:主机函数可能在结果准备好之前返回控制权。与给定资源对象中的主CUDA流同步,以等待搜索结果的到达。
动态批处理搜索是线程安全的:在多个线程中使用相同索引的副本调用搜索函数,以增加批处理的占用率。
- Parameters:
res – [输入]
params – [in] 查询特定的批处理参数,例如最大等待时间
index – [in] 一个动态批处理索引
queries – [in] 一个设备矩阵视图,指向一个行优先矩阵 [n_queries, dim]
neighbors – [out] 一个设备矩阵视图,指向源数据集中邻居的索引 [n_queries, k]
distances – [out] 一个设备矩阵视图,用于存储到选定邻居的距离 [n_queries, k]
-
void search(raft::resources const &res, cuvs::neighbors::dynamic_batching::search_params const ¶ms, dynamic_batching::index<int8_t, int64_t> const &index, raft::device_matrix_view<const int8_t, int64_t, raft::row_major> queries, raft::device_matrix_view<int64_t, int64_t, raft::row_major> neighbors, raft::device_matrix_view<float, int64_t, raft::row_major> distances)#
使用动态批处理索引搜索ANN。
上游索引的搜索参数和可选的过滤函数在动态批处理索引构建时配置。
与许多其他索引一样,动态批处理搜索具有流顺序语义:主机函数可能在结果准备好之前返回控制权。与给定资源对象中的主CUDA流同步,以等待搜索结果的到达。
动态批处理搜索是线程安全的:在多个线程中使用相同索引的副本调用搜索函数,以增加批处理的占用率。
- Parameters:
res – [输入]
params – [in] 查询特定的批处理参数,例如最大等待时间
index – [in] 一个动态批处理索引
queries – [in] 一个设备矩阵视图,指向一个行优先矩阵 [n_queries, dim]
neighbors – [out] 一个设备矩阵视图,指向源数据集中邻居的索引 [n_queries, k]
distances – [out] 一个设备矩阵视图,用于存储到选定邻居的距离 [n_queries, k]
-
void search(raft::resources const &res, cuvs::neighbors::dynamic_batching::search_params const ¶ms, dynamic_batching::index<uint8_t, int64_t> const &index, raft::device_matrix_view<const uint8_t, int64_t, raft::row_major> queries, raft::device_matrix_view<int64_t, int64_t, raft::row_major> neighbors, raft::device_matrix_view<float, int64_t, raft::row_major> distances)#
使用动态批处理索引搜索ANN。
上游索引的搜索参数和可选的过滤函数在动态批处理索引构建时配置。
与许多其他索引一样,动态批处理搜索具有流顺序语义:主机函数可能在结果准备好之前返回控制权。与给定资源对象中的主CUDA流同步,以等待搜索结果的到达。
动态批处理搜索是线程安全的:在多个线程中使用相同索引的副本调用搜索函数,以增加批处理的占用率。
- Parameters:
res – [输入]
params – [in] 查询特定的批处理参数,例如最大等待时间
index – [in] 一个动态批处理索引
queries – [in] 一个设备矩阵视图,指向一个行优先矩阵 [n_queries, dim]
neighbors – [out] 一个设备矩阵视图,指向源数据集中邻居的索引 [n_queries, k]
distances – [out] 一个设备矩阵视图,用于存储到选定邻居的距离 [n_queries, k]