Skip to content

Commit

Permalink
(DNND) Add custom point example with simple API
Browse files Browse the repository at this point in the history
  • Loading branch information
Keita Iwabuchi committed Jun 12, 2024
1 parent ec20f52 commit 5059ab3
Show file tree
Hide file tree
Showing 5 changed files with 97 additions and 7 deletions.
1 change: 1 addition & 0 deletions examples/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@ if (SALTATLAS_USE_METALL)
add_saltatlas_example(dnnd_pm_optimize_example)
add_saltatlas_example(dnnd_pm_query_example)
add_saltatlas_example(dnnd_simple_example)
add_saltatlas_example(dnnd_simple_custom_distance_example)
add_saltatlas_example(dnnd_simple_custom_point_example)

add_saltatlas_dnnd_example_feature_type(dnnd_pm_const_example float)
Expand Down
70 changes: 70 additions & 0 deletions examples/dnnd_simple_custom_distance_example.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
// Copyright 2024 Lawrence Livermore National Security, LLC and other
// saltatlas Project Developers. See the top-level COPYRIGHT file for details.
//
// SPDX-License-Identifier: MIT

/// \brief A simple example of using DNND's simple with a custom distance function.
/// It is recommended to see the examples/dnnd_simple_example.cpp beforehand.
/// Usage:
/// cd build
/// mpirun -n 2 ./example/dnnd_simple_custom_distance_example

#include <iostream>
#include <vector>

#include <ygm/comm.hpp>

#include <saltatlas/dnnd/dnnd_simple.hpp>

// Point ID type
using id_t = uint32_t;
using dist_t = double;

// Point Type
using point_type = saltatlas::feature_vector<float>;

// Custom distance function
// The distance function should have the signature as follows:
// distance_type(const point_type& a, const point_type& b);
dist_t custom_distance(const point_type& p1, const point_type& p2) {
// A simple (squared) L2 distance example
dist_t dist = 0.0;
for (size_t i = 0; i < p1.size(); ++i) {
dist += (p1[i] - p2[i]) * (p1[i] - p2[i]);
}
return dist;
}

int main(int argc, char** argv) {
ygm::comm comm(&argc, &argv);

saltatlas::dnnd<id_t, point_type, dist_t> g(custom_distance, comm);
std::vector<std::filesystem::path> paths{
"../examples/datasets/point_5-4.txt"};
g.load_points(paths.begin(), paths.end(), "wsv");

// ----- NNG build and NN search APIs ----- //
int k = 4;
g.build(k);

bool make_graph_undirected = true;
g.optimize(make_graph_undirected);

// Run queries
std::vector<point_type> queries;
if (comm.rank() == 0) {
queries.push_back(point_type{61.58, 29.68, 20.43, 99.22, 21.81});
}
int num_to_search = 4;
const auto results = g.query(queries.begin(), queries.end(), num_to_search);

if (comm.rank() == 0) {
std::cout << "Neighbours (id, distance):";
for (const auto& [nn_id, nn_dist] : results[0]) {
std::cout << " " << nn_id << " (" << nn_dist << ")";
}
std::cout << std::endl;
}

return 0;
}
8 changes: 8 additions & 0 deletions examples/dnnd_simple_custom_point_example.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,13 @@
//
// SPDX-License-Identifier: MIT

/// \brief A simple example of using DNND's simple API with a custom point type
/// and custom distance function.
/// It is recommended to see the examples/dnnd_simple_example.cpp beforehand.
/// Usage:
/// cd build
/// mpirun -n 2 ./example/dnnd_simple_custom_point_example

#include <iostream>
#include <vector>

Expand Down Expand Up @@ -39,6 +46,7 @@ int main(int argc, char** argv) {

// Add points
{
// Assuming ids and points are stored in vectors
std::vector<id_t> ids;
std::vector<graph_point> points;
g.add_points(ids.begin(), ids.end(), points.begin(), points.end());
Expand Down
16 changes: 15 additions & 1 deletion examples/dnnd_simple_example.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,11 @@
//
// SPDX-License-Identifier: MIT

/// \brief A simple example of using the DNND's simple API.
/// Usage:
/// cd build
/// mpirun -n 2 ./example/dnnd_simple_example

#include <iostream>
#include <vector>

Expand All @@ -20,8 +25,16 @@ using point_type = saltatlas::feature_vector<float>;
int main(int argc, char** argv) {
ygm::comm comm(&argc, &argv);

saltatlas::dnnd<id_t, point_type, dist_t> g(saltatlas::distance::id::l2,
// Create a DNND object
// Use the squared L2 distance function
saltatlas::dnnd<id_t, point_type, dist_t> g(saltatlas::distance::id::sql2,
comm);

// Load points from file(s)
// The file format is assumed to be whitespace-separated values (wsv)
// One point per line. Each feature value is separated by a whitespace.
// DNND assigns an ID to each point in the order they are loaded,
// i.e., ID is the line number starting from 0.
std::vector<std::filesystem::path> paths{
"../examples/datasets/point_5-4.txt"};
g.load_points(paths.begin(), paths.end(), "wsv");
Expand All @@ -41,6 +54,7 @@ int main(int argc, char** argv) {
int num_to_search = 4;
const auto results = g.query(queries.begin(), queries.end(), num_to_search);

// Show the query results
if (comm.rank() == 0) {
std::cout << "Neighbours (id, distance):";
for (const auto& [nn_id, nn_dist] : results[0]) {
Expand Down
9 changes: 3 additions & 6 deletions include/saltatlas/dnnd/dnnd_simple.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,7 @@
//
// SPDX-License-Identifier: MIT

#ifndef SALTATLAS_INCLUDE_SALTATLAS_DNND_DNND_SIMPLE_HPP_
#define SALTATLAS_INCLUDE_SALTATLAS_DNND_DNND_SIMPLE_HPP_
#pragma once

#include <filesystem>
#include <string_view>
Expand All @@ -25,7 +24,7 @@ namespace saltatlas {
template <typename Id = uint64_t,
typename Point = saltatlas::feature_vector<double>,
typename Distance = double>
class dnnd : public dndetail::base_dnnd<Id, Point, Distance> {
class dnnd : public dndetail::base_dnnd<Id, Point, Distance> { // FIXIME: change to use composition model rather than inheritance
private:
using base_type = dndetail::base_dnnd<Id, Point, Distance>;
using data_core_type = typename base_type::data_core_type;
Expand Down Expand Up @@ -249,6 +248,4 @@ class dnnd : public dndetail::base_dnnd<Id, Point, Distance> {
data_core_type m_data_core;
};

} // namespace saltatlas

#endif // SALTATLAS_INCLUDE_SALTATLAS_DNND_DNND_SIMPLE_HPP_
} // namespace saltatlas

0 comments on commit 5059ab3

Please sign in to comment.