summaryrefslogtreecommitdiffstats
path: root/eval
diff options
context:
space:
mode:
authorTor Egge <Tor.Egge@broadpark.no>2020-12-04 13:13:02 +0100
committerTor Egge <Tor.Egge@broadpark.no>2020-12-04 13:19:49 +0100
commitf7d77ed81f3773aeb7bf7a0662d996e2f9de6e08 (patch)
tree3b3ead33c2bf5c4fbba25dd05c74b6d6b1024e54 /eval
parent8bf896022d56552a6b9832afada4634083f4511a (diff)
Split up tensor_model.hpp to avoid ODR violation.
Diffstat (limited to 'eval')
-rw-r--r--eval/src/vespa/eval/eval/test/CMakeLists.txt1
-rw-r--r--eval/src/vespa/eval/eval/test/tensor_model.cpp12
-rw-r--r--eval/src/vespa/eval/eval/test/tensor_model.h260
-rw-r--r--eval/src/vespa/eval/eval/test/tensor_model.hpp236
4 files changed, 276 insertions, 233 deletions
diff --git a/eval/src/vespa/eval/eval/test/CMakeLists.txt b/eval/src/vespa/eval/eval/test/CMakeLists.txt
index 735c793f74b..2e9b50da5e6 100644
--- a/eval/src/vespa/eval/eval/test/CMakeLists.txt
+++ b/eval/src/vespa/eval/eval/test/CMakeLists.txt
@@ -6,6 +6,7 @@ vespa_add_library(eval_eval_test OBJECT
reference_evaluation.cpp
reference_operations.cpp
tensor_conformance.cpp
+ tensor_model.cpp
test_io.cpp
value_compare.cpp
)
diff --git a/eval/src/vespa/eval/eval/test/tensor_model.cpp b/eval/src/vespa/eval/eval/test/tensor_model.cpp
new file mode 100644
index 00000000000..646dab459c1
--- /dev/null
+++ b/eval/src/vespa/eval/eval/test/tensor_model.cpp
@@ -0,0 +1,12 @@
+// Copyright Verizon Media. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root.
+
+#include "tensor_model.h"
+
+namespace vespalib::eval::test {
+
+Seq::~Seq() = default;
+
+Domain::Domain(const Domain &) = default;
+Domain::~Domain() = default;
+
+}
diff --git a/eval/src/vespa/eval/eval/test/tensor_model.h b/eval/src/vespa/eval/eval/test/tensor_model.h
new file mode 100644
index 00000000000..c56f809c936
--- /dev/null
+++ b/eval/src/vespa/eval/eval/test/tensor_model.h
@@ -0,0 +1,260 @@
+// Copyright Verizon Media. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root.
+
+#pragma once
+
+#include <vespa/vespalib/testkit/test_kit.h>
+#include <vespa/eval/eval/tensor_spec.h>
+#include <vespa/eval/eval/value_type.h>
+#include <vespa/eval/eval/operation.h>
+#include <vespa/eval/eval/function.h>
+#include <vespa/eval/eval/node_types.h>
+#include <vespa/eval/eval/interpreted_function.h>
+
+namespace vespalib::eval::test {
+
+using map_fun_t = vespalib::eval::operation::op1_t;
+using join_fun_t = vespalib::eval::operation::op2_t;
+
+// Random access sequence of numbers
+struct Sequence {
+ virtual double operator[](size_t i) const = 0;
+ virtual ~Sequence() {}
+};
+
+// Sequence of natural numbers (starting at 1)
+struct N : Sequence {
+ double operator[](size_t i) const override { return (1.0 + i); }
+};
+
+// Sequence of another sequence divided by 10
+struct Div10 : Sequence {
+ const Sequence &seq;
+ Div10(const Sequence &seq_in) : seq(seq_in) {}
+ double operator[](size_t i) const override { return (seq[i] / 10.0); }
+};
+
+// Sequence of another sequence divided by 16
+struct Div16 : Sequence {
+ const Sequence &seq;
+ Div16(const Sequence &seq_in) : seq(seq_in) {}
+ double operator[](size_t i) const override { return (seq[i] / 16.0); }
+};
+
+
+// Sequence of another sequence minus 2
+struct Sub2 : Sequence {
+ const Sequence &seq;
+ Sub2(const Sequence &seq_in) : seq(seq_in) {}
+ double operator[](size_t i) const override { return (seq[i] - 2.0); }
+};
+
+// Sequence of a unary operator applied to a sequence
+struct OpSeq : Sequence {
+ const Sequence &seq;
+ map_fun_t op;
+ OpSeq(const Sequence &seq_in, map_fun_t op_in) : seq(seq_in), op(op_in) {}
+ double operator[](size_t i) const override { return op(seq[i]); }
+};
+
+// Sequence of applying sigmoid to another sequence
+struct Sigmoid : Sequence {
+ const Sequence &seq;
+ Sigmoid(const Sequence &seq_in) : seq(seq_in) {}
+ double operator[](size_t i) const override { return operation::Sigmoid::f(seq[i]); }
+};
+
+// Sequence of applying sigmoid to another sequence, plus rounding to nearest float
+struct SigmoidF : Sequence {
+ const Sequence &seq;
+ SigmoidF(const Sequence &seq_in) : seq(seq_in) {}
+ double operator[](size_t i) const override { return (float)operation::Sigmoid::f(seq[i]); }
+};
+
+// pre-defined sequence of numbers
+struct Seq : Sequence {
+ std::vector<double> seq;
+ Seq() : seq() {}
+ Seq(const std::vector<double> &seq_in) : seq(seq_in) {}
+ ~Seq() override;
+ double operator[](size_t i) const override {
+ ASSERT_LESS(i, seq.size());
+ return seq[i];
+ }
+};
+
+// Random access bit mask
+struct Mask {
+ virtual bool operator[](size_t i) const = 0;
+ virtual ~Mask() {}
+};
+
+// Mask with all bits set
+struct All : Mask {
+ bool operator[](size_t) const override { return true; }
+};
+
+// Mask with no bits set
+struct None : Mask {
+ bool operator[](size_t) const override { return false; }
+};
+
+// Mask with false for each Nth index
+struct SkipNth : Mask {
+ size_t n;
+ SkipNth(size_t n_in) : n(n_in) {}
+ bool operator[](size_t i) const override { return (i % n) != 0; }
+};
+
+// pre-defined mask
+struct Bits : Mask {
+ std::vector<bool> bits;
+ Bits(const std::vector<bool> &bits_in) : bits(bits_in) {}
+ ~Bits() { }
+ bool operator[](size_t i) const override {
+ ASSERT_LESS(i, bits.size());
+ return bits[i];
+ }
+};
+
+// A mask converted to a sequence of two unique values (mapped from true and false)
+struct Mask2Seq : Sequence {
+ const Mask &mask;
+ double true_value;
+ double false_value;
+ Mask2Seq(const Mask &mask_in, double true_value_in = 1.0, double false_value_in = 0.0)
+ : mask(mask_in), true_value(true_value_in), false_value(false_value_in) {}
+ double operator[](size_t i) const override { return mask[i] ? true_value : false_value; }
+};
+
+// custom op1
+struct MyOp {
+ static double f(double a) {
+ return ((a + 1) * 2);
+ }
+};
+
+// 'a in [1,5,7,13,42]'
+struct MyIn {
+ static double f(double a) {
+ if ((a == 1) ||
+ (a == 5) ||
+ (a == 7) ||
+ (a == 13) ||
+ (a == 42))
+ {
+ return 1.0;
+ } else {
+ return 0.0;
+ }
+ }
+};
+
+// A collection of labels for a single dimension
+struct Domain {
+ vespalib::string dimension;
+ size_t size; // indexed
+ std::vector<vespalib::string> keys; // mapped
+ Domain(const Domain &);
+ Domain(const vespalib::string &dimension_in, size_t size_in)
+ : dimension(dimension_in), size(size_in), keys() {}
+ Domain(const vespalib::string &dimension_in, const std::vector<vespalib::string> &keys_in)
+ : dimension(dimension_in), size(0), keys(keys_in) {}
+ ~Domain();
+};
+
+struct Layout {
+ CellType cell_type;
+ std::vector<Domain> domains;
+ Layout(std::initializer_list<Domain> domains_in)
+ : cell_type(CellType::DOUBLE), domains(domains_in) {}
+ Layout(CellType cell_type_in, std::vector<Domain> domains_in)
+ : cell_type(cell_type_in), domains(std::move(domains_in)) {}
+ auto begin() const { return domains.begin(); }
+ auto end() const { return domains.end(); }
+ auto size() const { return domains.size(); }
+ auto operator[](size_t idx) const { return domains[idx]; }
+};
+
+Layout float_cells(const Layout &layout);
+
+Domain x();
+Domain x(size_t size);
+Domain x(const std::vector<vespalib::string> &keys);
+
+Domain y();
+Domain y(size_t size);
+Domain y(const std::vector<vespalib::string> &keys);
+
+Domain z();
+Domain z(size_t size);
+Domain z(const std::vector<vespalib::string> &keys);
+
+// Infer the tensor type spanned by the given spaces
+vespalib::string infer_type(const Layout &layout);
+
+// Wrapper for the things needed to generate a tensor
+struct Source {
+ using Address = TensorSpec::Address;
+
+ const Layout &layout;
+ const Sequence &seq;
+ const Mask &mask;
+ Source(const Layout &layout_in, const Sequence &seq_in, const Mask &mask_in)
+ : layout(layout_in), seq(seq_in), mask(mask_in) {}
+};
+
+// Mix layout with a number sequence to make a tensor spec
+class TensorSpecBuilder
+{
+private:
+ using Label = TensorSpec::Label;
+ using Address = TensorSpec::Address;
+
+ Source _source;
+ TensorSpec _spec;
+ Address _addr;
+ size_t _idx;
+
+ void generate(size_t layout_idx) {
+ if (layout_idx == _source.layout.size()) {
+ if (_source.mask[_idx]) {
+ _spec.add(_addr, _source.seq[_idx]);
+ }
+ ++_idx;
+ } else {
+ const Domain &domain = _source.layout[layout_idx];
+ if (domain.size > 0) { // indexed
+ for (size_t i = 0; i < domain.size; ++i) {
+ _addr.emplace(domain.dimension, Label(i)).first->second = Label(i);
+ generate(layout_idx + 1);
+ }
+ } else { // mapped
+ for (const vespalib::string &key: domain.keys) {
+ _addr.emplace(domain.dimension, Label(key)).first->second = Label(key);
+ generate(layout_idx + 1);
+ }
+ }
+ }
+ }
+
+public:
+ TensorSpecBuilder(const Layout &layout, const Sequence &seq, const Mask &mask)
+ : _source(layout, seq, mask), _spec(infer_type(layout)), _addr(), _idx(0) {}
+ TensorSpec build() {
+ generate(0);
+ return _spec;
+ }
+};
+TensorSpec spec(const Layout &layout, const Sequence &seq, const Mask &mask);
+TensorSpec spec(const Layout &layout, const Sequence &seq);
+TensorSpec spec(const Layout &layout);
+TensorSpec spec(const Domain &domain, const Sequence &seq, const Mask &mask);
+TensorSpec spec(const Domain &domain, const Sequence &seq);
+TensorSpec spec(const Domain &domain);
+TensorSpec spec(double value);
+TensorSpec spec();
+TensorSpec spec(const vespalib::string &type,
+ const std::vector<std::pair<TensorSpec::Address, TensorSpec::Value>> &cells);
+TensorSpec spec(const vespalib::string &value_expr);
+
+}
diff --git a/eval/src/vespa/eval/eval/test/tensor_model.hpp b/eval/src/vespa/eval/eval/test/tensor_model.hpp
index 02e0b51742d..4b65862b3e7 100644
--- a/eval/src/vespa/eval/eval/test/tensor_model.hpp
+++ b/eval/src/vespa/eval/eval/test/tensor_model.hpp
@@ -2,184 +2,9 @@
#pragma once
-#include <vespa/vespalib/testkit/test_kit.h>
-#include <vespa/eval/eval/tensor_spec.h>
-#include <vespa/eval/eval/value_type.h>
-#include <vespa/eval/eval/operation.h>
-#include <vespa/eval/eval/function.h>
-#include <vespa/eval/eval/node_types.h>
-#include <vespa/eval/eval/interpreted_function.h>
+#include "tensor_model.h"
-namespace vespalib {
-namespace eval {
-namespace test {
-
-using map_fun_t = vespalib::eval::operation::op1_t;
-using join_fun_t = vespalib::eval::operation::op2_t;
-
-// Random access sequence of numbers
-struct Sequence {
- virtual double operator[](size_t i) const = 0;
- virtual ~Sequence() {}
-};
-
-// Sequence of natural numbers (starting at 1)
-struct N : Sequence {
- double operator[](size_t i) const override { return (1.0 + i); }
-};
-
-// Sequence of another sequence divided by 10
-struct Div10 : Sequence {
- const Sequence &seq;
- Div10(const Sequence &seq_in) : seq(seq_in) {}
- double operator[](size_t i) const override { return (seq[i] / 10.0); }
-};
-
-// Sequence of another sequence divided by 16
-struct Div16 : Sequence {
- const Sequence &seq;
- Div16(const Sequence &seq_in) : seq(seq_in) {}
- double operator[](size_t i) const override { return (seq[i] / 16.0); }
-};
-
-
-// Sequence of another sequence minus 2
-struct Sub2 : Sequence {
- const Sequence &seq;
- Sub2(const Sequence &seq_in) : seq(seq_in) {}
- double operator[](size_t i) const override { return (seq[i] - 2.0); }
-};
-
-// Sequence of a unary operator applied to a sequence
-struct OpSeq : Sequence {
- const Sequence &seq;
- map_fun_t op;
- OpSeq(const Sequence &seq_in, map_fun_t op_in) : seq(seq_in), op(op_in) {}
- double operator[](size_t i) const override { return op(seq[i]); }
-};
-
-// Sequence of applying sigmoid to another sequence
-struct Sigmoid : Sequence {
- const Sequence &seq;
- Sigmoid(const Sequence &seq_in) : seq(seq_in) {}
- double operator[](size_t i) const override { return operation::Sigmoid::f(seq[i]); }
-};
-
-// Sequence of applying sigmoid to another sequence, plus rounding to nearest float
-struct SigmoidF : Sequence {
- const Sequence &seq;
- SigmoidF(const Sequence &seq_in) : seq(seq_in) {}
- double operator[](size_t i) const override { return (float)operation::Sigmoid::f(seq[i]); }
-};
-
-// pre-defined sequence of numbers
-struct Seq : Sequence {
- std::vector<double> seq;
- Seq() : seq() {}
- Seq(const std::vector<double> &seq_in) : seq(seq_in) {}
- ~Seq() override;
- double operator[](size_t i) const override {
- ASSERT_LESS(i, seq.size());
- return seq[i];
- }
-};
-
-Seq::~Seq() = default;
-
-// Random access bit mask
-struct Mask {
- virtual bool operator[](size_t i) const = 0;
- virtual ~Mask() {}
-};
-
-// Mask with all bits set
-struct All : Mask {
- bool operator[](size_t) const override { return true; }
-};
-
-// Mask with no bits set
-struct None : Mask {
- bool operator[](size_t) const override { return false; }
-};
-
-// Mask with false for each Nth index
-struct SkipNth : Mask {
- size_t n;
- SkipNth(size_t n_in) : n(n_in) {}
- bool operator[](size_t i) const override { return (i % n) != 0; }
-};
-
-// pre-defined mask
-struct Bits : Mask {
- std::vector<bool> bits;
- Bits(const std::vector<bool> &bits_in) : bits(bits_in) {}
- ~Bits() { }
- bool operator[](size_t i) const override {
- ASSERT_LESS(i, bits.size());
- return bits[i];
- }
-};
-
-// A mask converted to a sequence of two unique values (mapped from true and false)
-struct Mask2Seq : Sequence {
- const Mask &mask;
- double true_value;
- double false_value;
- Mask2Seq(const Mask &mask_in, double true_value_in = 1.0, double false_value_in = 0.0)
- : mask(mask_in), true_value(true_value_in), false_value(false_value_in) {}
- double operator[](size_t i) const override { return mask[i] ? true_value : false_value; }
-};
-
-// custom op1
-struct MyOp {
- static double f(double a) {
- return ((a + 1) * 2);
- }
-};
-
-// 'a in [1,5,7,13,42]'
-struct MyIn {
- static double f(double a) {
- if ((a == 1) ||
- (a == 5) ||
- (a == 7) ||
- (a == 13) ||
- (a == 42))
- {
- return 1.0;
- } else {
- return 0.0;
- }
- }
-};
-
-// A collection of labels for a single dimension
-struct Domain {
- vespalib::string dimension;
- size_t size; // indexed
- std::vector<vespalib::string> keys; // mapped
- Domain(const Domain &);
- Domain(const vespalib::string &dimension_in, size_t size_in)
- : dimension(dimension_in), size(size_in), keys() {}
- Domain(const vespalib::string &dimension_in, const std::vector<vespalib::string> &keys_in)
- : dimension(dimension_in), size(0), keys(keys_in) {}
- ~Domain();
-};
-Domain::Domain(const Domain &) = default;
-Domain::~Domain() {}
-
-struct Layout {
- CellType cell_type;
- std::vector<Domain> domains;
- Layout(std::initializer_list<Domain> domains_in)
- : cell_type(CellType::DOUBLE), domains(domains_in) {}
- Layout(CellType cell_type_in, std::vector<Domain> domains_in)
- : cell_type(cell_type_in), domains(std::move(domains_in)) {}
- auto begin() const { return domains.begin(); }
- auto end() const { return domains.end(); }
- auto size() const { return domains.size(); }
- auto operator[](size_t idx) const { return domains[idx]; }
-};
+namespace vespalib::eval::test {
Layout float_cells(const Layout &layout) {
return Layout(CellType::FLOAT, layout.domains);
@@ -210,59 +35,6 @@ vespalib::string infer_type(const Layout &layout) {
return ValueType::tensor_type(dimensions, layout.cell_type).to_spec();
}
-// Wrapper for the things needed to generate a tensor
-struct Source {
- using Address = TensorSpec::Address;
-
- const Layout &layout;
- const Sequence &seq;
- const Mask &mask;
- Source(const Layout &layout_in, const Sequence &seq_in, const Mask &mask_in)
- : layout(layout_in), seq(seq_in), mask(mask_in) {}
-};
-
-// Mix layout with a number sequence to make a tensor spec
-class TensorSpecBuilder
-{
-private:
- using Label = TensorSpec::Label;
- using Address = TensorSpec::Address;
-
- Source _source;
- TensorSpec _spec;
- Address _addr;
- size_t _idx;
-
- void generate(size_t layout_idx) {
- if (layout_idx == _source.layout.size()) {
- if (_source.mask[_idx]) {
- _spec.add(_addr, _source.seq[_idx]);
- }
- ++_idx;
- } else {
- const Domain &domain = _source.layout[layout_idx];
- if (domain.size > 0) { // indexed
- for (size_t i = 0; i < domain.size; ++i) {
- _addr.emplace(domain.dimension, Label(i)).first->second = Label(i);
- generate(layout_idx + 1);
- }
- } else { // mapped
- for (const vespalib::string &key: domain.keys) {
- _addr.emplace(domain.dimension, Label(key)).first->second = Label(key);
- generate(layout_idx + 1);
- }
- }
- }
- }
-
-public:
- TensorSpecBuilder(const Layout &layout, const Sequence &seq, const Mask &mask)
- : _source(layout, seq, mask), _spec(infer_type(layout)), _addr(), _idx(0) {}
- TensorSpec build() {
- generate(0);
- return _spec;
- }
-};
TensorSpec spec(const Layout &layout, const Sequence &seq, const Mask &mask) {
return TensorSpecBuilder(layout, seq, mask).build();
}
@@ -302,6 +74,4 @@ TensorSpec spec(const vespalib::string &value_expr) {
return TensorSpec::from_expr(value_expr);
}
-} // namespace vespalib::eval::test
-} // namespace vespalib::eval
-} // namespace vespalib
+}