1 #ifndef CPPAD_CG_MODEL_C_SOURCE_GEN_FOR1_INCLUDED 2 #define CPPAD_CG_MODEL_C_SOURCE_GEN_FOR1_INCLUDED 24 determineJacobianSparsity();
27 std::map<size_t, std::vector<size_t> > elements;
28 for (
size_t e = 0; e < _jacSparsity.rows.size(); e++) {
29 elements[_jacSparsity.cols[e]].push_back(_jacSparsity.rows[e]);
32 if (!_loopTapes.empty()) {
36 prepareSparseForwardOneWithLoops(elements);
43 startingJob(
"'model (forward one)'", JobTimer::SOURCE_GENERATION);
45 if (isAtomicsUsed()) {
46 generateSparseForwardOneSourcesWithAtomics(elements);
48 generateSparseForwardOneSourcesNoAtomics(elements);
55 generateGlobalDirectionalFunctionSource(FUNCTION_SPARSE_FORWARD_ONE,
57 FUNCTION_FORWARD_ONE_SPARSITY,
68 size_t n = _fun.Domain();
72 const std::string jobName =
"model (forward one)";
73 startingJob(
"'" + jobName +
"'", JobTimer::SOURCE_GENERATION);
75 for (
const auto& it : elements) {
77 const std::vector<size_t>& rows = it.second;
80 _cache <<
"model (forward one, indep " << j <<
")";
81 const std::string subJobName = _cache.str();
83 startingJob(
"'" + subJobName +
"'", JobTimer::GRAPH);
86 handler.setJobTimer(_jobTimer);
91 for (
size_t i = 0; i < n; i++) {
92 indVars[i].setValue(_x[i]);
103 _fun.Forward(0, indVars);
107 CPPADCG_ASSERT_UNKNOWN(dy.size() == _fun.Range());
110 for (
size_t it2 : rows) {
111 dyCustom.push_back(dy[it2]);
121 _cache << _name <<
"_" << FUNCTION_SPARSE_FORWARD_ONE <<
"_indep" << j;
122 langC.setGenerateFunction(_cache.str());
124 std::ostringstream code;
125 std::unique_ptr<VariableNameGenerator<Base> > nameGen(createVariableNameGenerator(
"dy"));
128 handler.
generateCode(code, langC, dyCustom, nameGenHess, _atomicFunctions, subJobName);
139 size_t n = _fun.Domain();
142 handler.setJobTimer(_jobTimer);
147 for (
size_t i = 0; i < n; i++) {
148 x[i].setValue(_x[i]);
160 CppAD::sparse_jacobian_work work;
161 _fun.SparseJacobianForward(x, _jacSparsity.sparsity, _jacSparsity.rows, _jacSparsity.cols, jacFlat, work);
166 std::map<size_t, vector<CGBase> > jac;
167 std::map<size_t, std::map<size_t, size_t> > positions;
169 for (
const auto& it : elements) {
171 const std::vector<size_t>& column = it.second;
173 jac[j].resize(column.size());
174 std::map<size_t, size_t>& pos = positions[j];
176 for (
size_t e = 0; e < column.size(); e++) {
177 size_t i = column[e];
182 for (
size_t el = 0; el < _jacSparsity.rows.size(); el++) {
183 size_t i = _jacSparsity.rows[el];
184 size_t j = _jacSparsity.cols[el];
185 size_t e = positions[j].at(i);
188 column[e] = jacFlat[el] * dx;
194 typename std::map<size_t, vector<CGBase> >::iterator itJ;
195 for (itJ = jac.begin(); itJ != jac.end(); ++itJ) {
196 size_t j = itJ->first;
200 _cache <<
"model (forward one, indep " << j <<
")";
201 const std::string subJobName = _cache.str();
208 _cache << _name <<
"_" << FUNCTION_SPARSE_FORWARD_ONE <<
"_indep" << j;
209 langC.setGenerateFunction(_cache.str());
211 std::ostringstream code;
212 std::unique_ptr<VariableNameGenerator<Base> > nameGen(createVariableNameGenerator(
"dy"));
215 handler.
generateCode(code, langC, dyCustom, nameGenHess, _atomicFunctions, subJobName);
222 size_t m = _fun.Range();
223 size_t n = _fun.Domain();
226 _cache << _name <<
"_" << FUNCTION_FORWARD_ONE;
227 std::string model_function(_cache.str());
230 std::string argsDcl = langC.generateDefaultFunctionArgumentsDcl();
231 std::string args = langC.generateDefaultFunctionArguments();
234 _cache <<
"#include <stdlib.h>\n" 237 "int " << _name <<
"_" << FUNCTION_SPARSE_FORWARD_ONE <<
"(unsigned long pos, " << argsDcl <<
");\n" 238 "void " << _name <<
"_" << FUNCTION_FORWARD_ONE_SPARSITY <<
"(unsigned long pos, unsigned long const** elements, unsigned long* nnz);\n" 241 _baseTypeName +
" ty[]",
242 langC.generateArgumentAtomicDcl()});
244 " unsigned long ePos, ej, i, j, nnz, nnzMax;\n" 245 " unsigned long const* pos;\n" 246 " unsigned long* txPos;\n" 247 " unsigned long* txPosTmp;\n" 248 " unsigned long nnzTx;\n" 249 " " << _baseTypeName <<
" const * in[2];\n" 250 " " << _baseTypeName <<
"* out[1];\n" 251 " " << _baseTypeName <<
" x[" << n <<
"];\n" 252 " " << _baseTypeName <<
"* compressed;\n" 258 " for (j = 0; j < " << n <<
"; j++) {\n" 259 " if (tx[j * 2 + 1] != 0.0) {\n" 260 " " << _name <<
"_" << FUNCTION_FORWARD_ONE_SPARSITY <<
"(j, &pos, &nnz);\n" 261 " if (nnz > nnzMax)\n" 263 " else if (nnz == 0)\n" 266 " txPosTmp = (unsigned long*) realloc(txPos, nnzTx * sizeof(unsigned long));\n" 267 " if (txPosTmp != NULL) {\n" 268 " txPos = txPosTmp;\n" 271 " return -1; // failure to allocate memory\n" 273 " txPos[nnzTx - 1] = j;\n" 276 " for (i = 0; i < " << m <<
"; i++) {\n" 277 " ty[i * 2 + 1] = 0;\n" 280 " if (nnzTx == 0) {\n" 282 " return 0; //nothing to do\n" 285 " compressed = (" << _baseTypeName <<
"*) malloc(nnzMax * sizeof(" << _baseTypeName <<
"));\n" 287 " for (j = 0; j < " << n <<
"; j++)\n" 288 " x[j] = tx[j * 2];\n" 290 " for (ej = 0; ej < nnzTx; ej++) {\n" 292 " " << _name <<
"_" << FUNCTION_FORWARD_ONE_SPARSITY <<
"(j, &pos, &nnz);\n" 295 " in[1] = &tx[j * 2 + 1];\n" 296 " out[0] = compressed;\n";
297 if (!_loopTapes.empty()) {
298 _cache <<
" for(ePos = 0; ePos < nnz; ePos++)\n" 299 " compressed[ePos] = 0;\n" 302 _cache <<
" ret = " << _name <<
"_" << FUNCTION_SPARSE_FORWARD_ONE <<
"(j, " << args <<
");\n" 305 " free(compressed);\n" 310 " for (ePos = 0; ePos < nnz; ePos++) {\n" 311 " ty[pos[ePos] * 2 + 1] += compressed[ePos];\n" 315 " free(compressed);\n" 319 _sources[model_function +
".c"] = _cache.str();
virtual void generateSparseForwardOneSourcesNoAtomics(const std::map< size_t, std::vector< size_t > > &elements)
virtual void generateSparseForwardOneSources()
void setValue(const Base &val)
virtual void generateSparseForwardOneSourcesWithAtomics(const std::map< size_t, std::vector< size_t > > &elements)
void setMaxOperationsPerAssignment(size_t maxOperationsPerAssignment)
static void printFunctionDeclaration(std::ostringstream &out, const std::string &returnType, const std::string &functionName, const std::vector< std::string > &arguments, const std::vector< std::string > &arguments2={})
void makeVariables(VectorCG &variables)
virtual void setMaxAssignmentsPerFunction(size_t maxAssignmentsPerFunction, std::map< std::string, std::string > *sources)
void makeVariable(AD< CGB > &variable)
virtual void setParameterPrecision(size_t p)
virtual void generateCode(std::ostream &out, Language< Base > &lang, CppAD::vector< CGB > &dependent, VariableNameGenerator< Base > &nameGen, const std::string &jobName="source")