Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Reenable NN descent batch tests #424

Draft
wants to merge 11 commits into
base: branch-24.12
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
300 changes: 294 additions & 6 deletions cpp/include/cuvs/neighbors/nn_descent.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,8 @@ struct index_params : cuvs::neighbors::index_params {
size_t intermediate_graph_degree = 128; // Degree of input graph for pruning.
size_t max_iterations = 20; // Number of nn-descent iterations.
float termination_threshold = 0.0001; // Termination threshold of nn-descent.
bool return_distances = false; // return distances if true
size_t n_clusters = 1; // defaults to not using any batching

/** @brief Construct NN descent parameters for a specific kNN graph degree
*
Expand Down Expand Up @@ -100,14 +102,20 @@ struct index : cuvs::neighbors::index {
* @param res raft::resources is an object mangaging resources
* @param n_rows number of rows in knn-graph
* @param n_cols number of cols in knn-graph
* @param return_distances whether to return distances
*/
index(raft::resources const& res, int64_t n_rows, int64_t n_cols)
index(raft::resources const& res, int64_t n_rows, int64_t n_cols, bool return_distances = false)
: cuvs::neighbors::index(),
res_{res},
metric_{cuvs::distance::DistanceType::L2Expanded},
graph_{raft::make_host_matrix<IdxT, int64_t, raft::row_major>(n_rows, n_cols)},
graph_view_{graph_.view()}
graph_view_{graph_.view()},
return_distances_{return_distances}
{
if (return_distances) {
distances_ = raft::make_device_matrix<float, int64_t>(res_, n_rows, n_cols);
distances_view_ = distances_.value().view();
}
}

/**
Expand All @@ -119,14 +127,22 @@ struct index : cuvs::neighbors::index {
*
* @param res raft::resources is an object mangaging resources
* @param graph_view raft::host_matrix_view<IdxT, int64_t, raft::row_major> for storing knn-graph
* @param distances_view optional raft::device_matrix_view<float, int64_t, row_major> for storing
* distances
* @param return_distances whether to return distances
*/
index(raft::resources const& res,
raft::host_matrix_view<IdxT, int64_t, raft::row_major> graph_view)
raft::host_matrix_view<IdxT, int64_t, raft::row_major> graph_view,
std::optional<raft::device_matrix_view<float, int64_t, row_major>> distances_view =
std::nullopt,
bool return_distances = false)
: cuvs::neighbors::index(),
res_{res},
metric_{cuvs::distance::DistanceType::L2Expanded},
graph_{raft::make_host_matrix<IdxT, int64_t, raft::row_major>(0, 0)},
graph_view_{graph_view}
graph_view_{graph_view},
distances_view_{distances_view},
return_distances_{return_distances}
{
}

Expand Down Expand Up @@ -155,6 +171,13 @@ struct index : cuvs::neighbors::index {
return graph_view_;
}

/** neighborhood graph distances [size, graph-degree] */
[[nodiscard]] inline auto distances() noexcept
-> std::optional<device_matrix_view<float, int64_t, row_major>>
{
return distances_view_;
}

// Don't allow copying the index for performance reasons (try avoiding copying data)
index(const index&) = delete;
index(index&&) = default;
Expand All @@ -166,8 +189,11 @@ struct index : cuvs::neighbors::index {
raft::resources const& res_;
cuvs::distance::DistanceType metric_;
raft::host_matrix<IdxT, int64_t, raft::row_major> graph_; // graph to return for non-int IdxT
std::optional<raft::device_matrix<float, int64_t, row_major>> distances_;
raft::host_matrix_view<IdxT, int64_t, raft::row_major>
graph_view_; // view of graph for user provided matrix
std::optional<raft::device_matrix_view<float, int64_t, row_major>> distances_view_;
bool return_distances_;
};

/** @} */
Expand Down Expand Up @@ -393,8 +419,6 @@ auto build(raft::resources const& res,
raft::device_matrix_view<const uint8_t, int64_t, raft::row_major> dataset)
-> cuvs::neighbors::nn_descent::index<uint32_t>;

/** @} */

/**
* @brief Build nn-descent Index with dataset in host memory
*
Expand Down Expand Up @@ -427,6 +451,270 @@ auto build(raft::resources const& res,
raft::host_matrix_view<const uint8_t, int64_t, raft::row_major> dataset)
-> cuvs::neighbors::nn_descent::index<uint32_t>;

/**
* @brief Build nn-descent Index with dataset in device memory
*
* The following distance metrics are supported:
* - L2
*
* Usage example:
* @code{.cpp}
* using namespace cuvs::neighbors;
* // use default index parameters
* nn_descent::index_params index_params;
* // create and fill the index from a [N, D] raft::device_matrix_view dataset
* auto index = nn_descent::index(res, index_params, N, D);
* // index.graph() provides a raft::host_matrix_view of an
* // all-neighbors knn graph of dimensions [N, k] of the input
* // dataset
* nn_descent::build(res, index_params, dataset, index);
* @endcode
*
* @param[in] res raft::resources is an object mangaging resources
* @param[in] params an instance of nn_descent::index_params that are parameters
* to run the nn-descent algorithm
* @param[in] dataset raft::device_matrix_view input dataset expected to be located
* in device memory
* @param[out] index<IdxT> index containing all-neighbors knn graph in host memory
*/
void build(raft::resources const& res,
index_params const& params,
raft::device_matrix_view<const float, int64_t, raft::row_major> dataset,
index<uint32_t>& index);

