Skip to content

Instantly share code, notes, and snippets.

@alendit
Last active April 5, 2018 13:17
Show Gist options
  • Save alendit/73ec62887d00fb44ef32e8f8eec41af3 to your computer and use it in GitHub Desktop.
Save alendit/73ec62887d00fb44ef32e8f8eec41af3 to your computer and use it in GitHub Desktop.
Benchmark for the arrow::Status destructor slowdown. Must be compiled with `-lbenchmark` (google benchmark).
#include <arrow/status.h>
#include <benchmark/benchmark.h>
#include <string>
#include <iostream>
using namespace arrow;
#define REPEAT_N(N, BODY) \
for (int idx=0;idx<N;++idx) { \
BODY \
} \
class StatusDestructor {
public:
// Create a success status.
StatusDestructor() : state_(NULL) {}
~StatusDestructor() { delete state_; }
StatusDestructor(StatusCode code, const std::string& msg);
StatusDestructor(const StatusDestructor& s)
: state_((s.state_ == NULL) ? NULL : new State(*s.state_)) {}
// Return a success status.
static StatusDestructor OK() { return StatusDestructor(); }
private:
struct State {
StatusCode code;
std::string msg;
};
// OK status has a `NULL` state_. Otherwise, `state_` points to
// a `State` structure containing the error code and message(s)
State* state_;
};
class StatusDestructorPredict {
public:
// Create a success status.
StatusDestructorPredict() : state_(NULL) {}
~StatusDestructorPredict() { if ARROW_PREDICT_FALSE(state_ != NULL) delete state_; }
StatusDestructorPredict(StatusCode code, const std::string& msg);
StatusDestructorPredict(const StatusDestructorPredict& s)
: state_((s.state_ == NULL) ? NULL : new State(*s.state_)) {}
// Return a success status.
static StatusDestructorPredict OK() { return StatusDestructorPredict(); }
private:
struct State {
StatusCode code;
std::string msg;
};
// OK status has a `NULL` state_. Otherwise, `state_` points to
// a `State` structure containing the error code and message(s)
State* state_;
};
class StatusDestructorNoOp {
public:
// Create a success status.
StatusDestructorNoOp() : state_(NULL) {}
~StatusDestructorNoOp() { }
StatusDestructorNoOp(const StatusDestructorNoOp& s)
: state_((s.state_ == NULL) ? NULL : new State(*s.state_)) {}
// Return a success status.
static StatusDestructorNoOp OK() { return StatusDestructorNoOp(); }
private:
struct State {
StatusCode code;
std::string msg;
};
// OK status has a `NULL` state_. Otherwise, `state_` points to
// a `State` structure containing the error code and message(s)
State* state_;
};
// BENCHMARKS
static void BM_ArrowStatus(benchmark::State& state) {
for (auto _ : state) {
REPEAT_N(1000,
{
Status s = arrow::Status::OK();
benchmark::DoNotOptimize(&s);
})
}
}
BENCHMARK(BM_ArrowStatus);
// this should be exactly the same as Arrows status
static void BM_OwnCopyStatus(benchmark::State& state) {
for (auto _ : state) {
REPEAT_N(1000,
{
StatusDestructor s = StatusDestructor::OK();
benchmark::DoNotOptimize(&s);
})
}
}
BENCHMARK(BM_OwnCopyStatus);
// ???
static void BM_NoOpStatus(benchmark::State& state) {
for (auto _ : state) {
REPEAT_N(1000,
{
StatusDestructorNoOp s = StatusDestructorNoOp::OK();
benchmark::DoNotOptimize(&s);
})
}
}
BENCHMARK(BM_NoOpStatus);
// ???
static void BM_PredictStatus(benchmark::State& state) {
for (auto _ : state) {
REPEAT_N(1000,
{
StatusDestructorPredict s = StatusDestructorPredict::OK();
benchmark::DoNotOptimize(&s);
})
}
}
BENCHMARK(BM_PredictStatus);
BENCHMARK_MAIN();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment