void step() { phi.initGhostCells( ); { #pragma omp parallel for firstprivate( ghostfield) for( unsigned i=0; i<2; i++) { swap_fields( field[i], ghostfield);// now field is void ghostfield.initGhostCells( ); arakawa( phi, ghostfield, nonlinear[i]); swap_fields( field[i], ghostfield);// now ghostfield is void } karniadakis.step_i<S>( field, nonlinear); #pragma omp parallel for for( unsigned i=0; i<2; i++) dft_drt.r2c( field[i], cfield[i]); karniadakis.step_ii( cfield); swap_fields( cphi, phi); //now phi is void multiply_coefficients(); #pragma omp parallel for for( unsigned i=0; i<2; i++) dft_drt.c2r( cfield[i], field[i]); } dft_drt.c2r( cphi, phi); //field in phi again }
int main() { //Construct coefficients and init karniadakis with correct normalisation const Complex kxmin { 0, 2.*M_PI/lx}, kzmin{ 0, M_PI/lz}; for( unsigned i=0; i<nz; i++) for( unsigned j=0; j<nx/2+1; j++) rayleigh_equations( coefficients(i,j), (double)j*kxmin, (double)(i+1)*kzmin); karniadakis.init_coeff( coefficients, (double)(2*nx*(nz))); //swaps in coefficients //Initialize the complex fields //////////////////////// cfield[0].zero(); cfield[1].zero(); Complex ctheta_0 = { 0, -0.5*theta_0}; Complex comega_0 = {0.5*omega_0, 0}; cfield[0](iz, ix) = ctheta_0; cfield[1](iz, ix) = comega_0; //Transform and backtransform will multiply input dft_drt.c2r( cfield[0], field[0]), dft_drt.c2r( cfield[1], field[1]); dft_drt.r2c( field[0], cfield[0]), dft_drt.r2c( field[1], cfield[1]); //Hopefully the step_ii function will correctly normalize karniadakis.invert_coeff<TL_EULER>(); karniadakis.step_ii( cfield); if( abs( cfield[0](iz,ix) - ctheta_0) > 1e-14 || abs( cfield[1](iz,ix) - comega_0) > 1e-14 ) { cout << "TEST FAILED: \n"; cout << setprecision(6) << fixed; cout << "Rayleigh = "<< R <<endl; cout << "-0.5 theta_0 = " <<ctheta_0<< endl << " 0.5 omega_0 = "<< comega_0<<endl; cout << cfield[0](iz,ix) << endl<< cfield[1](iz,ix)<<endl; cout <<scientific<< "Difference: " <<abs( cfield[0](iz,ix) - ctheta_0 )<<endl; cout <<scientific<< "Difference: " <<abs( cfield[1](iz,ix) - comega_0 )<<endl; } else cout << "TEST PASSED!\n"; return 0; }
int main() { ////////////////////////////////glfw////////////////////////////// GLFWwindow* w = draw::glfwInitAndCreateWindow( 800, 200, "Behold the convection!"); draw::RenderHostData render(1,1); draw::ColorMapRedBlueExt colors( R); std::vector<double> visual; ////////////////////////////////////////////////////////////////// const Complex kxmin { 0, 2.*M_PI/lx}, kzmin{ 0, M_PI/lz}; TurbulentBath bath(R); for( unsigned i=0; i<nz; i++) for( unsigned j=0; j<nx/2+1; j++) { rayleigh_equations( coefficients(i,j), (double)j*kxmin, (double)(i+1)*kzmin); laplace_inverse( cphi_coefficients(i,j), (double)j*kxmin, (double)(i+1)*kzmin); cfield[0](i,j) ={ bath( coefficients(i,j)(0,0).real()), bath( coefficients(i,j)(0,0).real())}; } //init solvers karniadakis.init_coeff( coefficients, prefactor); //swaps in coefficients //init fields cfield[1].zero(); cphi.zero(); multiply_coefficients(); dft_drt.c2r( cfield[0], field[0]); dft_drt.c2r( cfield[1], field[1]); dft_drt.c2r( cphi, phi); //first steps karniadakis.invert_coeff<TL_EULER>(); step<TL_EULER>(); karniadakis.invert_coeff<TL_ORDER2>(); step<TL_ORDER2>(); karniadakis.invert_coeff<TL_ORDER3>(); step<TL_ORDER3>(); ////////////////////////////////////////////////////////////////// double timer[10]; Timer t; static int i=0; cout << "PRESS ESC OR CLOSE WINDOW TO TERMINATE PROGRAM!\n"; while( !glfwWindowShouldClose( w)) { visual = field[0].copy(); render.renderQuad( visual, nx, nz, colors); glfwPollEvents(); glfwSwapBuffers( w ); //////////////call stepper/////////////////////////////////// t.tic(); for( unsigned j=0; j<N; j++) step<TL_ORDER3>(); t.toc(); timer[i++%10] = t.diff(); ////////////////////////////////////////////////////////////// } double avg = 0; for( int i=0; i<10; i++) avg+=timer[i]/10./(double)N; cout << "Average time for one step: " << avg << "s\n"; cout << "Total number of steps: " << i*N << "\n"; glfwTerminate(); ////////////////////////////////////////////////////////////////// fftw_cleanup(); return 0; }