16 std::vector<MatrixXd>&& mm):
24 "VectorSource: no source vector defined at " + std::to_string(
index));
31 "VectorSource: no source matrix defined at " + std::to_string(
index));
37 const std::vector<std::pair<size_t,size_t> >& ma):
45 "Dummy Source: no size defined at " + std::to_string(
index));
48 VectorXd
vec(n_entries);
49 for (
size_t iii = 0; iii < n_entries; iii++) {
57 "Dummy Source: no size defined at " + std::to_string(
index));
61 MatrixXd mat(n_rows, n_cols);
62 for (
size_t iii = 0; iii < n_rows; iii++) {
63 for (
size_t jjj = 0; jjj < n_cols; jjj++) {
64 mat(iii, jjj) = jjj + n_cols * iii;
78 VectorXd output = source.at(
m_index);
79 assert(output.rows() > 0);
80 if (
static_cast<size_t>(output.rows()) !=
m_n_outputs) {
81 std::string len = std::to_string(output.rows());
84 "Found vector of length " + len +
", expected " + found);
108 for (
const auto source: sources) {
116 VectorXd input =
node->compute(source);
117 size_t n_elements = input.rows();
118 assert(n_elements ==
node->n_outputs());
119 output.segment(offset, n_elements) = input;
120 offset += n_elements;
136 MatrixXd output = source.matrix_at(
m_index);
137 if (output.rows() == 0) {
140 if (
static_cast<size_t>(output.rows()) !=
m_n_outputs) {
141 std::string len = std::to_string(output.rows());
144 "Found vector of length " + len +
", expected " + found);
162 MatrixXd mat =
scan(src);
163 size_t n_cols = mat.cols();
166 return MatrixXd::Zero(mat.rows(), 1);
168 return mat.col(n_cols - 1);
181 MatrixXd input =
m_source->scan(source);
182 MatrixXd output(
m_stack->n_outputs(), input.cols());
183 size_t n_columns = input.cols();
184 for (
size_t col_n = 0; col_n < n_columns; col_n++) {
185 output.col(col_n) =
m_stack->compute(input.col(col_n));
198 return m_source->scan(source).rowwise().sum();
208 void throw_cfg(
const std::string &
msg,
size_t index) {
212 size_t n_source =
node.sources.size();
213 if (n_source != 1) throw_cfg(
"need one source, found", n_source);
214 int layer_n =
node.index;
215 if (layer_n < 0) throw_cfg(
"negative layer number", layer_n);
217 void check_compute_node(
const NodeConfig&
node,
size_t n_layers) {
218 check_compute_node(
node);
219 int layer_n =
node.index;
220 if (
static_cast<size_t>(layer_n) >= n_layers) {
221 throw_cfg(
"no layer number", layer_n);
225 INode* get_feedforward_node(
227 const std::vector<LayerConfig>& layers,
228 const std::unordered_map<size_t, INode*>& node_map,
229 std::unordered_map<size_t, Stack*>& stack_map) {
234 int layer_n =
node.index;
235 if (!stack_map.count(layer_n)) {
236 stack_map[layer_n] =
new Stack(
source->n_outputs(),
237 {layers.at(layer_n)});
243 const std::vector<LayerConfig>& layers,
244 const std::unordered_map<size_t, ISequenceNode*>& node_map,
245 std::unordered_map<size_t, RecurrentStack*>& stack_map) {
249 int layer_n =
node.index;
250 if (!stack_map.count(layer_n)) {
252 {layers.at(layer_n)});
258 const std::vector<LayerConfig>& layers,
259 const std::unordered_map<size_t, ISequenceNode*>& node_map,
260 std::unordered_map<size_t, Stack*>& stack_map) {
265 int layer_n =
node.index;
266 if (!stack_map.count(layer_n)) {
267 stack_map[layer_n] =
new Stack(
source->n_outputs(),
268 {layers.at(layer_n)});
286 const std::vector<LayerConfig>& layers):
289 for (
size_t iii = 0; iii < nodes.size(); iii++) {
297 node.second =
nullptr;
304 node.second =
nullptr;
308 stack.second =
nullptr;
312 stack.second =
nullptr;
316 if (!
m_nodes.count(node_number)) {
317 auto num = std::to_string(node_number);
320 "Graph: output at " + num +
" not feed forward");
324 return m_nodes.at(node_number)->compute(source);
334 auto num = std::to_string(node_number);
335 if (
m_nodes.count(node_number)) {
337 "Graph: output at " + num +
" not a sequence");
354 const std::vector<NodeConfig>& nodes,
355 const std::vector<LayerConfig>& layers,
356 std::set<size_t> cycle_check) {
364 if (iii >= nodes.size()) throw_cfg(
"no node index", iii);
369 if (
node.
type == NodeConfig::Type::INPUT) {
370 check_compute_node(
node);
371 size_t input_number =
node.sources.at(0);
374 }
else if (
node.
type == NodeConfig::Type::INPUT_SEQUENCE) {
375 check_compute_node(
node);
376 size_t input_number =
node.sources.at(0);
382 if (cycle_check.count(iii)) {
385 cycle_check.insert(iii);
386 for (
size_t source_node:
node.sources) {
387 build_node(source_node, nodes, layers, cycle_check);
391 if (
node.
type == NodeConfig::Type::FEED_FORWARD) {
394 }
else if (
node.
type == NodeConfig::Type::TIME_DISTRIBUTED) {
397 }
else if (
node.
type == NodeConfig::Type::SEQUENCE) {
403 }
else if (
node.
type == NodeConfig::Type::CONCATENATE) {
405 std::vector<const INode*> in_nodes;
406 for (
size_t source_node:
node.sources) {
407 in_nodes.push_back(
m_nodes.at(source_node));
410 }
else if (
node.
type == NodeConfig::Type::SUM) {
411 if (
node.sources.size() != 1) {
std::vector< size_t > vec
std::vector< const INode * > m_sources
ConcatenateNode(const std::vector< const INode * > &)
virtual size_t n_outputs() const override
virtual VectorXd compute(const ISource &) const override
std::vector< std::pair< size_t, size_t > > m_matrix_sizes
std::vector< size_t > m_sizes
virtual VectorXd at(size_t index) const override
virtual MatrixXd matrix_at(size_t index) const override
DummySource(const std::vector< size_t > &input_sizes, const std::vector< std::pair< size_t, size_t > > &={})
virtual size_t n_outputs() const override
FeedForwardNode(const Stack *, const INode *source)
virtual VectorXd compute(const ISource &) const override
std::unordered_map< size_t, INode * > m_nodes
std::unordered_map< size_t, RecurrentStack * > m_seq_stacks
std::unordered_map< size_t, ISequenceNode * > m_seq_nodes
MatrixXd scan(const ISource &, size_t node_number) const
std::unordered_map< size_t, Stack * > m_stacks
void build_node(const size_t, const std::vector< NodeConfig > &nodes, const std::vector< LayerConfig > &layers, std::set< size_t > cycle_check={})
VectorXd compute(const ISource &, size_t node_number) const
virtual MatrixXd scan(const ISource &) const override
const RecurrentStack * m_stack
SequenceNode(const RecurrentStack *, const ISequenceNode *source)
virtual size_t n_outputs() const override
virtual VectorXd compute(const ISource &) const override
const ISequenceNode * m_source
virtual size_t n_outputs() const override
SumNode(const ISequenceNode *source)
virtual VectorXd compute(const ISource &) const override
const ISequenceNode * m_source
const ISequenceNode * m_source
virtual MatrixXd scan(const ISource &) const override
TimeDistributedNode(const Stack *, const ISequenceNode *source)
virtual size_t n_outputs() const override
VectorSource(std::vector< VectorXd > &&, std::vector< MatrixXd > &&={})
virtual VectorXd at(size_t index) const override
virtual MatrixXd matrix_at(size_t index) const override
std::vector< VectorXd > m_inputs
std::vector< MatrixXd > m_matrix_inputs
layers(flags, cells_name, *args, **kw)
Here we define wrapper functions to set up all of the standard corrections.