Skip to content

Commit

Permalink
Extract numeric helpers from src/runtime into src/numeric
Browse files Browse the repository at this point in the history
Signed-off-by: Juan Cruz Viotti <jv@jviotti.com>
  • Loading branch information
jviotti committed Sep 27, 2024
1 parent 57bdae3 commit ee07931
Show file tree
Hide file tree
Showing 15 changed files with 53 additions and 47 deletions.
1 change: 1 addition & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ configure: .always
$(CMAKE) -S . -B ./build \
-DCMAKE_BUILD_TYPE:STRING=$(PRESET) \
-DCMAKE_COMPILE_WARNING_AS_ERROR:BOOL=ON \
-DJSONBINPACK_NUMERIC:BOOL=ON \
-DJSONBINPACK_RUNTIME:BOOL=ON \
-DJSONBINPACK_COMPILER:BOOL=ON \
-DJSONBINPACK_TESTS:BOOL=ON \
Expand Down
3 changes: 2 additions & 1 deletion src/numeric/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
noa_library(NAMESPACE sourcemeta PROJECT jsonbinpack NAME numeric
FOLDER "JSON BinPack/Numeric")
FOLDER "JSON BinPack/Numeric"
PRIVATE_HEADERS integral.h real.h zigzag.h)

if(JSONBINPACK_INSTALL)
noa_library_install(NAMESPACE sourcemeta PROJECT jsonbinpack NAME numeric)
Expand Down
24 changes: 3 additions & 21 deletions src/numeric/include/sourcemeta/jsonbinpack/numeric.h
Original file line number Diff line number Diff line change
@@ -1,9 +1,6 @@
#ifndef SOURCEMETA_JSONBINPACK_NUMERIC_H_
#define SOURCEMETA_JSONBINPACK_NUMERIC_H_

#include <cstdint> // std::uint8_t, std::int64_t
#include <limits> // std::numeric_limits

/// @defgroup numeric Numeric
/// @brief A comprehensive numeric library for JSON BinPack
///
Expand All @@ -13,23 +10,8 @@
/// #include <sourcemeta/jsonbinpack/numeric.h>
/// ```

namespace sourcemeta::jsonbinpack {

/// @ingroup numeric
template <typename T> constexpr auto is_byte(const T value) noexcept -> bool {
return value <= std::numeric_limits<std::uint8_t>::max();
}

/// @ingroup numeric
constexpr auto count_multiples(const std::int64_t minimum,
const std::int64_t maximum,
const std::int64_t multiplier) -> std::uint64_t {
assert(minimum <= maximum);
assert(multiplier > 0);
return static_cast<std::uint64_t>((maximum / multiplier) -
((minimum - 1) / multiplier));
}

} // namespace sourcemeta::jsonbinpack
#include <sourcemeta/jsonbinpack/numeric_integral.h>
#include <sourcemeta/jsonbinpack/numeric_real.h>
#include <sourcemeta/jsonbinpack/numeric_zigzag.h>

#endif
Original file line number Diff line number Diff line change
@@ -1,27 +1,39 @@
#ifndef SOURCEMETA_JSONBINPACK_RUNTIME_NUMERIC_H_
#define SOURCEMETA_JSONBINPACK_RUNTIME_NUMERIC_H_
#ifndef SOURCEMETA_JSONBINPACK_NUMERIC_INTEGRAL_H_
#define SOURCEMETA_JSONBINPACK_NUMERIC_INTEGRAL_H_

#include <cassert> // assert
#include <cmath> // std::abs
#include <cstdint> // std::uint8_t, std::int64_t, std::uint64_t
#include <limits> // std::numeric_limits

// TODO: Move to src/numeric

