/// <summary> /// Evaluate the reference state at the given point. /// </summary> virtual void EvaluateReferenceState( const PhysicalConstants & phys, double dZ, double dLon, double dLat, double * dState ) const { // 3D temperature double dT = m_dT0 - m_dGamma * dZ; // 3D pressure double dPressure = phys.GetP0() * pow(1.0 - m_dGamma / m_dT0 * dZ, phys.GetG() / (phys.GetR() * m_dGamma)); // 3D density double dRho = dPressure / (phys.GetR() * dT); // Store the state dState[0] = 0.0; dState[1] = 0.0; dState[2] = phys.RhoThetaFromPressure(dPressure) / dRho; dState[3] = 0.0; dState[4] = dRho; }
/// <summary> /// Evaluate the reference state at the given point. /// </summary> virtual void EvaluateReferenceState( const PhysicalConstants & phys, double dZp, double dXp, double dYp, double * dState ) const { const double dLy = m_dGDim[3] - m_dGDim[2]; // Pressure coordinate double dGeopotential; double dTemperature; double dEta = EtaFromRLL( phys, dZp, dXp, dYp, dGeopotential, dTemperature); // Calculate zonal velocity and set other velocity components double dExpDecay = exp(-(log(dEta) / m_dbC) * (log(dEta) / m_dbC)); double dUlon = -m_dU0 * sin(m_dpiC * dYp / dLy) * sin(m_dpiC * dYp / dLy) * log(dEta) * dExpDecay; dState[0] = dUlon; dState[1] = 0.0; dState[3] = 0.0; // Calculate rho and theta double dPressure = phys.GetP0() * dEta; //std::cout << std::setprecision(16) << "Z = " << dZp << " Eta = " << dEta << "\n"; double dRho = dPressure / (phys.GetR() * dTemperature); double dRhoTheta = phys.RhoThetaFromPressure(dPressure); dState[2] = dRhoTheta / dRho; dState[4] = dRho; }
/// <summary> /// Evaluate the state vector at the given point. /// </summary> virtual void EvaluatePointwiseState( const PhysicalConstants & phys, const Time & time, double dZ, double dLon, double dLat, double * dState, double * dTracer ) const { // Radius double dR = dZ + phys.GetEarthRadius(); // Calculate parameters double dT0 = 0.5 * (ParamT0E + ParamT0P); double dConstA = 1.0 / ParamLapseRate; double dConstB = (dT0 - ParamT0P) / (dT0 * ParamT0P); double dConstC = 0.5 * (ParamK + 2.0) * (ParamT0E - ParamT0P) / (ParamT0E * ParamT0P); double dConstH = phys.GetR() * dT0 / phys.GetG(); // Computed quantities double dScaledZ = dZ / (ParamB * dConstH); // Calculate tau values double dTau1 = dConstA * ParamLapseRate / dT0 * exp(ParamLapseRate / dT0 * dZ) + dConstB * (1.0 - 2.0 * dScaledZ * dScaledZ) * exp(- dScaledZ * dScaledZ); double dTau2 = dConstC * (1.0 - 2.0 * dScaledZ * dScaledZ) * exp(- dScaledZ * dScaledZ); double dIntTau1 = dConstA * (exp(ParamLapseRate / dT0 * dZ) - 1.0) + dConstB * dZ * exp(- dScaledZ * dScaledZ); double dIntTau2 = dConstC * dZ * exp(- dScaledZ * dScaledZ); // Calculate utility terms double dRRatio; if (m_fDeepAtmosphere) { dRRatio = dR / phys.GetEarthRadius(); } else { dRRatio = 1.0; } double dInteriorTerm = pow(dRRatio * cos(dLat), ParamK) - ParamK / (ParamK + 2.0) * pow(dRRatio * cos(dLat), ParamK + 2.0); // Calculate temperature double dTemperature = 1.0 / (dRRatio * dRRatio) / (dTau1 - dTau2 * dInteriorTerm); // Calculate hydrostatic pressure double dPressure = phys.GetP0() * exp( - phys.GetG() / phys.GetR() * (dIntTau1 - dIntTau2 * dInteriorTerm)); // Calculate hydrostatic density double dRho = dPressure / (phys.GetR() * dTemperature); // Velocity field double dInteriorTermU = pow(dRRatio * cos(dLat), ParamK - 1.0) - pow(dRRatio * cos(dLat), ParamK + 1.0); double dBigU = phys.GetG() / phys.GetEarthRadius() * ParamK * dIntTau2 * dInteriorTermU * dTemperature; double dRCosLat; if (m_fDeepAtmosphere) { dRCosLat = dR * cos(dLat); } else { dRCosLat = phys.GetEarthRadius() * cos(dLat); } double dOmegaRCosLat = phys.GetOmega() * dRCosLat; if (dOmegaRCosLat * dOmegaRCosLat + dRCosLat * dBigU < 0.0) { _EXCEPTIONT("Negative discriminant detected."); } double dUlon = - dOmegaRCosLat + sqrt(dOmegaRCosLat * dOmegaRCosLat + dRCosLat * dBigU); double dUlat = 0.0; // Calculate velocity perturbation double dUlonPert; double dUlatPert; EvaluatePointwisePerturbation( phys, dZ, dLon, dLat, dUlonPert, dUlatPert); dUlon += dUlonPert; dUlat += dUlatPert; // Store the state dState[0] = dUlon; dState[1] = dUlat; dState[2] = phys.RhoThetaFromPressure(dPressure) / dRho; dState[3] = 0.0; dState[4] = dRho; }
/// <summary> /// Evaluate the reference state at the given point. /// </summary> virtual void EvaluateReferenceState( const PhysicalConstants & phys, double dZ, double dLon, double dLat, double * dState ) const { // Radius double dR = dZ + phys.GetEarthRadius(); // Calculate parameters double dT0 = 0.5 * (ParamT0E + ParamT0P); double dConstA = 1.0 / ParamLapseRate; double dConstB = (dT0 - ParamT0P) / (dT0 * ParamT0P); double dConstC = 0.5 * (ParamK + 2.0) * (ParamT0E - ParamT0P) / (ParamT0E * ParamT0P); double dConstH = phys.GetR() * dT0 / phys.GetG(); // Computed quantities double dScaledZ = dZ / (ParamB * dConstH); // Calculate tau values double dTau1 = dConstA * ParamLapseRate / dT0 * exp(ParamLapseRate / dT0 * dZ) + dConstB * (1.0 - 2.0 * dScaledZ * dScaledZ) * exp(- dScaledZ * dScaledZ); double dTau2 = dConstC * (1.0 - 2.0 * dScaledZ * dScaledZ) * exp(- dScaledZ * dScaledZ); double dIntTau1 = dConstA * (exp(ParamLapseRate / dT0 * dZ) - 1.0) + dConstB * dZ * exp(- dScaledZ * dScaledZ); double dIntTau2 = dConstC * dZ * exp(- dScaledZ * dScaledZ); // Calculate utility terms double dRRatio; if (m_fDeepAtmosphere) { dRRatio = dR / phys.GetEarthRadius(); } else { dRRatio = 1.0; } double dInteriorTerm = pow(dRRatio * cos(dLat), ParamK) - ParamK / (ParamK + 2.0) * pow(dRRatio * cos(dLat), ParamK + 2.0); // Calculate temperature double dTemperature = 1.0 / (dRRatio * dRRatio) / (dTau1 - dTau2 * dInteriorTerm); // Calculate hydrostatic pressure double dPressure = phys.GetP0() * exp( - phys.GetG() / phys.GetR() * (dIntTau1 - dIntTau2 * dInteriorTerm)); /* // Calculate pressure derivative double dDrPressure; if (m_fDeepAtmosphere) { dDrPressure = dPressure * phys.GetG() / phys.GetR() * ( - dTau1 + dTau2 * dInteriorTerm + dIntTau2 * ParamK / dR * (pow(dRRatio * cos(dLat), ParamK) - pow(dRRatio * cos(dLat), ParamK + 2.0))); } else { dDrPressure = dPressure * phys.GetG() / phys.GetR() * ( - dTau1 + dTau2 * dInteriorTerm); } // Calculate hydrostatic density double dHydroRho = - dRRatio * dRRatio / phys.GetG() * dDrPressure; */ // Calculate exact density double dRho = dPressure / (phys.GetR() * dTemperature); // Store the state dState[0] = 0.0; dState[1] = 0.0; dState[2] = phys.RhoThetaFromPressure(dPressure) / dRho; dState[3] = 0.0; dState[4] = dRho; }