summaryrefslogtreecommitdiffstats
path: root/eval
diff options
context:
space:
mode:
authorHåvard Pettersen <havardpe@oath.com>2020-10-14 16:26:18 +0000
committerHåvard Pettersen <havardpe@oath.com>2020-10-16 13:08:48 +0000
commit3ae8b990e26cfc47db257a1a5f8675f001937475 (patch)
tree365e0dabb59514da5b381972b98750bbe044200c /eval
parent7471fff2c35fd1523d178948d1edc5b2a02cdf63 (diff)
added tensor create benchmark
Diffstat (limited to 'eval')
-rw-r--r--eval/src/tests/tensor/instruction_benchmark/instruction_benchmark.cpp127
1 files changed, 86 insertions, 41 deletions
diff --git a/eval/src/tests/tensor/instruction_benchmark/instruction_benchmark.cpp b/eval/src/tests/tensor/instruction_benchmark/instruction_benchmark.cpp
index d795c4d83c2..da20520730b 100644
--- a/eval/src/tests/tensor/instruction_benchmark/instruction_benchmark.cpp
+++ b/eval/src/tests/tensor/instruction_benchmark/instruction_benchmark.cpp
@@ -57,6 +57,53 @@ template <typename T> using CREF = std::reference_wrapper<const T>;
//-----------------------------------------------------------------------------
+struct D {
+ vespalib::string name;
+ bool mapped;
+ size_t size;
+ size_t stride;
+ static D map(const vespalib::string &name_in, size_t size_in, size_t stride_in) { return D{name_in, true, size_in, stride_in}; }
+ static D idx(const vespalib::string &name_in, size_t size_in) { return D{name_in, false, size_in, 1}; }
+ operator ValueType::Dimension() const {
+ if (mapped) {
+ return ValueType::Dimension(name);
+ } else {
+ return ValueType::Dimension(name, size);
+ }
+ }
+ TensorSpec::Label operator()(size_t idx) const {
+ if (mapped) {
+ return TensorSpec::Label(fmt("label_%zu", idx));
+ } else {
+ return TensorSpec::Label(idx);
+ }
+ }
+};
+
+void add_cells(TensorSpec &spec, double &seq, TensorSpec::Address addr) {
+ spec.add(addr, seq);
+ seq += 1.0;
+}
+
+template <typename ...Ds> void add_cells(TensorSpec &spec, double &seq, TensorSpec::Address addr, const D &d, const Ds &...ds) {
+ for (size_t i = 0, idx = 0; i < d.size; ++i, idx += d.stride) {
+ addr.insert_or_assign(d.name, d(idx));
+ add_cells(spec, seq, addr, ds...);
+ }
+}
+
+template <typename ...Ds> TensorSpec make_spec(double seq, const Ds &...ds) {
+ TensorSpec spec(ValueType::tensor_type({ds...}, ValueType::CellType::FLOAT).to_spec());
+ add_cells(spec, seq, TensorSpec::Address(), ds...);
+ return spec;
+}
+
+TensorSpec make_vector(const D &d1, double seq) { return make_spec(seq, d1); }
+TensorSpec make_matrix(const D &d1, const D &d2, double seq) { return make_spec(seq, d1, d2); }
+TensorSpec make_cube(const D &d1, const D &d2, const D &d3, double seq) { return make_spec(seq, d1, d2, d3); }
+
+//-----------------------------------------------------------------------------
+
struct Impl {
size_t order;
vespalib::string name;
@@ -105,6 +152,16 @@ struct Impl {
const auto &map_node = tensor_function::map(lhs_node, function, stash);
return map_node.compile_self(engine, stash);
}
+ Instruction create_tensor_create(const ValueType &proto_type, const TensorSpec &proto, Stash &stash) const {
+ // create a complete tensor function, but only compile the relevant instruction
+ const auto &my_double = tensor_function::inject(ValueType::double_type(), 0, stash);
+ std::map<TensorSpec::Address,TensorFunction::CREF> spec;
+ for (const auto &cell: proto.cells()) {
+ spec.emplace(cell.first, my_double);
+ }
+ const auto &create_tensor_node = tensor_function::create(proto_type, spec, stash);
+ return create_tensor_node.compile_self(engine, stash);
+ }
};
//-----------------------------------------------------------------------------
@@ -365,51 +422,22 @@ void benchmark_concat(const vespalib::string &desc, const TensorSpec &lhs,
//-----------------------------------------------------------------------------
-struct D {
- vespalib::string name;
- bool mapped;
- size_t size;
- size_t stride;
- static D map(const vespalib::string &name_in, size_t size_in, size_t stride_in) { return D{name_in, true, size_in, stride_in}; }
- static D idx(const vespalib::string &name_in, size_t size_in) { return D{name_in, false, size_in, 1}; }
- operator ValueType::Dimension() const {
- if (mapped) {
- return ValueType::Dimension(name);
- } else {
- return ValueType::Dimension(name, size);
- }
- }
- TensorSpec::Label operator()(size_t idx) const {
- if (mapped) {
- return TensorSpec::Label(fmt("label_%zu", idx));
- } else {
- return TensorSpec::Label(idx);
- }
+void benchmark_tensor_create(const vespalib::string &desc, const TensorSpec &proto) {
+ Stash stash;
+ ValueType proto_type = ValueType::from_spec(proto.type());
+ ASSERT_FALSE(proto_type.is_error());
+ std::vector<CREF<TensorSpec>> stack_spec;
+ for (const auto &cell: proto.cells()) {
+ stack_spec.emplace_back(stash.create<TensorSpec>(make_spec(cell.second)));
}
-};
-
-void add_cells(TensorSpec &spec, double &seq, TensorSpec::Address addr) {
- spec.add(addr, seq);
- seq += 1.0;
-}
-
-template <typename ...Ds> void add_cells(TensorSpec &spec, double &seq, TensorSpec::Address addr, const D &d, const Ds &...ds) {
- for (size_t i = 0, idx = 0; i < d.size; ++i, idx += d.stride) {
- addr.insert_or_assign(d.name, d(idx));
- add_cells(spec, seq, addr, ds...);
+ std::vector<EvalOp::UP> list;
+ for (const Impl &impl: impl_list) {
+ auto op = impl.create_tensor_create(proto_type, proto, stash);
+ list.push_back(std::make_unique<EvalOp>(op, stack_spec, impl));
}
+ benchmark(desc, list);
}
-template <typename ...Ds> TensorSpec make_spec(double seq, const Ds &...ds) {
- TensorSpec spec(ValueType::tensor_type({ds...}, ValueType::CellType::FLOAT).to_spec());
- add_cells(spec, seq, TensorSpec::Address(), ds...);
- return spec;
-}
-
-TensorSpec make_vector(const D &d1, double seq) { return make_spec(seq, d1); }
-TensorSpec make_matrix(const D &d1, const D &d2, double seq) { return make_spec(seq, d1, d2); }
-TensorSpec make_cube(const D &d1, const D &d2, const D &d3, double seq) { return make_spec(seq, d1, d2, d3); }
-
//-----------------------------------------------------------------------------
TEST(MakeInputTest, print_some_test_input) {
@@ -662,6 +690,23 @@ TEST(MapBench, mixed_map) {
//-----------------------------------------------------------------------------
+TEST(TensorCreateBench, create_dense) {
+ auto proto = make_matrix(D::idx("a", 32), D::idx("b", 32), 1.0);
+ benchmark_tensor_create("dense tensor create", proto);
+}
+
+TEST(TensorCreateBench, create_sparse) {
+ auto proto = make_matrix(D::map("a", 32, 1), D::map("b", 32, 1), 1.0);
+ benchmark_tensor_create("sparse tensor create", proto);
+}
+
+TEST(TensorCreateBench, create_mixed) {
+ auto proto = make_matrix(D::map("a", 32, 1), D::idx("b", 32), 1.0);
+ benchmark_tensor_create("mixed tensor create", proto);
+}
+
+//-----------------------------------------------------------------------------
+
void print_results(const vespalib::string &desc, const std::vector<BenchmarkResult> &results) {
if (results.empty()) {
return;