/* frees all internal stuff of cvodeData */ static void CvodeData_freeStructures(cvodeData_t * data) { int i; if(data == NULL){ return; } /* free sensitivity structure */ if ( data->p != NULL ) free(data->p); if ( data->sensitivity != NULL ) { for ( i=0; i<data->neq; i++ ) free(data->sensitivity[i]); free(data->sensitivity); } /* free results structure */ CvodeResults_free(data->results); /* free current values array */ free(data->value); /* free event trigger flags */ free(data->trigger); /* free ODEs */ for ( i=0; i<data->neq; i++ ) ASTNode_free(data->ode[i]); free(data->ode); }
END_TEST START_TEST(test_IntegratorInstance_createResults) { integratorInstance_t *ii; cvodeSettings_t *cs; int r; cvodeResults_t *cr; model = ODEModel_createFromFile(EXAMPLES_FILENAME("MAPK.xml")); cs = CvodeSettings_create(); ii = IntegratorInstance_create(model, cs); r = IntegratorInstance_integrate(ii); ck_assert_int_eq(r, 1); cr = IntegratorInstance_createResults(ii); ck_assert(ii->results != cr); CvodeResults_free(cr); CvodeSettings_free(cs); IntegratorInstance_free(ii); }
/* initialize cvodeData from cvodeSettings and odeModel (could be separated in to functions to further support modularity and independence of data structures */ int CvodeData_initialize(cvodeData_t *data, cvodeSettings_t *opt, odeModel_t *om) { int i, j; /* data now also depends on cvodeSettings */ data->opt = opt; /* initialize values */ CvodeData_initializeValues(data); /* set current time */ data->currenttime = opt->TimePoints[0]; /* update assigned parameters, in case they depend on new time */ for ( i=0; i<om->nass; i++ ) data->value[om->neq+i] = evaluateAST(om->assignment[i],data); /* Then, check if formulas can be evaluated, and cvodeData_t * contains all necessary variables: evaluateAST(ASTNode_t *f, ,data) will ask the user for a value, if a a variable is unknown */ for ( i=0; i<om->neq; i++ ) evaluateAST(om->ode[i], data); /* create structures for sensitivity analysis */ if ( opt->Sensitivity ) { /* the following can later be called with numbers from sensitivity Settings inputs */ if ( data->sensitivity == NULL ) { CvodeData_allocateSens(data, om->neq, om->nconst); RETURN_ON_FATALS_WITH(0); } /* (re)set to 0.0 initial value */ for ( i=0; i<om->neq; i++ ) { for ( j=0; j<om->nsens; j++ ) { data->sensitivity[i][j] = 0.0; } } } /* Now we should have all variables, and can allocate the results structure, where the time series will be stored ... */ /* allow results only for finite integrations */ opt->StoreResults = !opt->Indefinitely && opt->StoreResults; /* free former results */ if ( data->results != NULL ) CvodeResults_free(data->results); /* create new results if required */ if ( opt->StoreResults ) { data->results = CvodeResults_create(data, opt->PrintStep); RETURN_ON_FATALS_WITH(0); if ( opt->Sensitivity ) { CvodeResults_allocateSens(data->results, om->neq, om->nconst, opt->PrintStep); /* write initial values for sensitivity */ for ( i=0; i<data->results->neq; i++ ) for ( j=0; j<data->results->nsens; ++j ) data->results->sensitivity[i][j][0] = data->sensitivity[i][j]; } RETURN_ON_FATALS_WITH(0); } return 1; }
/*!!! TODO : clarify if this function can be called when the solver time is other than 0, and how it relates to CvodeData_initializeValues -> handling of initialAssignments !!!*/ int CvodeData_initialize(cvodeData_t *data, cvodeSettings_t *opt, odeModel_t *om, int keepValues) { int i; /* data now also depends on cvodeSettings */ data->opt = opt; /* if discrete data is used via settings */ if ( opt->observation_data_type == 1 ) om->discrete_observation_data=1; else om->discrete_observation_data=0; /* initialize values from odeModel */ if ( !keepValues ) CvodeData_initializeValues(data); /* reset steadystate flag */ data->steadystate = 0; /* set current time : WHEN NOT 0 ?? */ if ( opt->Indefinitely ) data->currenttime = 0; else data->currenttime = opt->TimePoints[0]; /* update assigned parameters, in case they depend on new time */ /* WHY ONLY IF TIME != 0 ?? */ if ( data->currenttime != 0.0 ) { for ( i=0; i< (om->nass); i++ ) { nonzeroElem_t *ordered = om->assignmentOrder[i]; data->value[ordered->i] = evaluateAST(ordered->ij, data); } data->allRulesUpdated = 1; } /* Then, check if formulas can be evaluated, and cvodeData_t * contains all necessary variables: evaluateAST(ASTNode_t *f, ,data) will ask the user for a value, if a a variable is unknown */ for ( i=0; i<om->neq; i++ ) evaluateAST(om->ode[i], data); /* evaluate event triggers and set flags with their initial state */ for ( i=0; i<data->nevents; i++ ) data->trigger[i] = evaluateAST(om->event[i], data); /* RESULTS: Now we should have all variables, and can allocate the results structure, where the time series will be stored ... */ /* free former results */ if ( data->results != NULL ) CvodeResults_free(data->results); /* allow results only for finite integrations */ /* this is the only place where options structure is changed internally! StoreResults is overruled by Indefinitely */ opt->StoreResults = !opt->Indefinitely && opt->StoreResults; /* create new results if required */ if ( opt->StoreResults ) { data->results = CvodeResults_create(data, opt->PrintStep); if ( data->results == NULL ) return 0; } return 1; }
int main (int argc, char *argv[]){ int i, j; odeModel_t *om; cvodeSettings_t *set; integratorInstance_t *ii; cvodeResults_t *results; variableIndex_t *y, *p; /* Setting SBML ODE Solver integration parameters */ set = CvodeSettings_create(); CvodeSettings_setTime(set, 300.0, 10); CvodeSettings_setErrors(set, 1e-9, 1e-4, 1e9); /* ACTIVATE SENSITIVITY ANALYSIS */ CvodeSettings_setSensitivity(set, 1); /* 0: simultaneous 1: staggered, 2: staggered1 see CVODES user guide for details */ CvodeSettings_setSensMethod(set, 0); CvodeSettings_setJacobian(set, 1); /* for testing only */ /* CvodeSettings_dump(set); */ /* creating the odeModel */ om = ODEModel_createFromFile("MAPK.xml"); /* get a parameter for which we will check sensitivities */ p = ODEModel_getVariableIndex(om, "K1"); /* calling the integrator */ ii = IntegratorInstance_create(om, set); printf("### Printing Sensitivities to %s (%g) on the fly:\n", ODEModel_getVariableName(om, p), IntegratorInstance_getVariableValue(ii, p)); printf("#time "); IntegratorInstance_dumpNames(ii); IntegratorInstance_dumpPSensitivities(ii, p); while( !IntegratorInstance_timeCourseCompleted(ii) ) { if ( !IntegratorInstance_integrateOneStep(ii) ) { break; } IntegratorInstance_dumpPSensitivities(ii, p); } VariableIndex_free(p); if ( SolverError_getNum(FATAL_ERROR_TYPE) ) { printf("Integration not sucessful!\n"); SolverError_dumpAndClearErrors(); return(EXIT_FAILURE); } y = ODEModel_getVariableIndex(om, "MAPK_P"); printf("\nLet's look at a specific ODE variable:\n"); /* print sensitivities again, but now from stored results */ printf("### RESULTS for Sensitivity Analysis for one ODE variable\n"); printf("#time Variable Sensitivity Params...\n"); printf("#time "); printf("%s ", ODEModel_getVariableName(om, y)); for ( j=0; j<ODEModel_getNsens(om); j++ ) { p = ODEModel_getSensParamIndexByNum(om, j); printf("%s ", ODEModel_getVariableName(om, p)); VariableIndex_free(p); } printf("\n"); results = IntegratorInstance_createResults(ii); for ( i=0; i<CvodeResults_getNout(results); i++ ) { printf("%g ", CvodeResults_getTime(results, i)); printf("%g ", CvodeResults_getValue(results, y, i)); for ( j=0; j<ODEModel_getNsens(om); j++ ) { p = ODEModel_getSensParamIndexByNum(om, j); printf("%g ", CvodeResults_getSensitivity(results, y, p, i)); VariableIndex_free(p); } printf("\n"); } /* drawSensitivity(ii->data, "sensitivity", "ps", 0.9); */ p = ODEModel_getVariableIndex(om, "V1"); printf("\nWhat do sensitivities mean? Let's try out!\n\n"); printf("... add 1 to %s: %g + 1 = ", ODEModel_getVariableName(om, p), IntegratorInstance_getVariableValue(ii, p)); CvodeSettings_setSensitivity(set, 0); IntegratorInstance_reset(ii); IntegratorInstance_setVariableValue(ii, p, IntegratorInstance_getVariableValue(ii,p)+1); printf("%g\n", IntegratorInstance_getVariableValue(ii, p)); printf("... and integrate again:\n\n"); CvodeResults_free(results); IntegratorInstance_integrate(ii); results = IntegratorInstance_createResults(ii); /* and print changed results */ printf("#time %s\n", ODEModel_getVariableName(om, y)); for ( i=0; i<CvodeResults_getNout(results); i++ ) { printf("%g ", CvodeResults_getTime(results, i)); printf("%g\n", CvodeResults_getValue(results, y, i)); } printf("\nSee the difference?\n"); printf("Look what happens when the sensitivity changes its sign\n"); printf("between times 180 and 210.\n\n"); VariableIndex_free(y); VariableIndex_free(p); /* now we have the results and can free the inputs */ IntegratorInstance_free(ii); CvodeSettings_free(set); CvodeResults_free(results); ODEModel_free(om); return (EXIT_SUCCESS); }