/**
* @brief Build nn-descent Index with dataset in host memory
*
* The following distance metrics are supported:
* - L2
*
* Usage example:
* @code{.cpp}
* using namespace cuvs::neighbors;
* // use default index parameters
* nn_descent::index_params index_params;
* // create and fill the index from a [N, D] raft::device_matrix_view dataset
* auto index = nn_descent::index(res, index_params, N, D);
* // index.graph() provides a raft::host_matrix_view of an
* // all-neighbors knn graph of dimensions [N, k] of the input
* // dataset
* nn_descent::build(res, index_params, dataset, index);
* @endcode
*
* @tparam T data-type of the input dataset
* @tparam IdxT data-type for the output index
* @param res raft::resources is an object mangaging resources
* @param[in] params an instance of nn_descent::index_params that are parameters
* to run the nn-descent algorithm
* @param[in] dataset raft::host_matrix_view input dataset expected to be located
* in host memory
* @param[out] index<IdxT> index containing all-neighbors knn graph in host memory
*/
void build(raft::resources const& res,
index_params const& params,
raft::host_matrix_view<const float, int64_t, raft::row_major> dataset,
index<uint32_t>& index);

/**
* @brief Build nn-descent Index with dataset in host memory
*
* The following distance metrics are supported:
* - L2
*
* Usage example:
* @code{.cpp}
* using namespace cuvs::neighbors;
* // use default index parameters
* nn_descent::index_params index_params;
* // create and fill the index from a [N, D] raft::device_matrix_view dataset
* auto index = nn_descent::index(res, index_params, N, D);
* // index.graph() provides a raft::host_matrix_view of an
* // all-neighbors knn graph of dimensions [N, k] of the input
* // dataset
* nn_descent::build(res, index_params, dataset, index);
* @endcode
*
* @tparam T data-type of the input dataset
* @tparam IdxT data-type for the output index
* @param res raft::resources is an object mangaging resources
* @param[in] params an instance of nn_descent::index_params that are parameters
* to run the nn-descent algorithm
* @param[in] dataset raft::host_matrix_view input dataset expected to be located
* in host memory
* @param[out] index<IdxT> index containing all-neighbors knn graph in host memory
*/
void build(raft::resources const& res,
index_params const& params,
raft::device_matrix_view<const half, int64_t, raft::row_major> dataset,
index<uint32_t>& index);

/**
* @brief Build nn-descent Index with dataset in host memory
*
* The following distance metrics are supported:
* - L2
*
* Usage example:
* @code{.cpp}
* using namespace cuvs::neighbors;
* // use default index parameters
* nn_descent::index_params index_params;
* // create and fill the index from a [N, D] raft::device_matrix_view dataset
* auto index = nn_descent::index(res, index_params, N, D);
* // index.graph() provides a raft::host_matrix_view of an
* // all-neighbors knn graph of dimensions [N, k] of the input
* // dataset
* nn_descent::build(res, index_params, dataset, index);
* @endcode
*
* @tparam T data-type of the input dataset
* @tparam IdxT data-type for the output index
* @param res raft::resources is an object mangaging resources
* @param[in] params an instance of nn_descent::index_params that are parameters
* to run the nn-descent algorithm
* @param[in] dataset raft::host_matrix_view input dataset expected to be located
* in host memory
* @param[out] index<IdxT> index containing all-neighbors knn graph in host memory
*/
void build(raft::resources const& res,
index_params const& params,
raft::host_matrix_view<const half, int64_t, raft::row_major> dataset,
index<uint32_t>& index);

/**
* @brief Build nn-descent Index with dataset in host memory
*
* The following distance metrics are supported:
* - L2
*
* Usage example:
* @code{.cpp}
* using namespace cuvs::neighbors;
* // use default index parameters
* nn_descent::index_params index_params;
* // create and fill the index from a [N, D] raft::device_matrix_view dataset
* auto index = nn_descent::index(res, index_params, N, D);
* // index.graph() provides a raft::host_matrix_view of an
* // all-neighbors knn graph of dimensions [N, k] of the input
* // dataset
* nn_descent::build(res, index_params, dataset, index);
* @endcode
*
* @tparam T data-type of the input dataset
* @tparam IdxT data-type for the output index
* @param res raft::resources is an object mangaging resources
* @param[in] params an instance of nn_descent::index_params that are parameters
* to run the nn-descent algorithm
* @param[in] dataset raft::host_matrix_view input dataset expected to be located
* in host memory
* @param[out] index<IdxT> index containing all-neighbors knn graph in host memory
*/
void build(raft::resources const& res,
index_params const& params,
raft::device_matrix_view<const int8_t, int64_t, raft::row_major> dataset,
index<uint32_t>& index);

