00001
00002
00003
00004
00005
00006
00007 #include "Albany_AggregateScalarResponseFunction.hpp"
00008 #include "Epetra_LocalMap.h"
00009
00010 using Teuchos::RCP;
00011 using Teuchos::rcp;
00012
00013 Albany::AggregateScalarResponseFunction::
00014 AggregateScalarResponseFunction(
00015 const Teuchos::RCP<const Epetra_Comm>& comm,
00016 const Teuchos::Array< Teuchos::RCP<ScalarResponseFunction> >& responses_) :
00017 SamplingBasedScalarResponseFunction(comm),
00018 responses(responses_)
00019 {
00020 }
00021
00022 void
00023 Albany::AggregateScalarResponseFunction::
00024 setup()
00025 {
00026 typedef Teuchos::Array<Teuchos::RCP<ScalarResponseFunction> > ResponseArray;
00027 for (ResponseArray::iterator it = responses.begin(), it_end = responses.end(); it != it_end; ++it) {
00028 (*it)->setup();
00029 }
00030 }
00031
00032 Albany::AggregateScalarResponseFunction::
00033 ~AggregateScalarResponseFunction()
00034 {
00035 }
00036
00037 unsigned int
00038 Albany::AggregateScalarResponseFunction::
00039 numResponses() const
00040 {
00041 unsigned int n = 0;
00042 for (int i=0; i<responses.size(); i++)
00043 n += responses[i]->numResponses();
00044 return n;
00045 }
00046
00047 void
00048 Albany::AggregateScalarResponseFunction::
00049 evaluateResponse(const double current_time,
00050 const Epetra_Vector* xdot,
00051 const Epetra_Vector* xdotdot,
00052 const Epetra_Vector& x,
00053 const Teuchos::Array<ParamVec>& p,
00054 Epetra_Vector& g)
00055 {
00056 unsigned int offset = 0;
00057 for (unsigned int i=0; i<responses.size(); i++) {
00058
00059
00060 int num_responses = responses[i]->numResponses();
00061 Epetra_LocalMap local_response_map(num_responses, 0,
00062 *(responses[i]->getComm()));
00063
00064
00065 Epetra_Vector local_g(local_response_map);
00066
00067
00068 responses[i]->evaluateResponse(current_time, xdot, xdotdot, x, p, local_g);
00069
00070
00071 for (unsigned int j=0; j<num_responses; j++)
00072 g[offset+j] = local_g[j];
00073
00074
00075 offset += num_responses;
00076 }
00077 }
00078
00079 void
00080 Albany::AggregateScalarResponseFunction::
00081 evaluateTangent(const double alpha,
00082 const double beta,
00083 const double omega,
00084 const double current_time,
00085 bool sum_derivs,
00086 const Epetra_Vector* xdot,
00087 const Epetra_Vector* xdotdot,
00088 const Epetra_Vector& x,
00089 const Teuchos::Array<ParamVec>& p,
00090 ParamVec* deriv_p,
00091 const Epetra_MultiVector* Vxdot,
00092 const Epetra_MultiVector* Vxdotdot,
00093 const Epetra_MultiVector* Vx,
00094 const Epetra_MultiVector* Vp,
00095 Epetra_Vector* g,
00096 Epetra_MultiVector* gx,
00097 Epetra_MultiVector* gp)
00098 {
00099 unsigned int offset = 0;
00100 for (unsigned int i=0; i<responses.size(); i++) {
00101
00102
00103 int num_responses = responses[i]->numResponses();
00104 Epetra_LocalMap local_response_map(num_responses, 0,
00105 *(responses[i]->getComm()));
00106
00107
00108 RCP<Epetra_Vector> local_g;
00109 RCP<Epetra_MultiVector> local_gx, local_gp;
00110 if (g != NULL)
00111 local_g = rcp(new Epetra_Vector(local_response_map));
00112 if (gx != NULL)
00113 local_gx = rcp(new Epetra_MultiVector(local_response_map,
00114 gx->NumVectors()));
00115 if (gp != NULL)
00116 local_gp = rcp(new Epetra_MultiVector(local_response_map,
00117 gp->NumVectors()));
00118
00119
00120 responses[i]->evaluateTangent(alpha, beta, omega, current_time, sum_derivs,
00121 xdot, xdotdot, x, p, deriv_p, Vxdot, Vxdotdot, Vx, Vp,
00122 local_g.get(), local_gx.get(),
00123 local_gp.get());
00124
00125
00126 for (unsigned int j=0; j<num_responses; j++) {
00127 if (g != NULL)
00128 (*g)[offset+j] = (*local_g)[j];
00129 if (gx != NULL)
00130 for (int k=0; k<gx->NumVectors(); k++)
00131 (*gx)[k][offset+j] = (*local_gx)[k][j];
00132 if (gp != NULL)
00133 for (int k=0; k<gp->NumVectors(); k++)
00134 (*gp)[k][offset+j] = (*local_gp)[k][j];
00135 }
00136
00137
00138 offset += num_responses;
00139 }
00140 }
00141
00142 void
00143 Albany::AggregateScalarResponseFunction::
00144 evaluateGradient(const double current_time,
00145 const Epetra_Vector* xdot,
00146 const Epetra_Vector* xdotdot,
00147 const Epetra_Vector& x,
00148 const Teuchos::Array<ParamVec>& p,
00149 ParamVec* deriv_p,
00150 Epetra_Vector* g,
00151 Epetra_MultiVector* dg_dx,
00152 Epetra_MultiVector* dg_dxdot,
00153 Epetra_MultiVector* dg_dxdotdot,
00154 Epetra_MultiVector* dg_dp)
00155 {
00156 unsigned int offset = 0;
00157 for (unsigned int i=0; i<responses.size(); i++) {
00158
00159
00160 int num_responses = responses[i]->numResponses();
00161 Epetra_LocalMap local_response_map(num_responses, 0,
00162 *(responses[i]->getComm()));
00163
00164
00165 RCP<Epetra_Vector> local_g;
00166 if (g != NULL)
00167 local_g = rcp(new Epetra_Vector(local_response_map));
00168 RCP<Epetra_MultiVector> local_dgdx;
00169 if (dg_dx != NULL)
00170 local_dgdx = rcp(new Epetra_MultiVector(dg_dx->Map(), num_responses));
00171 RCP<Epetra_MultiVector> local_dgdxdot;
00172 if (dg_dxdot != NULL)
00173 local_dgdxdot = rcp(new Epetra_MultiVector(dg_dxdot->Map(), num_responses));
00174 RCP<Epetra_MultiVector> local_dgdxdotdot;
00175 if (dg_dxdotdot != NULL)
00176 local_dgdxdotdot = rcp(new Epetra_MultiVector(dg_dxdotdot->Map(), num_responses));
00177 RCP<Epetra_MultiVector> local_dgdp;
00178 if (dg_dp != NULL)
00179 local_dgdp = rcp(new Epetra_MultiVector(local_response_map,
00180 dg_dp->NumVectors()));
00181
00182
00183 responses[i]->evaluateGradient(current_time, xdot, xdotdot, x, p, deriv_p,
00184 local_g.get(), local_dgdx.get(),
00185 local_dgdxdot.get(), local_dgdxdotdot.get(), local_dgdp.get());
00186
00187
00188 for (unsigned int j=0; j<num_responses; j++) {
00189 if (g != NULL)
00190 (*g)[offset+j] = (*local_g)[j];
00191 if (dg_dx != NULL)
00192 (*dg_dx)(offset+j)->Update(1.0, *((*local_dgdx)(j)), 0.0);
00193 if (dg_dxdot != NULL)
00194 (*dg_dxdot)(offset+j)->Update(1.0, *((*local_dgdxdot)(j)), 0.0);
00195 if (dg_dxdotdot != NULL)
00196 (*dg_dxdotdot)(offset+j)->Update(1.0, *((*local_dgdxdotdot)(j)), 0.0);
00197 if (dg_dp != NULL)
00198 for (int k=0; k<dg_dp->NumVectors(); k++)
00199 (*dg_dp)[k][offset+j] = (*local_dgdp)[k][j];
00200 }
00201
00202
00203 offset += num_responses;
00204 }
00205 }