20#ifndef _NESTED_FUNCTION_H_
21#define _NESTED_FUNCTION_H_
23#include "mbsim/functions/function.h"
35 template<
typename Ret,
typename Arg>
48 int getArgSize()
const override {
return argDim; }
49 std::pair<int, int> getRetSize()
const override {
50 return fo1?fo1->getRetSize():fo2->getRetSize();
52 Ret operator()(
const Arg &arg)
override {
53 const double& a1 = arg(argIdx1);
56 const double& a2 = arg(argIdx2);
59 typename B::DRetDArg parDer(
const Arg &arg)
override {
61 const auto& v1 = fo1 ? fo1->parDer(arg(argIdx1)) : fo2->parDer1(arg(argIdx1),arg(argIdx2));
67 if constexpr (std::is_same_v<Ret, double>)
74 const auto& v2 = fo2->parDer2(arg(argIdx1),arg(argIdx2));
75 if constexpr (std::is_same_v<Ret, double>)
88 typename B::DRetDArg parDerDirDer(
const Arg &argDir,
const Arg &arg)
override {
89 const auto& v11 = fo1 ? fo1->parDerDirDer(argDir(argIdx1), arg(argIdx1)) :
90 fo2->parDer1DirDer1(argDir(argIdx1), arg(argIdx1),arg(argIdx2));
96 if constexpr (std::is_same_v<Ret, double>)
99 tmp.set(argIdx1, v11);
103 const auto& v22 = fo2->parDer2DirDer2(argDir(argIdx2), arg(argIdx1),arg(argIdx2));
104 const auto& v12 = fo2->parDer1DirDer2(argDir(argIdx2), arg(argIdx1),arg(argIdx2));
105 const auto& v21 = fo2->parDer2DirDer1(argDir(argIdx1), arg(argIdx1),arg(argIdx2));
106 if constexpr (std::is_same_v<Ret, double>)
108 tmp(argIdx1) = v11 + v12;
109 tmp(argIdx2) = v21 + v22;
113 tmp.set(argIdx1, v11 + v12);
114 tmp.set(argIdx2, v21 + v22);
119 void setArgumentIndex1(
size_t argIdx1_) { argIdx1 = argIdx1_; }
120 void setArgumentIndex2(
size_t argIdx2_) { argIdx2 = argIdx2_; }
121 void set1ArgFunction(
Function<Ret(
double)> *fo_) {
123 fo1->setParent(
this);
124 fo1->setName(
"OneArgumentFunction");
126 void set2ArgFunction(
Function<Ret(
double,
double)> *fo_) {
128 fo2->setParent(
this);
129 fo2->setName(
"TwoArgumentFunction");
131 void setArgDim(
size_t d) {
134 void initializeUsingXML(xercesc::DOMElement *element)
override {
135 if(MBXMLUtils::E(element)->hasAttribute(
"argDim"))
136 setArgDim(boost::lexical_cast<size_t>(MBXMLUtils::E(element)->getAttribute(
"argDim")));
137 xercesc::DOMElement *e=MBXMLUtils::E(element)->getFirstElementChildNamed(MBSIM%
"oneArgumentFunction");
140 e=MBXMLUtils::E(element)->getFirstElementChildNamed(MBSIM%
"twoArgumentFunction");
143 e=MBXMLUtils::E(element)->getFirstElementChildNamed(MBSIM%
"argumentIndex1");
145 setArgumentIndex1(MBXMLUtils::E(e)->getText<size_t>()-1);
146 e=MBXMLUtils::E(element)->getFirstElementChildNamed(MBSIM%
"argumentIndex2");
148 setArgumentIndex2(MBXMLUtils::E(e)->getText<size_t>()-1);
151 Function<Ret(Arg)>::init(stage, config);
152 if(fo1) fo1->init(stage, config);
153 if(fo2) fo2->init(stage, config);
156 Function<Ret(
double)> *fo1{
nullptr};
157 Function<Ret(
double,
double)> *fo2{
nullptr};
159 size_t argIdx1 { 0 };
160 size_t argIdx2 { 0 };
161 typename B::DRetDArg tmp;
162 void initTmp(
const typename std::remove_pointer_t<
decltype(fo1)>::DRetDArg &s1,
const Arg &s2) {
164 if(tmp.rows() == 0 || tmp.cols() == 0)
166 if constexpr (std::is_same_v<Ret, double>)
167 tmp.resize( s2.rows());
169 tmp.resize(s1.rows() , s2.rows());
void init(Element::InitStage stage, const InitConfigSet &config) override
plots time series header
Definition: demuxing_argument_function.h:150
Definition: demuxing_argument_function.h:27
InitStage
The stages of the initialization.
Definition: element.h:63
Definition: function.h:53
static ContainerType * createAndInit(const xercesc::DOMElement *element)
Definition: objectfactory.h:103
namespace MBSim
Definition: bilateral_constraint.cc:30