46 #include <Xyce_config.h>
56 #include <N_LAS_Vector.h>
57 #include <N_LAS_Matrix.h>
72 std::vector<std::string> & currentEqus, std::vector<std::string> & indepVars, std::vector<std::string> & fEqs,
73 std::vector<std::string> & qEqs, std::vector<std::string> & extraFunctions, std::vector<std::string> & extraParameters) :
78 currentEqus_(currentEqus),
79 indepVars_(indepVars),
82 extraFunctions_(extraFunctions),
83 extraParameters_(extraParameters)
111 std::vector< std::vector< int > > & segmentJacStamp )
132 std::map<std::string,int>::iterator currVarOffset =
indepVarOffset_.begin();
133 std::map<std::string,int>::iterator endVarOffset =
indepVarOffset_.end();
135 while( currVarOffset != endVarOffset )
137 std::set<std::string> depVarNames;
139 if( currVarOffset->first ==
"V" )
170 std::set<std::string>::iterator depVarNamesEnd = depVarNames.end();
172 std::map< std::string, int > tmpIndVarMap;
174 for(
int i=0; i<numEnteries; i++)
180 Xyce::dout() <<
"Assigned tmpIndVarMap[ " << offsetToIndepVar_[i] <<
" ]= " << (numFound-1) << std::endl;
185 Xyce::dout() <<
"tmpIndVarMap assigned to variable " << currVarOffset->first << std::endl;
193 if( currVarOffset->first !=
"V" )
195 segmentJacStamp[offset + currVarOffset->second ].resize( numvars );
199 std::set<std::string>::iterator depVarNamesCurr = depVarNames.begin();
200 while( depVarNamesCurr != depVarNamesEnd )
202 if( currVarOffset->first ==
"V" )
204 segmentJacStamp[offset + currVarOffset->second ][ vOffset+
systemJacOffset_[currVarOffset->second ][*depVarNamesCurr ]] = offset +
indepVarOffset_[*depVarNamesCurr];
208 segmentJacStamp[offset + currVarOffset->second ][
systemJacOffset_[currVarOffset->second ][*depVarNamesCurr ]] = offset +
indepVarOffset_[*depVarNamesCurr];
217 Xyce::dout() <<
"MembraneUserDefined::setJacStamp() jacStamp = " << std::endl;
218 for(
int i = 0; i<segmentJacStamp.size(); ++i )
220 Xyce::dout() <<
"jacStamp[ " << i <<
" ] = { ";
221 for(
int j=0; j<segmentJacStamp[i].size(); ++j)
223 Xyce::dout() << segmentJacStamp[i][j];
224 if( j != ( segmentJacStamp[i].size() -1 ) )
226 Xyce::dout() <<
", ";
229 Xyce::dout() <<
" }" << std::endl;
231 Xyce::dout() << Xyce::section_divider << std::endl;
233 Xyce::dout() <<
"MembraneUserDefined::setJacStamp() systemJacOffset_ = " << std::endl;
236 Xyce::dout() <<
"systemJacOffset[ " << i <<
" ] = { ";
237 std::map<std::string,int>::iterator currVarOffset =
systemJacOffset_[i].begin();
238 std::map<std::string,int>::iterator endVarOffset =
systemJacOffset_[i].end();
239 while( currVarOffset != endVarOffset )
241 Xyce::dout() << currVarOffset->first <<
", " << currVarOffset->second << std::endl;
244 Xyce::dout() <<
" }" << std::endl;
246 Xyce::dout() << Xyce::section_divider << std::endl;
261 std::vector< int > & lidIndexVector,
262 Linear::Vector * solnVecPtr,
263 Linear::Vector * daeQVecPtr,
269 (*daeQVecPtr)[lidIndexVector[index]] +=
cMem_ * segArea * (*solnVecPtr)[lidIndexVector[index]];
271 Xyce::dout() <<
"loadDAEQVector: entry for index " << index <<
" : " <<
cMem_ * segArea * (*solnVecPtr)[lidIndexVector[index]] << std::endl;
275 for(
int i=0; i<numExp; i++)
279 for(
int j=0; j<numvars; j++)
284 double resultValue=0.0;
291 int lidIndexVectorIndex = index + i + 1;
292 (*daeQVecPtr)[lidIndexVector[lidIndexVectorIndex]] += resultValue;
293 Xyce::dout() <<
"loadDAEQVector: entry for LID index " << lidIndexVectorIndex
294 <<
", varname " <<
offsetToIndepVar_[lidIndexVectorIndex-index] <<
" : " << resultValue << std::endl;
309 std::vector< int > & lidIndexVector,
310 Linear::Vector * solnVecPtr,
311 Linear::Vector * daeFVecPtr,
314 Xyce::dout() <<
"loadDAEFVector" << std::endl;
319 (*daeFVecPtr)[lidIndexVector[index]] +=
gMem_ * segArea * ((*solnVecPtr)[lidIndexVector[index]] -
vRest_ );
326 for(
int i=0; i<numCurrentExp; i++)
328 Xyce::dout() <<
"membrane V equation contribution from current equation # " << i << std::endl;
331 for(
int j=0; j<numvars; j++)
334 Xyce::dout() <<
"Segment " << segmentNumber <<
" current load variable = " << currentEqusVarNames_[i][j] <<
" value = " <<
currentEqusVarValues_[i][j] << std::endl;
337 double resultValue=0.0;
339 Xyce::dout() <<
"Segment " << segmentNumber <<
" current equ F = " << resultValue << std::endl;
343 (*daeFVecPtr)[lidIndexVector[index]] += segArea*resultValue;
348 for(
int i=0; i<numExp; i++)
350 Xyce::dout() <<
"F terms from f equation # " << i << std::endl;
353 for(
int j=0; j<numvars; j++)
356 Xyce::dout() <<
"Segment " << segmentNumber <<
" extra var load variable = " << fEqsEqusVarNames_[i][j] <<
" value = " <<
fEqsEqusVarValues_[i][j] << std::endl;
359 double resultValue=0.0;
364 int lidIndexVectorIndex = index + i + 1;
365 (*daeFVecPtr)[lidIndexVector[lidIndexVectorIndex]] += resultValue;
366 Xyce::dout() <<
"Segment " << segmentNumber <<
" LID index " << lidIndexVectorIndex
367 <<
", extra vars equ F = " << resultValue << std::endl;
381 std::vector< int > & lidIndexVector,
382 std::vector< std::vector< int > > & jacobianOffsets,
383 Linear::Vector * solnVecPtr,
384 Linear::Matrix * dQdxMatPtr,
387 Xyce::dout() <<
"loadDAEdQdx" << std::endl;
401 (*dQdxMatPtr)[lidIndexVector[index]][jacobianOffsets[row][vOffset]] +=
cMem_ * segArea;
408 for(
int i=0; i<numExp; i++)
411 Xyce::dout() <<
"Q terms for q equation " << i <<
"; assumed to be for variable " << targetVarName << std::endl;
414 for(
int j=0; j<numvars; j++)
417 Xyce::dout() <<
"contribution from " << qEqsEqusVarNames_[i][j] <<
": " <<
qEqsEqusVarValues_[i][j] << std::endl;
420 double resultValue=0.0;
421 std::vector<double> derivValues;
422 derivValues.resize( numvars );
424 Xyce::dout() <<
"expression result: " << resultValue << std::endl;
427 for(
int j=0; j<numvars; j++)
430 Xyce::dout() <<
"contribution of variable " << j <<
"(" << varName <<
")" << std::endl;
432 int targetVarIndex = index + targetVarOffset;
433 int targetVarRow = row + targetVarOffset;
435 Xyce::dout() <<
"targerVarOffset: " << targetVarOffset <<
", targetVarIndex: " << targetVarIndex
436 <<
", jacobianRow: " << targetVarRow <<
", jacobianCol: " << jacOffsetsCol << std::endl;
437 (*dQdxMatPtr)[lidIndexVector[targetVarIndex]][jacobianOffsets[targetVarRow][jacOffsetsCol]] += derivValues[j];
438 Xyce::dout() <<
"adding (*dQdxMatPtr)[ " << lidIndexVector[targetVarIndex] <<
" ][ " << jacobianOffsets[targetVarRow][jacOffsetsCol] <<
" ] = " << derivValues[j] << std::endl;
452 std::vector< int > & lidIndexVector,
453 std::vector< std::vector< int > > & jacobianOffsets,
454 Linear::Vector * solnVecPtr,
455 Linear::Matrix * dFdxMatPtr,
458 Xyce::dout() <<
"loadDAEdFdx" << std::endl;
472 (*dFdxMatPtr)[lidIndexVector[index]][jacobianOffsets[row][vOffset]] +=
gMem_ * segArea;
473 Xyce::dout() <<
"leak current dFdx: " <<
"vOffset = " << vOffset <<
" row = " << row << std::endl;
474 Xyce::dout() <<
"adding (*dFdxMatPtr)[ " << lidIndexVector[index] <<
" ][ " << jacobianOffsets[row][vOffset ] <<
" ] = " <<
gMem_ * segArea << std::endl;
478 for(
int i=0; i<numCurrentEq; i++)
482 for(
int j=0; j<numvars; j++)
487 double resultValue=0.0;
488 std::vector<double> derivValues;
489 derivValues.resize( numvars );
494 for(
int j=0; j<numvars; j++)
497 Xyce::dout() <<
"contribution of variable " << j <<
"(" << varName <<
") to V" << std::endl;
501 Xyce::dout() <<
" jacOffsetsRow: " << row <<
" jacOffsetsCol: " << jacOffsetsCol << std::endl;
503 (*dFdxMatPtr)[lidIndexVector[index]][ jacobianOffsets[row][jacOffsetsCol] ] += segArea*derivValues[j];
504 Xyce::dout() <<
"adding (*dFdxMatPtr)[ " << lidIndexVector[index] <<
" ][ " << jacobianOffsets[row][jacOffsetsCol] <<
" ] = " << segArea*derivValues[j] << std::endl;
510 for(
int i=0; i<numExp; i++)
513 Xyce::dout() <<
"F terms for f equation " << i <<
"; assumed to be for variable " << targetVarName << std::endl;
516 for(
int j=0; j<numvars; j++)
521 double resultValue=0.0;
522 std::vector<double> derivValues;
523 derivValues.resize( numvars );
527 for(
int j=0; j<numvars; j++)
530 Xyce::dout() <<
"contribution of variable " << j <<
"(" << varName <<
")" << std::endl;
532 int targetVarIndex = index + targetVarOffset;
533 int targetVarRow = row + targetVarOffset;
535 Xyce::dout() <<
"targetVarOffset: " << targetVarOffset <<
" targetVarIndex: " << targetVarIndex
536 <<
", jacOffsetsRow: " << targetVarRow <<
" jacOffsetsCol: " << jacOffsetsCol << std::endl;
537 (*dFdxMatPtr)[lidIndexVector[targetVarIndex]][ jacobianOffsets[targetVarRow][jacOffsetsCol] ] += derivValues[j];
538 Xyce::dout() <<
"Adding (*dFdxMatPtr)[ " << lidIndexVector[targetVarIndex] <<
" ][ " << jacobianOffsets[targetVarRow][jacOffsetsCol] <<
" ] = " << derivValues[j] << std::endl;
553 int numStrings = stringInput.size();
554 for(
int i=0; i<numStrings; i++ )
557 expRCPOut.push_back( rcp(
new Util::Expression( stringInput.at(i) ) ) );
587 for(
int i=0; i<numParams; i+=2)
589 std::vector<std::string> names;
592 if( names.size() > 1 )
594 Xyce::dout() <<
"Warning MembraneUserDefined::consolidateExpressions() parameter name vec longer than expected." << names.size() << std::endl;
604 for(
int i=0; i<numFuncs; i+=2 )
606 std::vector<std::string> names;
645 Xyce::dout() <<
"Currentequ = " <<
currentEqusExpRCP_.at(i)->get_expression() << std::endl;
650 Xyce::dout() <<
"F: " <<
fEqsExpRCP_.at(i)->get_expression() <<
" Q: " <<
qEqsExpRCP_.at(i)->get_expression() << std::endl;
651 double fval=0, qval=0;
652 std::vector<double> fargs, qargs;
653 fargs.push_back(0.2); fargs.push_back(-0.015); qargs.push_back(0.2);
656 Xyce::dout() <<
"F(V=-0.015,n/m/h=0.2) = " << fval <<
" Q(V=-0.015,n/m/h=0.2) = " << qval << std::endl;
676 for(
int i=0; i<numParams; i++)
678 int numExp = expRCP_.size();
679 for(
int j=0; j<numExp; j++ )
698 for(
int i=0; i<numFuncs; i++)
700 int numExp = expRCP_.size();
701 for(
int j=0; j<numExp; j++ )
727 for(
int i=0; i<numIndependentVars; i++ )
729 std::vector<std::string> expNames;
731 int numExpNames=expNames.size();
732 for(
int j=0; j<numExpNames; j++ )
734 Xyce::dout() <<
"makeSymbolSet, i=" <<i <<
", j="<<j <<
": adding " << expNames.at(j) <<
" to userDefinedNames" << std::endl;
751 while( currName != endName )
765 Xyce::dout() <<
"MembraneUserDefined::makeSymbolSet() Independent var offset map : " << std::endl;
766 std::map<std::string,int>::iterator currVarOffset =
indepVarOffset_.begin();
767 std::map<std::string,int>::iterator endVarOffset =
indepVarOffset_.end();
768 while( currVarOffset != endVarOffset )
770 Xyce::dout() <<
"map[ " << currVarOffset->first <<
" ] = " << currVarOffset->second << std::endl;
775 while( currOffset != endOffset )
777 Xyce::dout() <<
"inv-map[ " << currOffset->first <<
" ] = " << currOffset->second << std::endl;
798 int numExp = expRCP.size();
801 expNamesVec.resize( numExp );
802 expValsVec.resize( numExp );
804 for(
int i=0; i<numExp; i++ )
807 std::vector<std::string> expNamesTmp;
808 expRCP.at(i)->get_names( type, expNamesTmp );
809 int numExpNames=expNamesTmp.size();
810 for(
int j=0; j<numExpNames; j++ )
816 if( findResult != endName )
819 expRCP.at(i)->make_var( expNamesTmp.at(j) );
821 expNamesVec[i].push_back( expNamesTmp.at(j) );
825 Xyce::dout() <<
"Warning symbol \"" << expNamesTmp.at(j) <<
"\" not listed in independent variables. Ignoring for now." << std::endl;
829 expValsVec[i].resize( expNamesVec[i].size() );
831 Xyce::dout() <<
"MembraneUserDefined::convertSymbolsToVars: expression " << expRCP.at(i)->get_expression() <<
" Has vars: ";
832 std::vector<std::string>::iterator cni = expNamesVec[i].begin();
833 std::vector<std::string>::iterator eni = expNamesVec[i].end();
836 Xyce::dout() << *cni <<
", ";
839 Xyce::dout() << std::endl;
std::vector< std::vector< std::string > > currentEqusVarNames_
std::vector< std::vector< double > > currentEqusVarValues_
std::vector< std::string > extraParameters_
std::vector< std::string > fEqs_
std::map< int, std::string > offsetToIndepVar_
std::vector< std::vector< std::string > > qEqsEqusVarNames_
Pure virtual class to augment a linear system.
void substituteParameters(std::vector< RCP< Util::Expression > > &expRCP_)
void convertSymbolsToVars(std::vector< RCP< Util::Expression > > &expRCP_, std::vector< std::vector< std::string > > &expNames, std::vector< std::vector< double > > &expValsVec)
std::vector< std::vector< double > > fEqsEqusVarValues_
std::vector< RCP< Util::Expression > > extraFunctionsExpRCP_
std::vector< RCP< Util::Expression > > currentEqusExpRCP_
std::vector< RCP< Util::Expression > > qEqsExpRCP_
std::vector< std::vector< double > > qEqsEqusVarValues_
void loadDAEdQdx(int segmentNumber, int vOffset, std::vector< int > &lidIndexVector, std::vector< std::vector< int > > &jacobianOffsets, Linear::Vector *solnVecPtr, Linear::Matrix *dQdxMatPtr, double segArea)
std::vector< int > funcNumArgs_
const T & value(const ParameterBase &entity, const Descriptor &descriptor)
Returns the value of the parameter for the entity.
const int numExternalVars_
std::vector< RCP< Util::Expression > > fEqsExpRCP_
void loadDAEFVector(int segmentNumber, std::vector< int > &lidIndexVector, Linear::Vector *solnVecPtr, Linear::Vector *daeFVecPtr, double segArea)
std::vector< RCP< Util::Expression > > indepVarsExpRCP_
MembraneUserDefined(const SolverState &ss1, double cMem, double gMem, double vRest, std::vector< std::string > ¤tEqus, std::vector< std::string > &indepVars, std::vector< std::string > &fEqs, std::vector< std::string > &qEqs, std::vector< std::string > &extraFunctions, std::vector< std::string > &extraParameters)
std::vector< std::string > indepVars_
std::vector< RCP< Util::Expression > > funcExpRCP_
std::vector< std::string > extraFunctions_
void convertStringsToExpression(std::vector< std::string > &stringInput, std::vector< RCP< Util::Expression > > &expRCPOut)
void loadDAEQVector(int segmentNumber, std::vector< int > &lidIndexVector, Linear::Vector *solnVecPtr, Linear::Vector *daeQVecPtr, double segArea)
std::vector< std::vector< std::string > > fEqsEqusVarNames_
std::vector< std::string > paramNames_
void loadDAEdFdx(int segmentNumber, int vOffset, std::vector< int > &lidIndexVector, std::vector< std::vector< int > > &jacobianOffsets, Linear::Vector *solnVecPtr, Linear::Matrix *dFdxMatPtr, double segArea)
std::vector< std::string > funcNames_
std::vector< double > paramValues_
std::vector< std::map< std::string, int > > systemJacOffset_
std::vector< std::string > userDefinedNames_
std::vector< RCP< Util::Expression > > extraParametersExpRCP_
std::vector< std::string > qEqs_
std::vector< std::string > currentEqus_
void substituteFunctions(std::vector< RCP< Util::Expression > > &expRCP_)
void setJacStamp(int numExtVars, int segmentNumber, int vOffset, std::vector< std::vector< int > > &segmentJacStamp)
void consolidateExpressions()
std::map< std::string, int > indepVarOffset_