62 lines
1.8 KiB
C++
62 lines
1.8 KiB
C++
|
|
#include <cstdint>
|
||
|
|
#include <iostream>
|
||
|
|
|
||
|
|
#include "dpf.hpp"
|
||
|
|
#include "dpf/app_flow.hpp"
|
||
|
|
#include "dpf/app_plans.hpp"
|
||
|
|
|
||
|
|
// A private range count. Each secret value is one comparison key. The
|
||
|
|
// public interval is [lo, hi). The comparison opens to 1 at a query q
|
||
|
|
// when q is strictly above the secret value, so the two endpoints
|
||
|
|
// differ by 1 exactly on lo <= v < hi. The count is the sum of those
|
||
|
|
// bits. The servers never see a value, and the interval is public.
|
||
|
|
//
|
||
|
|
// c++ -std=c++17 -march=native -I include -I thirdparty \
|
||
|
|
// examples/applications/range_count.cpp
|
||
|
|
|
||
|
|
namespace
|
||
|
|
{
|
||
|
|
|
||
|
|
std::uint64_t inside(std::uint8_t value, std::uint8_t lo, std::uint8_t hi)
|
||
|
|
{
|
||
|
|
auto [k0, k1] = dpf::make_dpf(value, dpf::gt(std::uint64_t{1}));
|
||
|
|
const auto above_lo = dpf::reconstruct(
|
||
|
|
dpf::eval_point(dpf::cmp, k0, lo),
|
||
|
|
dpf::eval_point(dpf::cmp, k1, lo));
|
||
|
|
const auto above_hi = dpf::reconstruct(
|
||
|
|
dpf::eval_point(dpf::cmp, k0, hi),
|
||
|
|
dpf::eval_point(dpf::cmp, k1, hi));
|
||
|
|
// eval(q) = 1 iff q > value, so eval(hi) - eval(lo) = 1{lo <= value < hi}.
|
||
|
|
return above_hi - above_lo;
|
||
|
|
}
|
||
|
|
|
||
|
|
} // namespace
|
||
|
|
|
||
|
|
int main()
|
||
|
|
{
|
||
|
|
constexpr std::uint8_t lo = 10;
|
||
|
|
constexpr std::uint8_t hi = 20;
|
||
|
|
const std::uint8_t values[] = {3, 10, 12, 19, 20, 40};
|
||
|
|
|
||
|
|
std::uint64_t count = 0;
|
||
|
|
for (auto v : values)
|
||
|
|
count += inside(v, lo, hi);
|
||
|
|
|
||
|
|
// 10, 12, and 19. 3 and 40 are outside. 20 is the open end.
|
||
|
|
if (count != 3 || inside(10, lo, hi) != 1 || inside(20, lo, hi) != 0
|
||
|
|
|| inside(9, lo, hi) != 0)
|
||
|
|
{
|
||
|
|
std::cerr << "range count " << count << "\n";
|
||
|
|
return 1;
|
||
|
|
}
|
||
|
|
|
||
|
|
{
|
||
|
|
if (int rc = dpf::app::run_measured("range_count",
|
||
|
|
dpf::protocol::range_count_plan(0), 8))
|
||
|
|
return rc;
|
||
|
|
}
|
||
|
|
|
||
|
|
std::cout << count << "\n";
|
||
|
|
return 0;
|
||
|
|
}
|