unum-cloud / usearch

Fast Open-Source Search & Clustering engine × for Vectors & 🔜 Strings × in C++, C, Python, JavaScript, Rust, Java, Objective-C, Swift, C#, GoLang, and Wolfram 🔍
https://unum-cloud.github.io/usearch/
Apache License 2.0
2.27k stars 143 forks source link

Bug: Failed to run c++ examples. #414

Closed SheldonFung98 closed 6 months ago

SheldonFung98 commented 6 months ago

Describe the bug

Thanks for the hard work. I run the provided C++ example:

using namespace unum::usearch;

metric_punned_t metric(256, metric_kind_t::l2sq_k, scalar_kind_t::f32_k);

// If you plan to store more than 4 Billion entries - use `index_dense_big_t`.
// Or directly instantiate the template variant you need - `index_dense_gt<vector_key_t, internal_id_t>`.
index_dense_t index = index_dense_t::make(metric);
float vec[3] = {0.1, 0.3, 0.2};

index.reserve(10); // Pre-allocate memory for 10 vectors
index.add(42, &vec[0]); // Pass a key and a vector
auto results = index.search(&vec[0], 5); // Pass a query and limit number of results

for (std::size_t i = 0; i != results.size(); ++i)
    results[i].element.key, results[i].element.vector, results[i].distance;

It gives an error saying: error: ‘struct unum::usearch::index_gt<float, long unsigned int, unsigned int, unum::usearch::aligned_allocator_gt<>, unum::usearch::memory_mapping_allocator_gt<64> >::match_t’ has no member named ‘element’

Then I did some modification:

#include <usearch/index.hpp>
#include <usearch/index_dense.hpp>
#include <usearch/index_plugins.hpp>
#include <iostream>

using namespace unum::usearch;
int main(){

metric_punned_t metric(256, metric_kind_t::l2sq_k, scalar_kind_t::f32_k);

// If you plan to store more than 4 Billion entries - use `index_dense_big_t`.
// Or directly instantiate the template variant you need - `index_dense_gt<vector_key_t, internal_id_t>`.
index_dense_t index = index_dense_t::make(metric);
float vec[3] = {0.1, 0.3, 0.2};

index.reserve(10); // Pre-allocate memory for 10 vectors
index.add(42, &vec[0]); // Pass a key and a vector
//auto results = index_.search(&vec[0], 5); // Pass a query and limit number of results

std::uint64_t matched_keys[10] = {0};
float matched_distances[10] = {0};

std::size_t matched_count = index.search(&vec[2], 5).dump_to(matched_keys, matched_distances);  // Pass a query and limit number of results

for (std::size_t i = 0; i != matched_count; ++i)
    std::cout << matched_keys[i] << " " << matched_distances[i] << std::endl;

return 0;
}

It compile successfully, however the output gives:

42 -nan

Could you help me fix it? Also, is it possible that you could provide an example of using C++ Eigen lib?

Steps to reproduce

At the repo root folder, I add a test.cpp file:

#include <usearch/index.hpp>
#include <usearch/index_dense.hpp>
#include <usearch/index_plugins.hpp>
#include <iostream>

using namespace unum::usearch;
int main(){

metric_punned_t metric(256, metric_kind_t::l2sq_k, scalar_kind_t::f32_k);

// If you plan to store more than 4 Billion entries - use `index_dense_big_t`.
// Or directly instantiate the template variant you need - `index_dense_gt<vector_key_t, internal_id_t>`.
index_dense_t index = index_dense_t::make(metric);
float vec[3] = {0.1, 0.3, 0.2};

index.reserve(10); // Pre-allocate memory for 10 vectors
index.add(42, &vec[0]); // Pass a key and a vector
//auto results = index_.search(&vec[0], 5); // Pass a query and limit number of results

std::uint64_t matched_keys[10] = {0};
float matched_distances[10] = {0};

std::size_t matched_count = index.search(&vec[2], 5).dump_to(matched_keys, matched_distances);  // Pass a query and limit number of results

for (std::size_t i = 0; i != matched_count; ++i)
    std::cout << matched_keys[i] << " " << matched_distances[i] << std::endl;

return 0;
}

Then compile:

g++ -Iinclude -Ifp16/include -o test test.cpp

Expected behavior

Expect to give correct distance value.

USearch version

v2.12.0

Operating System

Ubuntu 22.04

Hardware architecture

x86

Which interface are you using?

C++ implementation

Contact Details

No response

Are you open to being tagged as a contributor?

Is there an existing issue for this?

Code of Conduct

ashvardanian commented 6 months ago

Hey @SheldonFung98! You are creating and index with 256 dimensions and passing a pointer to a buffer with only 3 floats. That's undefined behavior.

error: ‘struct unum::usearch::index_gt<float, long unsigned int, unsigned int, unum::usearch::aligned_allocator_gt<>, unum::usearch::memory_mapping_allocator_gt<64> >::match_t’ has no member named ‘element’

As for this, can you please open a PR patching the documentation? Much appreciated 🤗

SheldonFung98 commented 6 months ago

Appreciate it! I will!