Skip to content

Commit 633ed00

Browse files
committed
Moved NumericType and get_numeric_type to knncolle for general use.
1 parent 558e085 commit 633ed00

4 files changed

Lines changed: 17 additions & 184 deletions

File tree

include/knncolle_annoy/Annoy.hpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -328,9 +328,9 @@ class AnnoyPrebuilt final : public knncolle::Prebuilt<Index_, Data_, Distance_>
328328
knncolle::quick_save(prefix + "num_dim", &my_dim, 1);
329329
knncolle::quick_save(prefix + "search_mult", &my_search_mult, 1);
330330

331-
NumericType types[2];
332-
types[0] = get_numeric_type<AnnoyIndex_>();
333-
types[1] = get_numeric_type<AnnoyData_>();
331+
knncolle::NumericType types[2];
332+
types[0] = knncolle::get_numeric_type<AnnoyIndex_>();
333+
types[1] = knncolle::get_numeric_type<AnnoyData_>();
334334
knncolle::quick_save(prefix + "types", types, 2);
335335

336336
const auto dname = get_distance_name<AnnoyDistance_>();

include/knncolle_annoy/load_annoy_prebuilt.hpp

Lines changed: 12 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -26,12 +26,12 @@ struct AnnoyPrebuiltTypes {
2626
/**
2727
* Type of the index, i.e., `AnnoyIndex_` in `AnnoyBuilder()`.
2828
*/
29-
NumericType index;
29+
knncolle::NumericType index;
3030

3131
/**
3232
* Type of the data, i.e., `AnnoyData_` in `AnnoyBuilder()`.
3333
*/
34-
NumericType data;
34+
knncolle::NumericType data;
3535

3636
/**
3737
* Name of the distance metric, i.e., `AnnoyDistance_` in `AnnoyBuilder()`.
@@ -47,7 +47,7 @@ struct AnnoyPrebuiltTypes {
4747
* This is typically used to choose template parameters for `load_annoy_prebuilt()`.
4848
*/
4949
inline AnnoyPrebuiltTypes load_annoy_prebuilt_types(const std::string& prefix) {
50-
NumericType types[2];
50+
knncolle::NumericType types[2];
5151
knncolle::quick_load(prefix + "types", types, 2);
5252

5353
AnnoyPrebuiltTypes config;
@@ -61,15 +61,16 @@ inline AnnoyPrebuiltTypes load_annoy_prebuilt_types(const std::string& prefix) {
6161
/**
6262
* Helper function to define a `knncolle::LoadPrebuiltFunction` for Annoy in `knncolle::load_prebuilt()`.
6363
*
64-
* In an Annoy-specific `knncolle::LoadPrebuiltFunction`,
65-
* users should first call `load_annoy_prebuilt_types()` to figure out the saved index's `AnnoyDistance_`, `AnnoyIndex` and `AnnoyData_`.
66-
* Then, they can call `load_annoy_prebuilt()` with the specified types to return a pointer to a `knncolle::Prebuilt` object.
67-
* This can be registered in `load_prebuilt_registry()` with the key in `knncolle_annoy::save_name`.
64+
* To load an Annoy index from disk, users are expected to define and register an Annoy-specific `knncolle::LoadPrebuiltFunction`.
65+
* In this function, users should first call `load_annoy_prebuilt_types()` to figure out the saved index's `AnnoyDistance_`, `AnnoyIndex` and `AnnoyData_`.
66+
* Then, they should call `load_annoy_prebuilt()` with the appropriate types to return a pointer to a `knncolle::Prebuilt` object.
67+
* This user-defined function should be registered in `load_prebuilt_registry()` with the key in `knncolle_annoy::save_name`.
6868
*
69-
* We do not automatically register a function as the user is responsible for deciding what types should be handled.
70-
* This avoids binary bloat from repeated instantiations of the Annoy template classes for every possible combination of types.
71-
* Instead, the user chooses which combinations of types can be loaded, e.g., if their application only deals with those combinations.
72-
* Users may also have more information to handle unknown types from `get_numeric_type()` or unknown distances from `get_distance_name()`.
69+
* We do not define a default function for loading Annoy indices as there are too many possible combinations of types.
70+
* Instead, the user is responsible for deciding which combinations of types should be handled.
71+
* This avoids binary bloat from repeated instantiations of the Annoy template classes, if an application only deals with a certain subset of combinations.
72+
* For types or distances that are unknown to `knncolle::get_numeric_type()` or `get_distance_name()`, respectively,
73+
* users can store additional information on disk via `customize_save_for_annoy_types()` for use in loading.
7374
*
7475
* @tparam Index_ Integer type for the observation indices.
7576
* @tparam Data_ Numeric type for the input and query data.

include/knncolle_annoy/utils.hpp

Lines changed: 1 addition & 128 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,6 @@
33

44
#include <fstream>
55
#include <string>
6-
#include <cstdint>
76
#include <cstddef>
87
#include <stdexcept>
98
#include <type_traits>
@@ -60,135 +59,9 @@ const char* get_distance_name() {
6059
}
6160
}
6261

63-
/**
64-
* Numeric types for `AnnoyIndex_` and `AnnoyData_` template parameters of `AnnoyBuilder`.
65-
* These are typically set by `get_numeric_type()`.
66-
*/
67-
enum class NumericType : char {
68-
UINT8_T, INT8_T,
69-
UINT16_T, INT16_T,
70-
UINT32_T, INT32_T,
71-
UINT64_T, INT64_T,
72-
UNSIGNED_CHAR, SIGNED_CHAR, CHAR,
73-
UNSIGNED_SHORT, SHORT,
74-
UNSIGNED_INT, INT,
75-
UNSIGNED_LONG, LONG,
76-
UNSIGNED_LONG_LONG, LONG_LONG,
77-
SIZE_T, PTRDIFF_T,
78-
FLOAT, DOUBLE,
79-
UNKNOWN
80-
};
81-
82-
/**
83-
* @tparam Type_ Some integer or floating-point type, typically used as `AnnoyIndex_` or `AnnoyData_` in `AnnoyBuilder()`.
84-
* @return Identity of the numeric type.
85-
*
86-
* For unknown types, consider using `customize_save_for_annoy_types()` to add more information to the on-disk representation during a `knncolle::Prebuilt::save()` call.
87-
*/
88-
template<typename Type_>
89-
NumericType get_numeric_type() {
90-
#ifdef UINT8_MAX
91-
if constexpr(std::is_same<Type_, std::uint8_t>::value) {
92-
return NumericType::UINT8_T;
93-
}
94-
#endif
95-
#ifdef INT8_MAX
96-
if constexpr(std::is_same<Type_, std::int8_t>::value) {
97-
return NumericType::INT8_T;
98-
}
99-
#endif
100-
101-
#ifdef UINT16_MAX
102-
if constexpr(std::is_same<Type_, std::uint16_t>::value) {
103-
return NumericType::UINT16_T;
104-
}
105-
#endif
106-
#ifdef INT16_MAX
107-
if constexpr(std::is_same<Type_, std::int16_t>::value) {
108-
return NumericType::INT16_T;
109-
}
110-
#endif
111-
112-
#ifdef UINT32_MAX
113-
if constexpr(std::is_same<Type_, std::uint32_t>::value) {
114-
return NumericType::UINT32_T;
115-
}
116-
#endif
117-
#ifdef INT32_MAX
118-
if constexpr(std::is_same<Type_, std::int32_t>::value) {
119-
return NumericType::INT32_T;
120-
}
121-
#endif
122-
123-
#ifdef UINT64_MAX
124-
if constexpr(std::is_same<Type_, std::uint64_t>::value) {
125-
return NumericType::UINT64_T;
126-
}
127-
#endif
128-
#ifdef INT64_MAX
129-
if constexpr(std::is_same<Type_, std::int64_t>::value) {
130-
return NumericType::INT64_T;
131-
}
132-
#endif
133-
134-
if constexpr(std::is_same<Type_, unsigned char>::value) {
135-
return NumericType::UNSIGNED_CHAR;
136-
}
137-
if constexpr(std::is_same<Type_, signed char>::value) {
138-
return NumericType::SIGNED_CHAR;
139-
}
140-
if constexpr(std::is_same<Type_, char>::value) {
141-
return NumericType::CHAR;
142-
}
143-
144-
if constexpr(std::is_same<Type_, unsigned short>::value) {
145-
return NumericType::UNSIGNED_SHORT;
146-
}
147-
if constexpr(std::is_same<Type_, short>::value) {
148-
return NumericType::SHORT;
149-
}
150-
151-
if constexpr(std::is_same<Type_, unsigned int>::value) {
152-
return NumericType::UNSIGNED_INT;
153-
}
154-
if constexpr(std::is_same<Type_, int>::value) {
155-
return NumericType::INT;
156-
}
157-
158-
if constexpr(std::is_same<Type_, unsigned long>::value) {
159-
return NumericType::UNSIGNED_LONG;
160-
}
161-
if constexpr(std::is_same<Type_, long>::value) {
162-
return NumericType::LONG;
163-
}
164-
165-
if constexpr(std::is_same<Type_, unsigned long long>::value) {
166-
return NumericType::UNSIGNED_LONG_LONG;
167-
}
168-
if constexpr(std::is_same<Type_, long long>::value) {
169-
return NumericType::LONG_LONG;
170-
}
171-
172-
if constexpr(std::is_same<Type_, std::size_t>::value) {
173-
return NumericType::SIZE_T;
174-
}
175-
if constexpr(std::is_same<Type_, std::ptrdiff_t>::value) {
176-
return NumericType::PTRDIFF_T;
177-
}
178-
179-
if constexpr(std::is_same<Type_, float>::value) {
180-
return NumericType::FLOAT;
181-
}
182-
if constexpr(std::is_same<Type_, double>::value) {
183-
return NumericType::DOUBLE;
184-
}
185-
186-
return NumericType::UNKNOWN;
187-
}
188-
18962
/**
19063
* Define a customized saving function to preserve type information from the Annoy index in `knncolle::Prebuilt::save()`.
191-
* Users can provide their own function here, to handle types that are unknown to `get_numeric_type()` or `get_distance_name()`.
64+
* Users can provide their own function here, to handle types that are unknown to `knncolle::get_numeric_type()` or `get_distance_name()`.
19265
* Any modifications to this function are not thread-safe and should be done in a serial section.
19366
*
19467
* @tparam AnnoyDistance_ An **Annoy**-compatible class to compute the distance between vectors.

tests/src/utils.cpp

Lines changed: 1 addition & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -3,48 +3,7 @@
33
#include "knncolle_annoy/utils.hpp"
44
#include "annoy/annoylib.h"
55

6-
#include <cstdint>
7-
#include <cstddef>
8-
9-
TEST(GetNumericType, Basic) {
10-
// Don't do more specific tests because some compilers might have aliases
11-
// e.g., size_t might be a uint64_t and get reported as a UINT64_T.
12-
EXPECT_NE(knncolle_annoy::get_numeric_type<std::uint8_t>(), knncolle_annoy::NumericType::UNKNOWN);
13-
EXPECT_NE(knncolle_annoy::get_numeric_type<std::int8_t>(), knncolle_annoy::NumericType::UNKNOWN);
14-
15-
EXPECT_NE(knncolle_annoy::get_numeric_type<std::uint16_t>(), knncolle_annoy::NumericType::UNKNOWN);
16-
EXPECT_NE(knncolle_annoy::get_numeric_type<std::int16_t>(), knncolle_annoy::NumericType::UNKNOWN);
17-
18-
EXPECT_NE(knncolle_annoy::get_numeric_type<std::uint32_t>(), knncolle_annoy::NumericType::UNKNOWN);
19-
EXPECT_NE(knncolle_annoy::get_numeric_type<std::int32_t>(), knncolle_annoy::NumericType::UNKNOWN);
20-
21-
EXPECT_NE(knncolle_annoy::get_numeric_type<std::uint64_t>(), knncolle_annoy::NumericType::UNKNOWN);
22-
EXPECT_NE(knncolle_annoy::get_numeric_type<std::int64_t>(), knncolle_annoy::NumericType::UNKNOWN);
23-
24-
EXPECT_NE(knncolle_annoy::get_numeric_type<char>(), knncolle_annoy::NumericType::UNKNOWN);
25-
EXPECT_NE(knncolle_annoy::get_numeric_type<signed char>(), knncolle_annoy::NumericType::UNKNOWN);
26-
EXPECT_NE(knncolle_annoy::get_numeric_type<unsigned char>(), knncolle_annoy::NumericType::UNKNOWN);
27-
28-
EXPECT_NE(knncolle_annoy::get_numeric_type<short>(), knncolle_annoy::NumericType::UNKNOWN);
29-
EXPECT_NE(knncolle_annoy::get_numeric_type<unsigned short>(), knncolle_annoy::NumericType::UNKNOWN);
30-
31-
EXPECT_NE(knncolle_annoy::get_numeric_type<int>(), knncolle_annoy::NumericType::UNKNOWN);
32-
EXPECT_NE(knncolle_annoy::get_numeric_type<unsigned int>(), knncolle_annoy::NumericType::UNKNOWN);
33-
34-
EXPECT_NE(knncolle_annoy::get_numeric_type<long>(), knncolle_annoy::NumericType::UNKNOWN);
35-
EXPECT_NE(knncolle_annoy::get_numeric_type<unsigned long>(), knncolle_annoy::NumericType::UNKNOWN);
36-
37-
EXPECT_NE(knncolle_annoy::get_numeric_type<long long>(), knncolle_annoy::NumericType::UNKNOWN);
38-
EXPECT_NE(knncolle_annoy::get_numeric_type<unsigned long long>(), knncolle_annoy::NumericType::UNKNOWN);
39-
40-
EXPECT_NE(knncolle_annoy::get_numeric_type<std::size_t>(), knncolle_annoy::NumericType::UNKNOWN);
41-
EXPECT_NE(knncolle_annoy::get_numeric_type<std::ptrdiff_t>(), knncolle_annoy::NumericType::UNKNOWN);
42-
43-
EXPECT_NE(knncolle_annoy::get_numeric_type<float>(), knncolle_annoy::NumericType::UNKNOWN);
44-
EXPECT_NE(knncolle_annoy::get_numeric_type<double>(), knncolle_annoy::NumericType::UNKNOWN);
45-
46-
EXPECT_EQ(knncolle_annoy::get_numeric_type<bool>(), knncolle_annoy::NumericType::UNKNOWN);
47-
}
6+
#include <string>
487

498
TEST(GetDistanceName, Basic) {
509
EXPECT_EQ(std::string(knncolle_annoy::get_distance_name<Annoy::Euclidean>()), "euclidean");

0 commit comments

Comments
 (0)