/**
* @brief Build nn-descent Index with dataset in host memory
*
* The following distance metrics are supported:
* - L2
*
* Usage example:
* @code{.cpp}
* using namespace cuvs::neighbors;
* // use default index parameters
* nn_descent::index_params index_params;
* // create and fill the index from a [N, D] raft::device_matrix_view dataset
* auto index = nn_descent::index(res, index_params, N, D);
* // index.graph() provides a raft::host_matrix_view of an
* // all-neighbors knn graph of dimensions [N, k] of the input
* // dataset
* nn_descent::build(res, index_params, dataset, index);
* @endcode
*
* @tparam T data-type of the input dataset
* @tparam IdxT data-type for the output index
* @param res raft::resources is an object mangaging resources
* @param[in] params an instance of nn_descent::index_params that are parameters
* to run the nn-descent algorithm
* @param[in] dataset raft::host_matrix_view input dataset expected to be located
* in host memory
* @param[out] index<IdxT> index containing all-neighbors knn graph in host memory
*/
void build(raft::resources const& res,
index_params const& params,
raft::host_matrix_view<const int8_t, int64_t, raft::row_major> dataset,
index<uint32_t>& index);

/**
* @brief Build nn-descent Index with dataset in host memory
*
* The following distance metrics are supported:
* - L2
*
* Usage example:
* @code{.cpp}
* using namespace cuvs::neighbors;
* // use default index parameters
* nn_descent::index_params index_params;
* // create and fill the index from a [N, D] raft::device_matrix_view dataset
* auto index = nn_descent::index(res, index_params, N, D);
* // index.graph() provides a raft::host_matrix_view of an
* // all-neighbors knn graph of dimensions [N, k] of the input
* // dataset
* nn_descent::build(res, index_params, dataset, index);
* @endcode
*
* @tparam T data-type of the input dataset
* @tparam IdxT data-type for the output index
* @param res raft::resources is an object mangaging resources
* @param[in] params an instance of nn_descent::index_params that are parameters
* to run the nn-descent algorithm
* @param[in] dataset raft::host_matrix_view input dataset expected to be located
* in host memory
* @param[out] index<IdxT> index containing all-neighbors knn graph in host memory
*/
void build(raft::resources const& res,
index_params const& params,
raft::device_matrix_view<const uint8_t, int64_t, raft::row_major> dataset,
index<uint32_t>& index);

/**
* @brief Build nn-descent Index with dataset in host memory
*
* The following distance metrics are supported:
* - L2
*
* Usage example:
* @code{.cpp}
* using namespace cuvs::neighbors;
* // use default index parameters
* nn_descent::index_params index_params;
* // create and fill the index from a [N, D] raft::device_matrix_view dataset
* auto index = nn_descent::index(res, index_params, N, D);
* // index.graph() provides a raft::host_matrix_view of an
* // all-neighbors knn graph of dimensions [N, k] of the input
* // dataset
* nn_descent::build(res, index_params, dataset, index);
* @endcode
*
* @tparam T data-type of the input dataset
* @tparam IdxT data-type for the output index
* @param res raft::resources is an object mangaging resources
* @param[in] params an instance of nn_descent::index_params that are parameters
* to run the nn-descent algorithm
* @param[in] dataset raft::host_matrix_view input dataset expected to be located
* in host memory
* @param[out] index<IdxT> index containing all-neighbors knn graph in host memory
*/
void build(raft::resources const& res,
index_params const& params,
raft::host_matrix_view<const uint8_t, int64_t, raft::row_major> dataset,
index<uint32_t>& index);

/** @} */

/**
* @brief Test if we have enough GPU memory to run NN descent algorithm.
*
Expand Down
5 changes: 2 additions & 3 deletions cpp/src/neighbors/detail/cagra/cagra_build.cuh
Original file line number Diff line number Diff line change
Expand Up @@ -33,8 +33,7 @@
#include <cuvs/neighbors/ivf_pq.hpp>
#include <cuvs/neighbors/refine.hpp>

// TODO: Fixme- this needs to be migrated
#include "../../nn_descent.cuh"
#include <cuvs/neighbors/nn_descent.hpp>

// TODO: This shouldn't be calling spatial/knn APIs
#include "../ann_utils.cuh"
Expand Down Expand Up @@ -357,7 +356,7 @@ void build_knn_graph(
cuvs::neighbors::nn_descent::index_params build_params)
{
auto nn_descent_idx = cuvs::neighbors::nn_descent::index<IdxT>(res, knn_graph);
cuvs::neighbors::nn_descent::build<DataT, IdxT>(res, build_params, dataset, nn_descent_idx);
cuvs::neighbors::nn_descent::build(res, build_params, dataset, nn_descent_idx);

using internal_IdxT = typename std::make_unsigned<IdxT>::type;
using g_accessor = typename decltype(nn_descent_idx.graph())::accessor_type;
Expand Down
Loading
Loading