namespace sourcemeta::jsonbinpack {

template <unsigned int T> constexpr auto uint_max = (2 << (T - 1)) - 1;

/// @ingroup numeric
template <typename T> constexpr auto is_byte(const T value) noexcept -> bool {
return value <= std::numeric_limits<std::uint8_t>::max();
}

/// @ingroup numeric
constexpr auto count_multiples(const std::int64_t minimum,
const std::int64_t maximum,
const std::int64_t multiplier) -> std::uint64_t {
assert(minimum <= maximum);
assert(multiplier > 0);
return static_cast<std::uint64_t>((maximum / multiplier) -
((minimum - 1) / multiplier));
}

/// @ingroup numeric
template <unsigned int T> constexpr auto uint_max = (2 << (T - 1)) - 1;

/// @ingroup numeric
template <typename T>
constexpr auto is_within(const T value, const std::int64_t lower,
const std::int64_t higher) noexcept -> bool {
return value >= lower && value <= higher;
}

/// @ingroup numeric
template <typename T>
constexpr auto is_within(const T value, const std::uint64_t lower,
const std::uint64_t higher) noexcept -> bool {
Expand All @@ -33,6 +45,7 @@ constexpr auto is_within(const T value, const std::uint64_t lower,
}
}

/// @ingroup numeric
constexpr auto abs(const std::int64_t value) noexcept -> std::uint64_t {
if (value < 0) {
return static_cast<std::uint64_t>(value * -1);
Expand All @@ -41,6 +54,7 @@ constexpr auto abs(const std::int64_t value) noexcept -> std::uint64_t {
}
}

/// @ingroup numeric
constexpr auto divide_ceil(const std::int64_t dividend,
const std::uint64_t divisor) noexcept
-> std::int64_t {
Expand Down Expand Up @@ -68,6 +82,7 @@ constexpr auto divide_ceil(const std::int64_t dividend,
}
}

/// @ingroup numeric
constexpr auto divide_floor(const std::int64_t dividend,
const std::uint64_t divisor) noexcept
-> std::int64_t {
Expand All @@ -88,6 +103,7 @@ constexpr auto divide_floor(const std::int64_t dividend,
}
}

/// @ingroup numeric
constexpr auto closest_smallest_exponent(const std::uint64_t value,
const std::uint8_t base,
const std::uint8_t exponent_start,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,19 +1,18 @@
#ifndef SOURCEMETA_JSONBINPACK_RUNTIME_ENCODER_REAL_H_
#define SOURCEMETA_JSONBINPACK_RUNTIME_ENCODER_REAL_H_
#ifndef SOURCEMETA_JSONBINPACK_NUMERIC_REAL_H_
#define SOURCEMETA_JSONBINPACK_NUMERIC_REAL_H_

#include <cassert> // assert
#include <cmath> // std::modf, std::floor, std::isfinite
#include <concepts> // std::floating_point, std::integral

// TODO: Move to src/numeric

namespace sourcemeta::jsonbinpack {

// IEEE764 floating-point encoding is not precise. Some real numbers
// cannot be represented directly and thus approximations must be
// used. Here, we abuse those imprecision characteristics for
// space-efficiency by performing rounding on a very, very low
// threshold.
/// @ingroup numeric
template <std::floating_point Real>
constexpr auto correct_ieee764(const Real value) -> Real {
assert(std::isfinite(value));
Expand All @@ -29,6 +28,7 @@ constexpr auto correct_ieee764(const Real value) -> Real {
}
}

/// @ingroup numeric
template <std::integral Integer, std::floating_point Real>
constexpr auto real_digits(Real value, std::uint64_t *point_position)
-> Integer {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,13 +1,12 @@
#ifndef SOURCEMETA_JSONBINPACK_RUNTIME_ZIGZAG_H_
#define SOURCEMETA_JSONBINPACK_RUNTIME_ZIGZAG_H_
#ifndef SOURCEMETA_JSONBINPACK_NUMERIC_ZIGZAG_H_
#define SOURCEMETA_JSONBINPACK_NUMERIC_ZIGZAG_H_

#include <cmath> // std::abs
#include <cstdint> // std::uint64_t, std::int64_t

// TODO: Move to src/numeric

namespace sourcemeta::jsonbinpack {

/// @ingroup numeric
constexpr auto zigzag_encode(const std::int64_t value) noexcept
-> std::uint64_t {
if (value >= 0) {
Expand All @@ -17,6 +16,7 @@ constexpr auto zigzag_encode(const std::int64_t value) noexcept
return (static_cast<std::uint64_t>(std::abs(value)) * 2) - 1;
}

/// @ingroup numeric
constexpr auto zigzag_decode(const std::uint64_t value) noexcept
-> std::int64_t {
if (value % 2 == 0) {
Expand Down
6 changes: 4 additions & 2 deletions src/runtime/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,9 @@ noa_library(NAMESPACE sourcemeta PROJECT jsonbinpack NAME runtime
FOLDER "JSON BinPack/Runtime"
PRIVATE_HEADERS
decoder.h decoder_basic.h
encoder.h encoder_basic.h encoder_context.h encoder_real.h
encoder.h encoder_basic.h encoder_context.h
plan.h plan_wrap.h parser.h
zigzag.h varint.h numeric.h
varint.h
SOURCES runtime_parser.cc runtime_parser_v1.h)

if(JSONBINPACK_INSTALL)
Expand All @@ -13,3 +13,5 @@ endif()

target_link_libraries(sourcemeta_jsonbinpack_runtime PUBLIC
sourcemeta::jsontoolkit::json)
target_link_libraries(sourcemeta_jsonbinpack_runtime PUBLIC
sourcemeta::jsonbinpack::numeric)
3 changes: 2 additions & 1 deletion src/runtime/include/sourcemeta/jsonbinpack/runtime_decoder.h
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
#ifndef SOURCEMETA_JSONBINPACK_RUNTIME_DECODER_H_
#define SOURCEMETA_JSONBINPACK_RUNTIME_DECODER_H_

#include <sourcemeta/jsonbinpack/numeric.h>

#include <sourcemeta/jsonbinpack/runtime_decoder_basic.h>
#include <sourcemeta/jsonbinpack/runtime_numeric.h>
#include <sourcemeta/jsonbinpack/runtime_plan.h>
#include <sourcemeta/jsonbinpack/runtime_plan_wrap.h>

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,9 @@
#define SOURCEMETA_JSONBINPACK_RUNTIME_DECODER_BASIC_H_
#ifndef DOXYGEN

#include <sourcemeta/jsonbinpack/numeric.h>

#include <sourcemeta/jsonbinpack/runtime_varint.h>
#include <sourcemeta/jsonbinpack/runtime_zigzag.h>

#include <cassert> // assert
#include <cmath> // std::ceil
Expand Down
4 changes: 2 additions & 2 deletions src/runtime/include/sourcemeta/jsonbinpack/runtime_encoder.h
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
#ifndef SOURCEMETA_JSONBINPACK_RUNTIME_ENCODER_H_
#define SOURCEMETA_JSONBINPACK_RUNTIME_ENCODER_H_

#include <sourcemeta/jsonbinpack/numeric.h>

#include <sourcemeta/jsonbinpack/runtime_encoder_basic.h>
#include <sourcemeta/jsonbinpack/runtime_encoder_real.h>
#include <sourcemeta/jsonbinpack/runtime_numeric.h>
#include <sourcemeta/jsonbinpack/runtime_plan.h>
#include <sourcemeta/jsonbinpack/runtime_plan_wrap.h>

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,10 @@
#define SOURCEMETA_JSONBINPACK_RUNTIME_ENCODER_BASIC_H_
#ifndef DOXYGEN

#include <sourcemeta/jsonbinpack/numeric.h>

#include <sourcemeta/jsonbinpack/runtime_encoder_context.h>
#include <sourcemeta/jsonbinpack/runtime_varint.h>
#include <sourcemeta/jsonbinpack/runtime_zigzag.h>

#include <algorithm> // std::find_if
#include <cassert> // assert
Expand Down
3 changes: 2 additions & 1 deletion src/runtime/include/sourcemeta/jsonbinpack/runtime_plan.h
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
#ifndef SOURCEMETA_JSONBINPACK_RUNTIME_ENCODING_H_
#define SOURCEMETA_JSONBINPACK_RUNTIME_ENCODING_H_

#include <sourcemeta/jsonbinpack/runtime_numeric.h>
#include <sourcemeta/jsonbinpack/numeric.h>

#include <sourcemeta/jsontoolkit/json.h>

#include <cstdint> // std::int64_t, std::uint64_t
Expand Down
2 changes: 1 addition & 1 deletion test/runtime/decode_zigzag_test.cc
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#include <gtest/gtest.h>

#include <sourcemeta/jsonbinpack/runtime_zigzag.h>
#include <sourcemeta/jsonbinpack/numeric.h>
#include <sourcemeta/jsontoolkit/json.h>

#include <limits> // std::numeric_limits
Expand Down
2 changes: 1 addition & 1 deletion test/runtime/encode_real_test.cc
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#include <gtest/gtest.h>

#include <sourcemeta/jsonbinpack/runtime_encoder_real.h>
#include <sourcemeta/jsonbinpack/numeric.h>

TEST(JSONBinPack_Encoder, real_digits_1) {
const double input{3.14};
Expand Down
2 changes: 1 addition & 1 deletion test/runtime/encode_zigzag_test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

#include <limits> // std::numeric_limits

#include <sourcemeta/jsonbinpack/runtime_zigzag.h>
#include <sourcemeta/jsonbinpack/numeric.h>

TEST(JSONBinPack_Encoder, zigzag_int_0_0) {
const int value = 0;
Expand Down

0 comments on commit ee07931

Please sign in to comment.