Changeset 3864
- Timestamp:
- Apr 5, 2019 9:01:56 AM (6 years ago)
- Location:
- palm/trunk
- Files:
-
- 3 added
- 3 deleted
- 11 edited
Legend:
- Unmodified
- Added
- Removed
-
palm/trunk/SOURCE/Makefile
r3833 r3864 1581 1581 advec_s_pw.o \ 1582 1582 advec_s_up.o \ 1583 chemistry_model_mod.o \ 1583 chem_gasphase_mod.o \ 1584 chemistry_model_mod.o \ 1584 1585 diffusion_s.o \ 1585 1586 netcdf_data_input_mod.o \ -
palm/trunk/SOURCE/advec_ws.f90
r3696 r3864 25 25 ! ----------------- 26 26 ! $Id$ 27 ! Remove tailing white spaces 28 ! 29 ! 3696 2019-01-24 16:37:35Z suehring 27 30 ! Bugfix in degradation height 28 31 ! … … 349 352 350 353 USE salsa_util_mod, & 351 ONLY: sums_salsa_ws_l 352 354 ONLY: sums_salsa_ws_l 355 353 356 USE statistics, & 354 357 ONLY: sums_us2_ws_l, sums_vs2_ws_l, sums_ws2_ws_l, sums_wsncs_ws_l,& … … 357 360 sums_wssas_ws_l, sums_wsss_ws_l, sums_wsus_ws_l, & 358 361 sums_wsvs_ws_l 359 362 360 363 361 364 ! … … 418 421 sums_wssas_ws_l = 0.0_wp 419 422 ENDIF 420 423 421 424 IF ( salsa ) THEN 422 425 ALLOCATE( sums_salsa_ws_l(nzb:nzt+1,0:threads_per_task-1) ) 423 sums_salsa_ws_l = 0.0_wp 426 sums_salsa_ws_l = 0.0_wp 424 427 ENDIF 425 428 … … 1143 1146 1144 1147 USE salsa_util_mod, & 1145 ONLY: sums_salsa_ws_l 1146 1148 ONLY: sums_salsa_ws_l 1149 1147 1150 USE statistics, & 1148 1151 ONLY: sums_us2_ws_l, sums_vs2_ws_l, sums_ws2_ws_l, sums_wsncs_ws_l,& … … 1221 1224 1222 1225 USE salsa_util_mod, & 1223 ONLY: sums_salsa_ws_l 1226 ONLY: sums_salsa_ws_l 1224 1227 1225 1228 USE statistics, & … … 1824 1827 ) * weight_substep(intermediate_timestep_count) 1825 1828 ENDDO 1826 1829 1827 1830 CASE ( 's' ) 1828 1831 1829 1832 DO k = nzb, nzt 1830 1833 sums_wsss_ws_l(k,tn) = sums_wsss_ws_l(k,tn) + & … … 1835 1838 ) * weight_substep(intermediate_timestep_count) 1836 1839 ENDDO 1837 1840 1838 1841 CASE ( 'aerosol_mass', 'aerosol_number', 'salsa_gas' ) 1839 1842 1840 1843 DO k = nzb, nzt 1841 1844 sums_salsa_ws_l(k,tn) = sums_salsa_ws_l(k,tn) + & … … 1845 1848 * ABS( w(k,j,i) - hom(k,1,3,0) ) & 1846 1849 ) * weight_substep(intermediate_timestep_count) 1847 ENDDO 1850 ENDDO 1848 1851 1849 1852 ! CASE ( 'kc' ) … … 1852 1855 1853 1856 END SELECT 1854 1857 1855 1858 END SUBROUTINE advec_s_ws_ij 1856 1859 … … 3595 3598 ONLY: nxl, nxlg, nxr, nxrg, nyn, nyng, nys, nysg, nzb, nzb_max, & 3596 3599 nzt, advc_flags_1 3597 3600 3598 3601 USE kinds 3599 3602 3600 3603 USE salsa_util_mod, & 3601 ONLY: sums_salsa_ws_l 3602 3604 ONLY: sums_salsa_ws_l 3605 3603 3606 USE statistics, & 3604 3607 ONLY: hom, sums_wspts_ws_l, sums_wsqs_ws_l, sums_wssas_ws_l, & 3605 3608 sums_wsqcs_ws_l, sums_wsqrs_ws_l, sums_wsncs_ws_l, & 3606 3609 sums_wsnrs_ws_l, sums_wsss_ws_l, weight_substep 3607 3610 3608 3611 3609 3612 -
palm/trunk/SOURCE/boundary_conds.f90
r3717 r3864 1409 1409 1410 1410 ENDIF 1411 1411 1412 1412 IF ( salsa ) THEN 1413 1413 CALL salsa_boundary_conds 1414 ENDIF 1414 ENDIF 1415 1415 1416 1416 END SUBROUTINE boundary_conds -
palm/trunk/SOURCE/module_interface.f90
r3840 r3864 25 25 ! ----------------- 26 26 ! $Id$ 27 ! Add a call for salsa_prognostic_equations 28 ! 29 ! 3840 2019-03-29 10:35:52Z knoop 27 30 ! bugfix: intent of dummy arguments changed to inout 28 31 ! … … 280 283 salsa_init, & 281 284 salsa_header, & 285 salsa_prognostic_equations, & 282 286 salsa_swap_timelevel, & 283 287 salsa_3d_data_averaging, & … … 909 913 IF ( gust_module_enabled ) CALL gust_prognostic_equations() 910 914 IF ( ocean_mode ) CALL ocean_prognostic_equations() 915 IF ( salsa ) CALL salsa_prognostic_equations() 911 916 912 917 … … 930 935 IF ( gust_module_enabled ) CALL gust_prognostic_equations( i, j, i_omp_start, tn ) 931 936 IF ( ocean_mode ) CALL ocean_prognostic_equations( i, j, i_omp_start, tn ) 937 IF ( salsa ) CALL salsa_prognostic_equations( i, j, i_omp_start, tn ) 932 938 933 939 -
palm/trunk/SOURCE/netcdf_data_input_mod.f90
r3855 r3864 25 25 ! ----------------- 26 26 ! $Id$ 27 ! get_variable_4d_to_3d_real modified to enable read in data of type 28 ! data(t,y,x,n) one timestep at a time + some routines made public 29 ! 30 ! 3855 2019-04-03 10:00:59Z suehring 27 31 ! Typo removed 28 32 ! … … 913 917 netcdf_data_input_interpolate, netcdf_data_input_offline_nesting, & 914 918 netcdf_data_input_surface_data, netcdf_data_input_topo, & 915 netcdf_data_input_var, get_attribute, get_variable, open_read_file 919 netcdf_data_input_var, get_attribute, get_variable, open_read_file, & 920 check_existence, inquire_num_variables, inquire_variable_names 916 921 917 922 … … 5557 5562 INTEGER(iwp) :: ke !< start index of 3rd dimension 5558 5563 INTEGER(iwp) :: ks !< end index of 3rd dimension 5559 5564 5560 5565 INTEGER(KIND=1), DIMENSION(:,:,:), ALLOCATABLE :: tmp !< temporary variable to read data from file according 5561 5566 !< to its reverse memory access … … 5566 5571 ! 5567 5572 !-- Inquire variable id 5568 nc_stat = NF90_INQ_VARID( id, TRIM( variable_name ), id_var ) 5573 nc_stat = NF90_INQ_VARID( id, TRIM( variable_name ), id_var ) 5569 5574 ! 5570 5575 !-- Check for collective read-operation and set respective NetCDF flags if … … 5573 5578 #if defined( __netcdf4_parallel ) 5574 5579 nc_stat = NF90_VAR_PAR_ACCESS (id, id_var, NF90_COLLECTIVE) 5575 #endif 5580 #endif 5576 5581 ENDIF 5577 5582 ! … … 5582 5587 nc_stat = NF90_GET_VAR( id, id_var, tmp, & 5583 5588 start = (/ is+1, js+1, ks+1 /), & 5584 count = (/ ie-is+1, je-js+1, ke-ks+1 /) ) 5585 5586 CALL handle_error( 'get_variable_3d_int8', 533, variable_name ) 5589 count = (/ ie-is+1, je-js+1, ke-ks+1 /) ) 5590 5591 CALL handle_error( 'get_variable_3d_int8', 533, variable_name ) 5587 5592 ! 5588 5593 !-- Resort data. Please note, dimension subscripts of var all start at 1. … … 5594 5599 ENDDO 5595 5600 ENDDO 5596 5601 5597 5602 DEALLOCATE( tmp ) 5598 5603 … … 5627 5632 INTEGER(iwp) :: ke !< start index of 3rd dimension 5628 5633 INTEGER(iwp) :: ks !< end index of 3rd dimension 5629 5634 5630 5635 REAL(wp), DIMENSION(:,:,:), ALLOCATABLE :: tmp !< temporary variable to read data from file according 5631 5636 !< to its reverse memory access … … 5641 5646 !-- required. 5642 5647 IF ( collective_read ) THEN 5643 #if defined( __netcdf4_parallel ) 5648 #if defined( __netcdf4_parallel ) 5644 5649 nc_stat = NF90_VAR_PAR_ACCESS (id, id_var, NF90_COLLECTIVE) 5645 5650 #endif … … 5653 5658 start = (/ is+1, js+1, ks+1 /), & 5654 5659 count = (/ ie-is+1, je-js+1, ke-ks+1 /) ) 5655 5660 5656 5661 CALL handle_error( 'get_variable_3d_real', 534, variable_name ) 5657 5662 ! … … 5664 5669 ENDDO 5665 5670 ENDDO 5666 5671 5667 5672 DEALLOCATE( tmp ) 5668 5673 … … 5737 5742 ELSE 5738 5743 ! 5739 !-- Allocate temporary variable according to memory access on file.5740 ALLOCATE( tmp(is:ie,js:je,k1s:k1e,k2s:k2e) )5741 ! 5742 !-- Get variable5743 nc_stat = NF90_GET_VAR( id, id_var, tmp, 5744 !-- Allocate temporary variable according to memory access on file. 5745 ALLOCATE( tmp(is:ie,js:je,k1s:k1e,k2s:k2e) ) 5746 ! 5747 !-- Get variable 5748 nc_stat = NF90_GET_VAR( id, id_var, tmp, & 5744 5749 start = (/ is+1, js+1, k1s+1, k2s+1 /), & 5745 5750 count = (/ ie-is+1, je-js+1, & … … 5748 5753 CALL handle_error( 'get_variable_4d_real', 535, variable_name ) 5749 5754 ! 5750 !-- Resort data. Please note, dimension subscripts of var all start at 1.5755 !-- Resort data. Please note, dimension subscripts of var all start at 1. 5751 5756 DO i = is, ie 5752 5757 DO j = js, je … … 5758 5763 ENDDO 5759 5764 ENDDO 5760 5765 5761 5766 DEALLOCATE( tmp ) 5762 5767 ENDIF … … 5828 5833 ELSE 5829 5834 ! 5830 !-- Allocate temporary variable according to memory access on file.5835 !-- Allocate temporary variable according to memory access on file. 5831 5836 ALLOCATE( tmp(is:ie,js:je,ks:ke) ) 5832 5837 ! 5833 !-- Get variable5834 nc_stat = NF90_GET_VAR( id, id_var, tmp, 5835 start = (/ ns+1, is+1, js+1, ks+1 /),&5836 count = (/ 1, ie-is+1, je-js+1, ke-ks+1 /) )5837 5838 !-- Get variable 5839 nc_stat = NF90_GET_VAR( id, id_var, tmp, & 5840 start = (/ is+1, js+1, ks+1, ns+1 /),& 5841 count = (/ ie-is+1, je-js+1, ke-ks+1, 1 /) ) 5842 5838 5843 CALL handle_error( 'get_variable_4d_to_3d_real', 536, variable_name ) 5839 5844 ! 5840 !-- Resort data. Please note, dimension subscripts of var all start at 1.5841 DO i = is, ie 5845 !-- Resort data. Please note, dimension subscripts of var all start at 1. 5846 DO i = is, ie 5842 5847 DO j = js, je 5843 5848 DO k = ks, ke … … 5846 5851 ENDDO 5847 5852 ENDDO 5848 5853 5849 5854 DEALLOCATE( tmp ) 5850 5855 … … 5962 5967 CHARACTER(LEN=*) :: variable_name !< variable name 5963 5968 5964 INTEGER(iwp) :: ns !< start index for subdomain input along n dimension: ns coincides here with ne, since, we select only one value along the 1st dimension n 5969 INTEGER(iwp) :: ns !< start index for subdomain input along n dimension: 5970 !< ns coincides here with ne, since, we select only one 5971 !< value along the 1st dimension n 5965 5972 5966 5973 INTEGER(iwp) :: t !< index along t direction … … 5986 5993 ! 5987 5994 !-- Inquire variable id 5988 nc_stat = NF90_INQ_VARID( id, TRIM( variable_name ), id_var ) 5995 nc_stat = NF90_INQ_VARID( id, TRIM( variable_name ), id_var ) 5989 5996 ! 5990 5997 !-- Check for collective read-operation and set respective NetCDF flags if 5991 !-- required. 5998 !-- required. 5992 5999 IF ( collective_read ) THEN 5993 6000 nc_stat = NF90_VAR_PAR_ACCESS (id, id_var, NF90_COLLECTIVE) … … 6036 6043 ENDDO 6037 6044 6038 DEALLOCATE( tmp )6045 DEALLOCATE( tmp ) 6039 6046 6040 6047 ENDIF -
palm/trunk/SOURCE/plant_canopy_model_mod.f90
r3761 r3864 22 22 ! Current revisions: 23 23 ! ------------------ 24 ! 24 ! 25 25 ! 26 26 ! Former revisions: … … 1055 1055 DO j = nys, nyn 1056 1056 DO k = 0, leaf_area_density_f%nz - 1 1057 IF ( leaf_area_density_f%var(k,j,i) /=&1058 leaf_area_density_f%fill )&1057 IF ( leaf_area_density_f%var(k,j,i) /= & 1058 leaf_area_density_f%fill ) & 1059 1059 lad_s(k,j,i) = leaf_area_density_f%var(k,j,i) 1060 1060 ENDDO -
palm/trunk/SOURCE/pmc_interface_mod.f90
r3833 r3864 25 25 ! ----------------- 26 26 ! $Id$ 27 ! Implemented nesting for salsa variables. 28 ! 29 ! 3833 2019-03-28 15:04:04Z forkel 27 30 ! replaced USE chem_modules by USE chem_gasphase_mod 28 31 ! … … 398 401 coupling_char, dt_3d, dz, humidity, message_string, & 399 402 neutral, passive_scalar, rans_mode, rans_tke_e, & 400 roughness_length, topography, volume_flow403 roughness_length, salsa, topography, volume_flow 401 404 402 405 USE chem_gasphase_mod, & … … 457 460 458 461 #endif 462 463 USE salsa_mod, & 464 ONLY: aerosol_mass, aerosol_number, gconc_2, mconc_2, nbins_aerosol, & 465 ncomponents_mass, nconc_2, nest_salsa, ngases_salsa, salsa_gas, & 466 salsa_gases_from_chem 459 467 460 468 USE surface_mod, & … … 518 526 INTEGER(idp), SAVE, DIMENSION(:,:), ALLOCATABLE, TARGET, PUBLIC :: part_adrc !< 519 527 520 REAL(wp), SAVE, DIMENSION(:,:,:,:), ALLOCATABLE, TARGET :: chem_spec_c !< Parent-grid array on child domain - chemical species 528 REAL(wp), SAVE, DIMENSION(:,:,:,:), ALLOCATABLE, TARGET :: chem_spec_c !< coarse grid array on child domain - chemical species 529 530 REAL(wp), SAVE, DIMENSION(:,:,:,:), ALLOCATABLE, TARGET :: aerosol_mass_c !< aerosol mass 531 REAL(wp), SAVE, DIMENSION(:,:,:,:), ALLOCATABLE, TARGET :: aerosol_number_c !< aerosol number 532 REAL(wp), SAVE, DIMENSION(:,:,:,:), ALLOCATABLE, TARGET :: salsa_gas_c !< salsa gases 521 533 ! 522 534 !-- Grid-spacing ratios. … … 817 829 818 830 CHARACTER(LEN=32) :: myname 819 820 INTEGER(iwp) :: child_id !< 821 INTEGER(iwp) :: ierr !< 822 INTEGER(iwp) :: k !< 823 INTEGER(iwp) :: m !< 824 INTEGER(iwp) :: mid !< 825 INTEGER(iwp) :: mm !< 826 INTEGER(iwp) :: n = 1 !< Running index for chemical species 827 INTEGER(iwp) :: nest_overlap !< 828 INTEGER(iwp) :: nomatch !< 829 INTEGER(iwp) :: nx_cl !< 830 INTEGER(iwp) :: ny_cl !< 831 INTEGER(iwp) :: nz_cl !< 832 INTEGER(iwp), DIMENSION(3) :: val !< Array for receiving the child-grid dimensions 831 INTEGER(iwp) :: child_id !< 832 INTEGER(iwp) :: ib = 1 !< running index for aerosol size bins 833 INTEGER(iwp) :: ic = 1 !< running index for aerosol mass bins 834 INTEGER(iwp) :: ig = 1 !< running index for salsa gases 835 INTEGER(iwp) :: ierr !< 836 INTEGER(iwp) :: k !< 837 INTEGER(iwp) :: m !< 838 INTEGER(iwp) :: mid !< 839 INTEGER(iwp) :: mm !< 840 INTEGER(iwp) :: n = 1 !< running index for chemical species 841 INTEGER(iwp) :: nest_overlap !< 842 INTEGER(iwp) :: nomatch !< 843 INTEGER(iwp) :: nx_cl !< 844 INTEGER(iwp) :: ny_cl !< 845 INTEGER(iwp) :: nz_cl !< 846 847 INTEGER(iwp), DIMENSION(5) :: val !< 848 833 849 REAL(wp), DIMENSION(:), ALLOCATABLE :: ch_xl !< 834 850 REAL(wp), DIMENSION(:), ALLOCATABLE :: ch_xr !< … … 1032 1048 CALL pmci_set_array_pointer( myname, child_id = child_id, & 1033 1049 nz_cl = nz_cl, n = n ) 1034 n = n + 1 1050 n = n + 1 1051 ELSEIF ( INDEX( TRIM( myname ), 'an_' ) /= 0 ) THEN 1052 CALL pmci_set_array_pointer( myname, child_id = child_id, & 1053 nz_cl = nz_cl, n = ib ) 1054 ib = ib + 1 1055 ELSEIF ( INDEX( TRIM( myname ), 'am_' ) /= 0 ) THEN 1056 CALL pmci_set_array_pointer( myname, child_id = child_id, & 1057 nz_cl = nz_cl, n = ic ) 1058 ic = ic + 1 1059 ELSEIF ( INDEX( TRIM( myname ), 'sg_' ) /= 0 .AND. & 1060 .NOT. salsa_gases_from_chem ) & 1061 THEN 1062 CALL pmci_set_array_pointer( myname, child_id = child_id, & 1063 nz_cl = nz_cl, n = ig ) 1064 ig = ig + 1 1035 1065 ELSE 1036 1066 CALL pmci_set_array_pointer( myname, child_id = child_id, & … … 1193 1223 IMPLICIT NONE 1194 1224 1195 CHARACTER(LEN=da_namelen) :: myname !< 1196 INTEGER(iwp) :: ierr !< MPI error code 1225 1226 CHARACTER(LEN=da_namelen) :: myname !< 1227 CHARACTER(LEN=5) :: salsa_char !< 1228 INTEGER(iwp) :: ib !< running index for aerosol size bins 1229 INTEGER(iwp) :: ic !< running index for aerosol mass bins 1230 INTEGER(iwp) :: ierr !< 1197 1231 INTEGER(iwp) :: icl !< Left index limit for children's parent-grid arrays 1198 1232 INTEGER(iwp) :: icla !< Left index limit for allocation of index-mapping and other auxiliary arrays … … 1201 1235 INTEGER(iwp) :: icra !< Right index limit for allocation of index-mapping and other auxiliary arrays 1202 1236 INTEGER(iwp) :: icrw !< Right index limit for children's parent-grid work arrays 1237 INTEGER(iwp) :: ig !< running index for salsa gases 1203 1238 INTEGER(iwp) :: jcn !< North index limit for children's parent-grid arrays 1204 1239 INTEGER(iwp) :: jcna !< North index limit for allocation of index-mapping and other auxiliary arrays … … 1281 1316 'chem_' // & 1282 1317 TRIM( chem_species(n)%name ), & 1283 'fine',&1318 'fine', & 1284 1319 'chem_' // & 1285 1320 TRIM( chem_species(n)%name ), & 1286 1321 ierr ) 1287 1322 ENDDO 1323 ENDIF 1324 1325 IF ( salsa .AND. nest_salsa ) THEN 1326 DO ib = 1, nbins_aerosol 1327 WRITE(salsa_char,'(i0)') ib 1328 CALL pmc_set_dataarray_name( 'coarse', & 1329 'an_' // & 1330 TRIM( salsa_char ), & 1331 'fine', & 1332 'an_' // & 1333 TRIM( salsa_char ), & 1334 ierr ) 1335 ENDDO 1336 DO ic = 1, nbins_aerosol * ncomponents_mass 1337 WRITE(salsa_char,'(i0)') ic 1338 CALL pmc_set_dataarray_name( 'coarse', & 1339 'am_' // & 1340 TRIM( salsa_char ), & 1341 'fine', & 1342 'am_' // & 1343 TRIM( salsa_char ), & 1344 ierr ) 1345 ENDDO 1346 IF ( .NOT. salsa_gases_from_chem ) THEN 1347 DO ig = 1, ngases_salsa 1348 WRITE(salsa_char,'(i0)') ig 1349 CALL pmc_set_dataarray_name( 'coarse', & 1350 'sg_' // & 1351 TRIM( salsa_char ), & 1352 'fine', & 1353 'sg_' // & 1354 TRIM( salsa_char ), & 1355 ierr ) 1356 ENDDO 1357 ENDIF 1288 1358 ENDIF 1289 1359 … … 1364 1434 CALL pmc_c_clear_next_array_list 1365 1435 1366 n = 1 1436 ib = 1 1437 ic = 1 1438 ig = 1 1439 n = 1 1440 1367 1441 DO WHILE ( pmc_c_getnextarray( myname ) ) 1368 1442 !-- Note that cg%nz is not the original nz of parent, but the highest … … 1375 1449 IF ( INDEX( TRIM( myname ), 'chem_' ) /= 0 ) THEN 1376 1450 CALL pmci_create_child_arrays ( myname, icl, icr, jcs, jcn, cg%nz, n ) 1377 n = n + 1 1451 n = n + 1 1452 ELSEIF ( INDEX( TRIM( myname ), 'an_' ) /= 0 ) THEN 1453 CALL pmci_create_child_arrays ( myname, icl, icr, jcs, jcn, cg%nz,& 1454 ib ) 1455 ib = ib + 1 1456 ELSEIF ( INDEX( TRIM( myname ), 'am_' ) /= 0 ) THEN 1457 CALL pmci_create_child_arrays ( myname, icl, icr, jcs, jcn, cg%nz,& 1458 ic ) 1459 ic = ic + 1 1460 ELSEIF ( INDEX( TRIM( myname ), 'sg_' ) /= 0 .AND. & 1461 .NOT. salsa_gases_from_chem ) & 1462 THEN 1463 CALL pmci_create_child_arrays ( myname, icl, icr, jcs, jcn, cg%nz,& 1464 ig ) 1465 ig = ig + 1 1378 1466 ELSE 1379 1467 CALL pmci_create_child_arrays ( myname, icl, icr, jcs, jcn, cg%nz ) … … 2114 2202 IF ( air_chemistry .AND. nest_chemistry ) & 2115 2203 pmc_max_array = pmc_max_array + nspec 2204 ! 2205 !-- Salsa, depens on the number aerosol size bins and chemical components + 2206 !-- the number of default gases 2207 IF ( salsa .AND. nest_salsa ) & 2208 pmc_max_array = pmc_max_array + nbins_aerosol + nbins_aerosol * & 2209 ncomponents_mass 2210 IF ( .NOT. salsa_gases_from_chem ) pmc_max_array = pmc_max_array + & 2211 ngases_salsa 2212 2213 2116 2214 #endif 2117 2215 … … 2126 2224 INTEGER(iwp), INTENT(IN) :: child_id !< 2127 2225 INTEGER(iwp), INTENT(IN) :: nz_cl !< 2128 INTEGER(iwp), INTENT(IN),OPTIONAL :: n !< index of chemical species 2226 INTEGER(iwp), INTENT(IN),OPTIONAL :: n !< index of chemical 2227 !< species / salsa variables 2129 2228 2130 2229 CHARACTER(LEN=*), INTENT(IN) :: name !< … … 2159 2258 IF ( TRIM(name) == "nr_part" ) i_2d => nr_part 2160 2259 IF ( TRIM(name) == "part_adr" ) i_2d => part_adr 2161 IF ( INDEX( TRIM(name), "chem_" ) /= 0 ) p_3d => chem_species(n)%conc 2260 IF ( INDEX( TRIM(name), "chem_" ) /= 0 ) p_3d => chem_species(n)%conc 2261 IF ( INDEX( TRIM(name), "an_" ) /= 0 ) p_3d => aerosol_number(n)%conc 2262 IF ( INDEX( TRIM(name), "am_" ) /= 0 ) p_3d => aerosol_mass(n)%conc 2263 IF ( INDEX( TRIM(name), "sg_" ) /= 0 .AND. .NOT. salsa_gases_from_chem ) & 2264 p_3d => salsa_gas(n)%conc 2162 2265 ! 2163 2266 !-- Next line is just an example for a 2D array (not active for coupling!) … … 2176 2279 IF ( TRIM(name) == "s" ) p_3d_sec => s_2 2177 2280 IF ( TRIM(name) == "diss" ) p_3d_sec => diss_2 2178 IF ( INDEX( TRIM(name), "chem_" ) /= 0 ) p_3d_sec => spec_conc_2(:,:,:,n) 2281 IF ( INDEX( TRIM(name), "chem_" ) /= 0 ) p_3d_sec => spec_conc_2(:,:,:,n) 2282 IF ( INDEX( TRIM(name), "an_" ) /= 0 ) p_3d_sec => nconc_2(:,:,:,n) 2283 IF ( INDEX( TRIM(name), "am_" ) /= 0 ) p_3d_sec => mconc_2(:,:,:,n) 2284 IF ( INDEX( TRIM(name), "sg_" ) /= 0 .AND. .NOT. salsa_gases_from_chem ) & 2285 p_3d_sec => gconc_2(:,:,:,n) 2179 2286 2180 2287 IF ( ASSOCIATED( p_3d ) ) THEN … … 2295 2402 INTEGER(iwp), INTENT(IN) :: nzc !< nzc is cg%nz, but note that cg%nz is not the original nz of parent, but the highest parent-grid level needed for nesting. 2296 2403 2297 INTEGER(iwp), INTENT(IN), OPTIONAL :: n !< number of chemical species 2404 INTEGER(iwp), INTENT(IN), OPTIONAL :: n !< number of chemical species / 2405 !< salsa variables 2298 2406 2299 2407 #if defined( __parallel ) … … 2356 2464 ALLOCATE( chem_spec_c(0:nzc+1,js:je,is:ie,1:nspec) ) 2357 2465 p_3d => chem_spec_c(:,:,:,n) 2466 ELSEIF ( TRIM( name(1:3) ) == "an_" ) THEN 2467 IF ( .NOT. ALLOCATED( aerosol_number_c ) ) & 2468 ALLOCATE( aerosol_number_c(0:nzc+1,js:je,is:ie,1:nbins_aerosol) ) 2469 p_3d => aerosol_number_c(:,:,:,n) 2470 ELSEIF ( TRIM( name(1:3) ) == "am_" ) THEN 2471 IF ( .NOT. ALLOCATED( aerosol_mass_c ) ) & 2472 ALLOCATE( aerosol_mass_c(0:nzc+1,js:je,is:ie,1:(nbins_aerosol*ncomponents_mass) ) ) 2473 p_3d => aerosol_mass_c(:,:,:,n) 2474 ELSEIF ( TRIM( name(1:3) ) == "sg_" .AND. .NOT. salsa_gases_from_chem ) & 2475 THEN 2476 IF ( .NOT. ALLOCATED( salsa_gas_c ) ) & 2477 ALLOCATE( salsa_gas_c(0:nzc+1,js:je,is:ie,1:ngases_salsa) ) 2478 p_3d => salsa_gas_c(:,:,:,n) 2358 2479 !ELSEIF (trim(name) == "z0") then 2359 2480 !IF (.not.allocated(z0c)) allocate(z0c(js:je, is:ie)) … … 2419 2540 2420 2541 INTEGER(iwp) :: i !< 2542 INTEGER(iwp) :: ib !< running index for aerosol size bins 2543 INTEGER(iwp) :: ic !< running index for aerosol mass bins 2421 2544 INTEGER(iwp) :: icl !< 2422 2545 INTEGER(iwp) :: icla !< … … 2425 2548 INTEGER(iwp) :: icra !< 2426 2549 INTEGER(iwp) :: icrw !< 2550 INTEGER(iwp) :: ig !< running index for salsa gases 2427 2551 INTEGER(iwp) :: j !< 2428 2552 INTEGER(iwp) :: jcn !< … … 2434 2558 INTEGER(iwp) :: k !< 2435 2559 INTEGER(iwp) :: n !< running index for chemical species 2560 2436 2561 REAL(wp) :: waittime !< 2437 2562 … … 2502 2627 kcto, iflo, ifuo, jflo, jfuo, kflo, kfuo, 's' ) 2503 2628 ENDDO 2629 ENDIF 2630 2631 IF ( salsa .AND. nest_salsa ) THEN 2632 DO ib = 1, nbins_aerosol 2633 CALL pmci_interp_1sto_all ( aerosol_number(ib)%conc, aerosol_number_c(:,:,:,ib), & 2634 kcto, iflo, ifuo, jflo, jfuo, kflo, kfuo, 's' ) 2635 ENDDO 2636 DO ic = 1, nbins_aerosol * ncomponents_mass 2637 CALL pmci_interp_1sto_all ( aerosol_mass(ic)%conc, aerosol_mass_c(:,:,:,ic), & 2638 kcto, iflo, ifuo, jflo, jfuo, kflo, kfuo, 's' ) 2639 ENDDO 2640 IF ( .NOT. salsa_gases_from_chem ) THEN 2641 DO ig = 1, ngases_salsa 2642 CALL pmci_interp_1sto_all ( salsa_gas(ig)%conc, salsa_gas_c(:,:,:,ig), & 2643 kcto, iflo, ifuo, jflo, jfuo, kflo, kfuo, 's' ) 2644 ENDDO 2645 ENDIF 2504 2646 ENDIF 2505 2647 … … 3080 3222 INTEGER(iwp) :: ibgp !< index running over the nbgp boundary ghost points in i-direction 3081 3223 INTEGER(iwp) :: jbgp !< index running over the nbgp boundary ghost points in j-direction 3224 INTEGER(iwp) :: ib !< running index for aerosol size bins 3225 INTEGER(iwp) :: ic !< running index for aerosol mass bins 3226 INTEGER(iwp) :: ig !< running index for salsa gases 3082 3227 INTEGER(iwp) :: n !< running index for number of chemical species 3083 3228 … … 3141 3286 ENDIF 3142 3287 3288 IF ( salsa .AND. nest_salsa ) THEN 3289 DO ib = 1, nbins_aerosol 3290 CALL pmci_interp_1sto_lr( aerosol_number(ib)%conc, aerosol_number_c(:,:,:,ib), & 3291 kcto, jflo, jfuo, kflo, kfuo, 'l', 's') 3292 ENDDO 3293 DO ic = 1, nbins_aerosol * ncomponents_mass 3294 CALL pmci_interp_1sto_lr( aerosol_mass(ic)%conc, aerosol_mass_c(:,:,:,ic), & 3295 kcto, jflo, jfuo, kflo, kfuo, 'l', 's') 3296 ENDDO 3297 IF ( .NOT. salsa_gases_from_chem ) THEN 3298 DO ig = 1, ngases_salsa 3299 CALL pmci_interp_1sto_lr( salsa_gas(ig)%conc, salsa_gas_c(:,:,:,ig), & 3300 kcto, jflo, jfuo, kflo, kfuo, 'l', 's') 3301 ENDDO 3302 ENDIF 3303 ENDIF 3304 3143 3305 ENDIF 3144 3306 ! … … 3195 3357 ENDDO 3196 3358 ENDIF 3359 3360 IF ( salsa .AND. nest_salsa ) THEN 3361 DO ib = 1, nbins_aerosol 3362 CALL pmci_interp_1sto_lr( aerosol_number(ib)%conc, aerosol_number_c(:,:,:,ib), & 3363 kcto, jflo, jfuo, kflo, kfuo, 'r', 's' ) 3364 ENDDO 3365 DO ic = 1, nbins_aerosol * ncomponents_mass 3366 CALL pmci_interp_1sto_lr( aerosol_mass(ic)%conc, aerosol_mass_c(:,:,:,ic), & 3367 kcto, jflo, jfuo, kflo, kfuo, 'r', 's' ) 3368 ENDDO 3369 IF ( .NOT. salsa_gases_from_chem ) THEN 3370 DO ig = 1, ngases_salsa 3371 CALL pmci_interp_1sto_lr( salsa_gas(ig)%conc, salsa_gas_c(:,:,:,ig), & 3372 kcto, jflo, jfuo, kflo, kfuo, 'r', 's' ) 3373 ENDDO 3374 ENDIF 3375 ENDIF 3376 3197 3377 ENDIF 3198 3378 ! … … 3248 3428 ENDDO 3249 3429 ENDIF 3430 3431 IF ( salsa .AND. nest_salsa ) THEN 3432 DO ib = 1, nbins_aerosol 3433 CALL pmci_interp_1sto_sn( aerosol_number(ib)%conc, aerosol_number_c(:,:,:,ib), & 3434 kcto, iflo, ifuo, kflo, kfuo, 's', 's' ) 3435 ENDDO 3436 DO ic = 1, nbins_aerosol * ncomponents_mass 3437 CALL pmci_interp_1sto_sn( aerosol_mass(ic)%conc, aerosol_mass_c(:,:,:,ic), & 3438 kcto, iflo, ifuo, kflo, kfuo, 's', 's' ) 3439 ENDDO 3440 IF ( .NOT. salsa_gases_from_chem ) THEN 3441 DO ig = 1, ngases_salsa 3442 CALL pmci_interp_1sto_sn( salsa_gas(ig)%conc, salsa_gas_c(:,:,:,ig), & 3443 kcto, iflo, ifuo, kflo, kfuo, 's', 's' ) 3444 ENDDO 3445 ENDIF 3446 ENDIF 3447 3250 3448 ENDIF 3251 3449 ! … … 3301 3499 ENDDO 3302 3500 ENDIF 3501 3502 IF ( salsa .AND. nest_salsa ) THEN 3503 DO ib = 1, nbins_aerosol 3504 CALL pmci_interp_1sto_sn( aerosol_number(ib)%conc, aerosol_number_c(:,:,:,ib), & 3505 kcto, iflo, ifuo, kflo, kfuo, 'n', 's' ) 3506 ENDDO 3507 DO ic = 1, nbins_aerosol * ncomponents_mass 3508 CALL pmci_interp_1sto_sn( aerosol_mass(ic)%conc, aerosol_mass_c(:,:,:,ic), & 3509 kcto, iflo, ifuo, kflo, kfuo, 'n', 's' ) 3510 ENDDO 3511 IF ( .NOT. salsa_gases_from_chem ) THEN 3512 DO ig = 1, ngases_salsa 3513 CALL pmci_interp_1sto_sn( salsa_gas(ig)%conc, salsa_gas_c(:,:,:,ig), & 3514 kcto, iflo, ifuo, kflo, kfuo, 'n', 's' ) 3515 ENDDO 3516 ENDIF 3517 ENDIF 3518 3303 3519 ENDIF 3304 3520 … … 3348 3564 kcto, iflo, ifuo, jflo, jfuo, 's' ) 3349 3565 ENDDO 3566 ENDIF 3567 3568 IF ( salsa .AND. nest_salsa ) THEN 3569 DO ib = 1, nbins_aerosol 3570 CALL pmci_interp_1sto_t( aerosol_number(ib)%conc, aerosol_number_c(:,:,:,ib), & 3571 kcto, iflo, ifuo, jflo, jfuo, 's' ) 3572 ENDDO 3573 DO ic = 1, nbins_aerosol * ncomponents_mass 3574 CALL pmci_interp_1sto_t( aerosol_mass(ic)%conc, aerosol_mass_c(:,:,:,ic), & 3575 kcto, iflo, ifuo, jflo, jfuo, 's' ) 3576 ENDDO 3577 IF ( .NOT. salsa_gases_from_chem ) THEN 3578 DO ig = 1, ngases_salsa 3579 CALL pmci_interp_1sto_t( salsa_gas(ig)%conc, salsa_gas_c(:,:,:,ig), & 3580 kcto, iflo, ifuo, jflo, jfuo, 's' ) 3581 ENDDO 3582 ENDIF 3350 3583 ENDIF 3351 3584 … … 3360 3593 !-- Note that TKE is not anterpolated. 3361 3594 IMPLICIT NONE 3595 INTEGER(iwp) :: ib !< running index for aerosol size bins 3596 INTEGER(iwp) :: ic !< running index for aerosol mass bins 3362 3597 INTEGER(iwp) :: n !< running index for number of chemical species 3363 3364 3598 INTEGER(iwp) :: ig !< running index for salsa gases 3599 3600 3365 3601 CALL pmci_anterp_tophat( u, uc, kcto, iflu, ifuu, jflo, jfuo, kflo, kfuo, ijkfc_u, 'u' ) 3366 3602 CALL pmci_anterp_tophat( v, vc, kcto, iflo, ifuo, jflv, jfuv, kflo, kfuo, ijkfc_v, 'v' ) … … 3419 3655 kcto, iflo, ifuo, jflo, jfuo, kflo, kfuo, ijkfc_s, 's' ) 3420 3656 ENDDO 3657 ENDIF 3658 3659 IF ( salsa .AND. nest_salsa ) THEN 3660 DO ib = 1, nbins_aerosol 3661 CALL pmci_anterp_tophat( aerosol_number(ib)%conc, aerosol_number_c(:,:,:,ib), & 3662 kcto, iflo, ifuo, jflo, jfuo, kflo, kfuo, ijkfc_s, 's' ) 3663 ENDDO 3664 DO ic = 1, nbins_aerosol * ncomponents_mass 3665 CALL pmci_anterp_tophat( aerosol_mass(ic)%conc, aerosol_mass_c(:,:,:,ic), & 3666 kcto, iflo, ifuo, jflo, jfuo, kflo, kfuo, ijkfc_s, 's' ) 3667 ENDDO 3668 IF ( .NOT. salsa_gases_from_chem ) THEN 3669 DO ig = 1, ngases_salsa 3670 CALL pmci_anterp_tophat( salsa_gas(ig)%conc, salsa_gas_c(:,:,:,ig), & 3671 kcto, iflo, ifuo, jflo, jfuo, kflo, kfuo, ijkfc_s, 's' ) 3672 ENDDO 3673 ENDIF 3421 3674 ENDIF 3422 3675 … … 4275 4528 ONLY: ibc_pt_b, ibc_q_b, ibc_s_b, ibc_uv_b 4276 4529 4530 USE salsa_mod, & 4531 ONLY: ibc_salsa_b 4532 4277 4533 USE surface_mod, & 4278 4534 ONLY: bc_h … … 4280 4536 IMPLICIT NONE 4281 4537 4282 INTEGER(iwp) :: i !< Index along x-direction 4283 INTEGER(iwp) :: j !< Index along y-direction 4284 INTEGER(iwp) :: k !< Index along z-direction 4285 INTEGER(iwp) :: m !< Running index for surface type 4286 INTEGER(iwp) :: n !< running index for number of chemical species 4287 4538 INTEGER(iwp) :: i !< Index along x-direction 4539 INTEGER(iwp) :: ib !< running index for aerosol size bins 4540 INTEGER(iwp) :: ic !< running index for aerosol mass bins 4541 INTEGER(iwp) :: ig !< running index for salsa gases 4542 INTEGER(iwp) :: j !< Index along y-direction 4543 INTEGER(iwp) :: k !< Index along z-direction 4544 INTEGER(iwp) :: m !< Running index for surface type 4545 INTEGER(iwp) :: n !< running index for number of chemical species 4546 4288 4547 ! 4289 4548 !-- Set Dirichlet boundary conditions for horizontal velocity components … … 4433 4692 ENDDO 4434 4693 ENDIF 4435 ENDIF 4694 ENDIF 4695 ! 4696 !-- Set Neumann boundary conditions for aerosols and salsa gases 4697 IF ( salsa .AND. nest_salsa ) THEN 4698 IF ( ibc_salsa_b == 1 ) THEN 4699 DO m = 1, bc_h(0)%ns 4700 i = bc_h(0)%i(m) 4701 j = bc_h(0)%j(m) 4702 k = bc_h(0)%k(m) 4703 DO ib = 1, nbins_aerosol 4704 aerosol_number(ib)%conc(k-1,j,i) = aerosol_number(ib)%conc(k,j,i) 4705 ENDDO 4706 DO ic = 1, nbins_aerosol * ncomponents_mass 4707 aerosol_mass(ic)%conc(k-1,j,i) = aerosol_mass(ic)%conc(k,j,i) 4708 ENDDO 4709 IF ( .NOT. salsa_gases_from_chem ) THEN 4710 DO ig = 1, ngases_salsa 4711 salsa_gas(ig)%conc(k-1,j,i) = salsa_gas(ig)%conc(k,j,i) 4712 ENDDO 4713 ENDIF 4714 ENDDO 4715 DO m = 1, bc_h(1)%ns 4716 i = bc_h(1)%i(m) 4717 j = bc_h(1)%j(m) 4718 k = bc_h(1)%k(m) 4719 DO ib = 1, nbins_aerosol 4720 aerosol_number(ib)%conc(k+1,j,i) = aerosol_number(ib)%conc(k,j,i) 4721 ENDDO 4722 DO ic = 1, nbins_aerosol * ncomponents_mass 4723 aerosol_mass(ic)%conc(k+1,j,i) = aerosol_mass(ic)%conc(k,j,i) 4724 ENDDO 4725 IF ( .NOT. salsa_gases_from_chem ) THEN 4726 DO ig = 1, ngases_salsa 4727 salsa_gas(ig)%conc(k+1,j,i) = salsa_gas(ig)%conc(k,j,i) 4728 ENDDO 4729 ENDIF 4730 ENDDO 4731 ENDIF 4732 ENDIF 4436 4733 4437 4734 END SUBROUTINE pmci_boundary_conds -
palm/trunk/SOURCE/prognostic_equations.f90
r3840 r3864 25 25 ! ----------------- 26 26 ! $Id$ 27 ! Modifications made for salsa: 28 ! - salsa_prognostic_equations moved to salsa_mod (and the call to 29 ! module_interface_mod) 30 ! - Renamed nbins --> nbins_aerosol, ncc_tot --> ncomponents_mass and 31 ! ngast --> ngases_salsa and loop indices b, c and sg to ib, ic and ig 32 ! 33 ! 3840 2019-03-29 10:35:52Z knoop 27 34 ! added USE chem_gasphase_mod for nvar, nspec and spc_names 28 35 ! … … 376 383 USE buoyancy_mod, & 377 384 ONLY: buoyancy 378 385 379 386 USE chem_modules, & 380 387 ONLY: call_chem_at_all_substeps, chem_gasphase_on, cs_name, & … … 447 454 skip_time_do_radiation 448 455 #endif 449 456 450 457 USE salsa_mod, & 451 ONLY: aerosol_mass, aerosol_number, dt_salsa, last_salsa_time, nbins,&452 n cc_tot, ngast, salsa_boundary_conds, salsa_diagnostics,&453 salsa_ driver, salsa_gas, salsa_gases_from_chem, salsa_tendency,&454 s kip_time_do_salsa455 458 ONLY: aerosol_mass, aerosol_number, dt_salsa, last_salsa_time, & 459 nbins_aerosol, ncomponents_mass, ngases_salsa, & 460 salsa_boundary_conds, salsa_diagnostics, salsa_driver, & 461 salsa_gas, salsa_gases_from_chem, skip_time_do_salsa 462 456 463 USE salsa_util_mod, & 457 ONLY: sums_salsa_ws_l 458 464 ONLY: sums_salsa_ws_l 465 459 466 USE statistics, & 460 467 ONLY: hom … … 506 513 507 514 IMPLICIT NONE 508 509 INTEGER(iwp) :: b !< index for aerosol size bins (salsa) 510 INTEGER(iwp) :: c !< index for chemical compounds (salsa) 511 INTEGER(iwp) :: g !< index for gaseous compounds (salsa) 515 512 516 INTEGER(iwp) :: i !< 513 517 INTEGER(iwp) :: i_omp_start !< 518 INTEGER(iwp) :: ib !< index for aerosol size bins (salsa) 519 INTEGER(iwp) :: ic !< index for chemical compounds (salsa) 520 INTEGER(iwp) :: icc !< additional index for chemical compounds (salsa) 521 INTEGER(iwp) :: ig !< index for gaseous compounds (salsa) 514 522 INTEGER(iwp) :: j !< 515 523 INTEGER(iwp) :: k !< … … 587 595 CALL cpu_log( log_point_s(84), 'chem.exch-horiz', 'stop' ) 588 596 589 ENDIF 597 ENDIF 590 598 ! 591 599 !-- Run SALSA and aerosol dynamic processes. SALSA is run with a longer time … … 593 601 !-- concentrations of aerosol number and mass 594 602 IF ( salsa ) THEN 595 596 IF ( time_since_reference_point >= skip_time_do_salsa ) THEN 603 604 IF ( time_since_reference_point >= skip_time_do_salsa ) THEN 597 605 IF ( ( time_since_reference_point - last_salsa_time ) >= dt_salsa ) & 598 606 THEN 599 607 CALL cpu_log( log_point_s(90), 'salsa processes ', 'start' ) 600 !$OMP PARALLEL PRIVATE (i,j, b,c,g)608 !$OMP PARALLEL PRIVATE (i,j,ib,ic,icc,ig) 601 609 !$OMP DO 602 610 ! … … 609 617 ENDDO 610 618 ENDDO 611 619 612 620 CALL cpu_log( log_point_s(90), 'salsa processes ', 'stop' ) 613 621 … … 615 623 ! 616 624 !-- Exchange ghost points and decycle if needed. 617 DO b = 1, nbins618 CALL exchange_horiz( aerosol_number( b)%conc, nbgp )619 CALL salsa_boundary_conds( aerosol_number( b)%conc_p,&620 aerosol_number( b)%init )621 DO c = 1, ncc_tot622 CALL exchange_horiz( aerosol_mass((c-1)*nbins+b)%conc, nbgp )623 CALL salsa_boundary_conds( &624 aerosol_mass((c-1)*nbins+b)%conc_p,&625 aerosol_mass((c-1)*nbins+b)%init )626 ENDDO 627 ENDDO 628 625 DO ib = 1, nbins_aerosol 626 CALL exchange_horiz( aerosol_number(ib)%conc, nbgp ) 627 CALL salsa_boundary_conds( aerosol_number(ib)%conc, & 628 aerosol_number(ib)%init ) 629 DO ic = 1, ncomponents_mass 630 icc = ( ic - 1 ) * nbins_aerosol + ib 631 CALL exchange_horiz( aerosol_mass(icc)%conc, nbgp ) 632 CALL salsa_boundary_conds( aerosol_mass(icc)%conc, & 633 aerosol_mass(icc)%init ) 634 ENDDO 635 ENDDO 636 629 637 IF ( .NOT. salsa_gases_from_chem ) THEN 630 DO g = 1, ngast631 CALL exchange_horiz( salsa_gas( g)%conc, nbgp )632 CALL salsa_boundary_conds( salsa_gas( g)%conc_p,&633 salsa_gas( g)%init )638 DO ig = 1, ngases_salsa 639 CALL exchange_horiz( salsa_gas(ig)%conc, nbgp ) 640 CALL salsa_boundary_conds( salsa_gas(ig)%conc, & 641 salsa_gas(ig)%init ) 634 642 ENDDO 635 643 ENDIF … … 638 646 !$OMP END PARALLEL 639 647 last_salsa_time = time_since_reference_point 640 641 ENDIF 642 643 ENDIF 644 648 649 ENDIF 650 651 ENDIF 652 645 653 ENDIF 646 654 … … 1442 1450 chem_species(lsp)%diss_l_cs ) 1443 1451 ENDDO 1444 1452 1445 1453 ENDIF ! Chemical equations 1446 1447 IF ( salsa ) THEN1448 !1449 !-- Loop over aerosol size bins: number and mass bins1450 IF ( time_since_reference_point >= skip_time_do_salsa ) THEN1451 1452 DO b = 1, nbins1453 sums_salsa_ws_l = aerosol_number(b)%sums_ws_l1454 CALL salsa_tendency( 'aerosol_number', &1455 aerosol_number(b)%conc_p, &1456 aerosol_number(b)%conc, &1457 aerosol_number(b)%tconc_m, &1458 i, j, i_omp_start, tn, b, b, &1459 aerosol_number(b)%flux_s, &1460 aerosol_number(b)%diss_s, &1461 aerosol_number(b)%flux_l, &1462 aerosol_number(b)%diss_l, &1463 aerosol_number(b)%init )1464 aerosol_number(b)%sums_ws_l = sums_salsa_ws_l1465 DO c = 1, ncc_tot1466 sums_salsa_ws_l = aerosol_mass((c-1)*nbins+b)%sums_ws_l1467 CALL salsa_tendency( 'aerosol_mass', &1468 aerosol_mass((c-1)*nbins+b)%conc_p,&1469 aerosol_mass((c-1)*nbins+b)%conc, &1470 aerosol_mass((c-1)*nbins+b)%tconc_m,&1471 i, j, i_omp_start, tn, b, c, &1472 aerosol_mass((c-1)*nbins+b)%flux_s,&1473 aerosol_mass((c-1)*nbins+b)%diss_s,&1474 aerosol_mass((c-1)*nbins+b)%flux_l,&1475 aerosol_mass((c-1)*nbins+b)%diss_l,&1476 aerosol_mass((c-1)*nbins+b)%init )1477 aerosol_mass((c-1)*nbins+b)%sums_ws_l = sums_salsa_ws_l1478 ENDDO1479 ENDDO1480 IF ( .NOT. salsa_gases_from_chem ) THEN1481 DO g = 1, ngast1482 sums_salsa_ws_l = salsa_gas(g)%sums_ws_l1483 CALL salsa_tendency( 'salsa_gas', salsa_gas(g)%conc_p, &1484 salsa_gas(g)%conc, salsa_gas(g)%tconc_m, &1485 i, j, i_omp_start, tn, g, g, &1486 salsa_gas(g)%flux_s, salsa_gas(g)%diss_s,&1487 salsa_gas(g)%flux_l, salsa_gas(g)%diss_l,&1488 salsa_gas(g)%init )1489 salsa_gas(g)%sums_ws_l = sums_salsa_ws_l1490 ENDDO1491 ENDIF1492 1493 ENDIF1494 1495 ENDIF1496 1454 1497 1455 ENDDO ! loop over j … … 1517 1475 IMPLICIT NONE 1518 1476 1519 INTEGER(iwp) :: b !< index for aerosol size bins (salsa)1520 INTEGER(iwp) :: c !< index for chemical compounds (salsa)1521 INTEGER(iwp) :: g !< index for gaseous compounds (salsa)1522 1477 INTEGER(iwp) :: i !< 1478 INTEGER(iwp) :: ib !< index for aerosol size bins (salsa) 1479 INTEGER(iwp) :: ic !< index for chemical compounds (salsa) 1480 INTEGER(iwp) :: icc !< additional index for chemical compounds (salsa) 1481 INTEGER(iwp) :: ig !< index for gaseous compounds (salsa) 1523 1482 INTEGER(iwp) :: j !< 1524 1483 INTEGER(iwp) :: k !< … … 1532 1491 !-- concentrations of aerosol number and mass 1533 1492 IF ( salsa ) THEN 1534 1535 1493 IF ( time_since_reference_point >= skip_time_do_salsa ) THEN 1536 1537 1494 IF ( ( time_since_reference_point - last_salsa_time ) >= dt_salsa ) & 1538 1495 THEN 1539 1540 1496 CALL cpu_log( log_point_s(90), 'salsa processes ', 'start' ) 1541 !$OMP PARALLEL PRIVATE (i,j, b,c,g)1497 !$OMP PARALLEL PRIVATE (i,j,ib,ic,icc,ig) 1542 1498 !$OMP DO 1543 1499 ! … … 1550 1506 ENDDO 1551 1507 ENDDO 1552 1508 1553 1509 CALL cpu_log( log_point_s(90), 'salsa processes ', 'stop' ) 1554 1555 1510 CALL cpu_log( log_point_s(91), 'salsa exch-horiz ', 'start' ) 1556 1511 ! 1557 1512 !-- Exchange ghost points and decycle if needed. 1558 DO b = 1, nbins 1559 CALL exchange_horiz( aerosol_number(b)%conc, nbgp ) 1560 CALL salsa_boundary_conds( aerosol_number(b)%conc_p, & 1561 aerosol_number(b)%init ) 1562 DO c = 1, ncc_tot 1563 CALL exchange_horiz( aerosol_mass((c-1)*nbins+b)%conc, nbgp ) 1564 CALL salsa_boundary_conds( & 1565 aerosol_mass((c-1)*nbins+b)%conc_p, & 1566 aerosol_mass((c-1)*nbins+b)%init ) 1567 ENDDO 1568 ENDDO 1569 1513 DO ib = 1, nbins_aerosol 1514 CALL exchange_horiz( aerosol_number(ib)%conc, nbgp ) 1515 CALL salsa_boundary_conds( aerosol_number(ib)%conc, & 1516 aerosol_number(ib)%init ) 1517 DO ic = 1, ncomponents_mass 1518 icc = ( ic - 1 ) * nbins_aerosol + ib 1519 CALL exchange_horiz( aerosol_mass(icc)%conc, nbgp ) 1520 CALL salsa_boundary_conds( aerosol_mass(icc)%conc, & 1521 aerosol_mass(icc)%init ) 1522 ENDDO 1523 ENDDO 1570 1524 IF ( .NOT. salsa_gases_from_chem ) THEN 1571 DO g = 1, ngast1572 CALL exchange_horiz( salsa_gas( g)%conc, nbgp )1573 CALL salsa_boundary_conds( salsa_gas( g)%conc_p,&1574 salsa_gas( g)%init )1525 DO ig = 1, ngases_salsa 1526 CALL exchange_horiz( salsa_gas(ig)%conc, nbgp ) 1527 CALL salsa_boundary_conds( salsa_gas(ig)%conc, & 1528 salsa_gas(ig)%init ) 1575 1529 ENDDO 1576 1530 ENDIF 1577 1531 CALL cpu_log( log_point_s(91), 'salsa exch-horiz ', 'stop' ) 1578 1579 1532 !$OMP END PARALLEL 1580 1533 last_salsa_time = time_since_reference_point 1581 1582 ENDIF 1583 1584 ENDIF 1585 1534 ENDIF 1535 ENDIF 1586 1536 ENDIF 1587 1537 … … 2661 2611 CALL cpu_log( log_point_s(25), 'chem.advec+diff+prog', 'stop' ) 2662 2612 ENDIF ! Chemicals equations 2663 2664 IF ( salsa ) THEN2665 CALL cpu_log( log_point_s(92), 'salsa advec+diff+prog ', 'start' )2666 !2667 !-- Loop over aerosol size bins: number and mass bins2668 IF ( time_since_reference_point >= skip_time_do_salsa ) THEN2669 2670 DO b = 1, nbins2671 sums_salsa_ws_l = aerosol_number(b)%sums_ws_l2672 CALL salsa_tendency( 'aerosol_number', aerosol_number(b)%conc_p, &2673 aerosol_number(b)%conc, &2674 aerosol_number(b)%tconc_m, &2675 b, b, aerosol_number(b)%init )2676 aerosol_number(b)%sums_ws_l = sums_salsa_ws_l2677 DO c = 1, ncc_tot2678 sums_salsa_ws_l = aerosol_mass((c-1)*nbins+b)%sums_ws_l2679 CALL salsa_tendency( 'aerosol_mass', &2680 aerosol_mass((c-1)*nbins+b)%conc_p, &2681 aerosol_mass((c-1)*nbins+b)%conc, &2682 aerosol_mass((c-1)*nbins+b)%tconc_m, &2683 b, c, aerosol_mass((c-1)*nbins+b)%init )2684 aerosol_mass((c-1)*nbins+b)%sums_ws_l = sums_salsa_ws_l2685 ENDDO2686 ENDDO2687 IF ( .NOT. salsa_gases_from_chem ) THEN2688 DO g = 1, ngast2689 sums_salsa_ws_l = salsa_gas(g)%sums_ws_l2690 CALL salsa_tendency( 'salsa_gas', salsa_gas(g)%conc_p, &2691 salsa_gas(g)%conc, salsa_gas(g)%tconc_m, &2692 g, g, salsa_gas(g)%init )2693 salsa_gas(g)%sums_ws_l = sums_salsa_ws_l2694 ENDDO2695 ENDIF2696 2697 ENDIF2698 2699 CALL cpu_log( log_point_s(92), 'salsa advec+diff+prog ', 'stop' )2700 ENDIF2701 2702 2613 2703 2614 END SUBROUTINE prognostic_equations_vector -
palm/trunk/SOURCE/salsa_mod.f90
r3833 r3864 26 26 ! ----------------- 27 27 ! $Id$ 28 ! Major changes in formatting, performance and data input structure (see branch 29 ! the history for details) 30 ! - Time-dependent emissions enabled: lod=1 for yearly PM emissions that are 31 ! normalised depending on the time, and lod=2 for preprocessed emissions 32 ! (similar to the chemistry module). 33 ! - Additionally, 'uniform' emissions allowed. This emission is set constant on 34 ! all horisontal upward facing surfaces and it is created based on parameters 35 ! surface_aerosol_flux, aerosol_flux_dpg/sigmag/mass_fracs_a/mass_fracs_b. 36 ! - All emissions are now implemented as surface fluxes! No 3D sources anymore. 37 ! - Update the emission information by calling salsa_emission_update if 38 ! skip_time_do_salsa >= time_since_reference_point and 39 ! next_aero_emission_update <= time_since_reference_point 40 ! - Aerosol background concentrations read from PIDS_DYNAMIC. The vertical grid 41 ! must match the one applied in the model. 42 ! - Gas emissions and background concentrations can be also read in in salsa_mod 43 ! if the chemistry module is not applied. 44 ! - In deposition, information on the land use type can be now imported from 45 ! the land use model 46 ! - Use SI units in PARIN, i.e. n_lognorm given in #/m3 and dpg in metres. 47 ! - Apply 100 character line limit 48 ! - Change all variable names from capital to lowercase letter 49 ! - Change real exponents to integer if possible. If not, precalculate the value 50 ! value of exponent 51 ! - Rename in1a to start_subrange_1a, fn2a to end_subrange_1a etc. 52 ! - Rename nbins --> nbins_aerosol, ncc_tot --> ncomponents_mass and ngast --> 53 ! ngases_salsa 54 ! - Rename ibc to index_bc, idu to index_du etc. 55 ! - Renamed loop indices b, c and sg to ib, ic and ig 56 ! - run_salsa subroutine removed 57 ! - Corrected a bud in salsa_driver: falsely applied ino instead of inh 58 ! - Call salsa_tendency within salsa_prognostic_equations which is called in 59 ! module_interface_mod instead of prognostic_equations_mod 60 ! - Removed tailing white spaces and unused variables 61 ! - Change error message to start by PA instead of SA 62 ! 63 ! 3833 2019-03-28 15:04:04Z forkel 28 64 ! added USE chem_gasphase_mod for nvar, nspec and spc_names 29 65 ! … … 71 107 ! -------- 72 108 ! @author Mona Kurppa (University of Helsinki) 73 ! 109 ! 74 110 ! 75 111 ! Description: 76 112 ! ------------ 77 !> Sectional aerosol module for large scale applications SALSA 113 !> Sectional aerosol module for large scale applications SALSA 78 114 !> (Kokkola et al., 2008, ACP 8, 2469-2483). Solves the aerosol number and mass 79 !> concentration as well as chemical composition. Includes aerosol dynamic 115 !> concentration as well as chemical composition. Includes aerosol dynamic 80 116 !> processes: nucleation, condensation/evaporation of vapours, coagulation and 81 !> deposition on tree leaves, ground and roofs. 117 !> deposition on tree leaves, ground and roofs. 82 118 !> Implementation is based on formulations implemented in UCLALES-SALSA except 83 !> for deposition which is based on parametrisations by Zhang et al. (2001, 84 !> Atmos. Environ. 35, 549-560) or Petroff&Zhang (2010, Geosci. Model Dev. 3, 119 !> for deposition which is based on parametrisations by Zhang et al. (2001, 120 !> Atmos. Environ. 35, 549-560) or Petroff&Zhang (2010, Geosci. Model Dev. 3, 85 121 !> 753-769) 86 122 !> 87 !> @todo Implement turbulent inflow of aerosols in inflow_turbulence. 88 !> @todo Deposition on subgrid scale vegetation 89 !> @todo Deposition on vegetation calculated by default for deciduous broadleaf 90 !> trees 91 !> @todo Revise masked data output. There is a potential bug in case of 92 !> terrain-following masked output, according to data_output_mask. 93 !> @todo There are now improved interfaces for NetCDF data input which can be 94 !> used instead of get variable etc. 123 !> @todo Apply information from emission_stack_height to lift emission sources 124 !> @todo emission mode "parameterized", i.e. based on street type 95 125 !------------------------------------------------------------------------------! 96 126 MODULE salsa_mod … … 98 128 USE basic_constants_and_equations_mod, & 99 129 ONLY: c_p, g, p_0, pi, r_d 100 130 101 131 USE chem_gasphase_mod, & 102 132 ONLY: nspec, nvar, spc_names … … 113 143 ONLY: nbgp, nx, nxl, nxlg, nxr, nxrg, ny, nyn, nyng, nys, nysg, nzb, & 114 144 nzb_s_inner, nz, nzt, wall_flags_0 115 145 116 146 USE kinds 117 147 118 148 USE pegrid 119 149 120 150 USE salsa_util_mod 121 151 … … 125 155 ! 126 156 !-- Local constants: 127 INTEGER(iwp), PARAMETER :: ngast = 5 !< total number of gaseous tracers: 128 !< 1 = H2SO4, 2 = HNO3, 3 = NH3, 129 !< 4 = OCNV (non-volatile OC), 130 !< 5 = OCSV (semi-volatile) 131 INTEGER(iwp), PARAMETER :: nmod = 7 !< number of modes for initialising 132 !< the aerosol size distribution 133 INTEGER(iwp), PARAMETER :: nreg = 2 !< Number of main size subranges 134 INTEGER(iwp), PARAMETER :: maxspec = 7 !< Max. number of aerosol species 135 ! 157 INTEGER(iwp), PARAMETER :: luc_urban = 8 !< default landuse type for urban: use desert! 158 INTEGER(iwp), PARAMETER :: ngases_salsa = 5 !< total number of gaseous tracers: 159 !< 1 = H2SO4, 2 = HNO3, 3 = NH3, 4 = OCNV 160 !< (non-volatile OC), 5 = OCSV (semi-volatile) 161 INTEGER(iwp), PARAMETER :: nmod = 7 !< number of modes for initialising the aerosol size 162 !< distribution 163 INTEGER(iwp), PARAMETER :: nreg = 2 !< Number of main size subranges 164 INTEGER(iwp), PARAMETER :: maxspec = 7 !< Max. number of aerosol species 165 INTEGER(iwp), PARAMETER :: season = 1 !< For dry depostion by Zhang et al.: 1 = summer, 166 !< 2 = autumn (no harvest yet), 3 = late autumn 167 !< (already frost), 4 = winter, 5 = transitional spring 168 ! 136 169 !-- Universal constants 137 REAL(wp), PARAMETER :: abo = 1.380662E-23_wp !< Boltzmann constant (J/K) 138 REAL(wp), PARAMETER :: alv = 2.260E+6_wp !< latent heat for H2O 139 !< vaporisation (J/kg) 140 REAL(wp), PARAMETER :: alv_d_rv = 4896.96865_wp !< alv / rv 141 REAL(wp), PARAMETER :: am_airmol = 4.8096E-26_wp !< Average mass of one air 142 !< molecule (Jacobson, 143 !< 2005, Eq. 2.3) 144 REAL(wp), PARAMETER :: api6 = 0.5235988_wp !< pi / 6 145 REAL(wp), PARAMETER :: argas = 8.314409_wp !< Gas constant (J/(mol K)) 146 REAL(wp), PARAMETER :: argas_d_cpd = 8.281283865E-3_wp !< argas per cpd 147 REAL(wp), PARAMETER :: avo = 6.02214E+23_wp !< Avogadro constant (1/mol) 148 REAL(wp), PARAMETER :: d_sa = 5.539376964394570E-10_wp !< diameter of 149 !< condensing sulphuric 150 !< acid molecule (m) 151 REAL(wp), PARAMETER :: for_ppm_to_nconc = 7.243016311E+16_wp !< 152 !< ppm * avo / R (K/(Pa*m3)) 170 REAL(wp), PARAMETER :: abo = 1.380662E-23_wp !< Boltzmann constant (J/K) 171 REAL(wp), PARAMETER :: alv = 2.260E+6_wp !< latent heat for H2O 172 !< vaporisation (J/kg) 173 REAL(wp), PARAMETER :: alv_d_rv = 4896.96865_wp !< alv / rv 174 REAL(wp), PARAMETER :: am_airmol = 4.8096E-26_wp !< Average mass of one air 175 !< molecule (Jacobson, 176 !< 2005, Eq. 2.3) 177 REAL(wp), PARAMETER :: api6 = 0.5235988_wp !< pi / 6 178 REAL(wp), PARAMETER :: argas = 8.314409_wp !< Gas constant (J/(mol K)) 179 REAL(wp), PARAMETER :: argas_d_cpd = 8.281283865E-3_wp !< argas per cpd 180 REAL(wp), PARAMETER :: avo = 6.02214E+23_wp !< Avogadro constant (1/mol) 181 REAL(wp), PARAMETER :: d_sa = 5.539376964394570E-10_wp !< diameter of condensing sulphuric 182 !< acid molecule (m) 183 REAL(wp), PARAMETER :: for_ppm_to_nconc = 7.243016311E+16_wp !< ppm * avo / R (K/(Pa*m3)) 153 184 REAL(wp), PARAMETER :: epsoc = 0.15_wp !< water uptake of organic 154 !< material 155 REAL(wp), PARAMETER :: mclim = 1.0E-23_wp !< mass concentration min 156 !< limit for aerosols (kg/m3) 157 REAL(wp), PARAMETER :: n3 = 158.79_wp !< Number of H2SO4 molecules in 158 !< 3 nm cluster if d_sa=5.54e-10m 159 REAL(wp), PARAMETER :: nclim = 1.0_wp !< number concentration min limit 160 !< for aerosols and gases (#/m3) 161 REAL(wp), PARAMETER :: surfw0 = 0.073_wp !< surface tension of pure water 162 !< at ~ 293 K (J/m2) 163 REAL(wp), PARAMETER :: vclim = 1.0E-24_wp !< volume concentration min 164 !< limit for aerosols (m3/m3) 185 !< material 186 REAL(wp), PARAMETER :: mclim = 1.0E-23_wp !< mass concentration min limit (kg/m3) 187 REAL(wp), PARAMETER :: n3 = 158.79_wp !< Number of H2SO4 molecules in 3 nm cluster 188 !< if d_sa=5.54e-10m 189 REAL(wp), PARAMETER :: nclim = 1.0_wp !< number concentration min limit (#/m3) 190 REAL(wp), PARAMETER :: surfw0 = 0.073_wp !< surface tension of water at 293 K (J/m2) 191 ! 165 192 !-- Molar masses in kg/mol 166 193 REAL(wp), PARAMETER :: ambc = 12.0E-3_wp !< black carbon (BC) 167 194 REAL(wp), PARAMETER :: amdair = 28.970E-3_wp !< dry air 168 REAL(wp), PARAMETER :: amdu = 100.E-3_wp !< mineral dust 195 REAL(wp), PARAMETER :: amdu = 100.E-3_wp !< mineral dust 169 196 REAL(wp), PARAMETER :: amh2o = 18.0154E-3_wp !< H2O 170 197 REAL(wp), PARAMETER :: amh2so4 = 98.06E-3_wp !< H2SO4 … … 176 203 REAL(wp), PARAMETER :: amoc = 150.E-3_wp !< organic carbon (OC) 177 204 REAL(wp), PARAMETER :: amss = 58.44E-3_wp !< sea salt (NaCl) 205 ! 178 206 !-- Densities in kg/m3 179 REAL(wp), PARAMETER :: arhobc = 2000.0_wp !< black carbon 180 REAL(wp), PARAMETER :: arhodu = 2650.0_wp !< mineral dust 181 REAL(wp), PARAMETER :: arhoh2o = 1000.0_wp !< H2O 182 REAL(wp), PARAMETER :: arhoh2so4 = 1830.0_wp !< SO4 183 REAL(wp), PARAMETER :: arhohno3 = 1479.0_wp !< HNO3 184 REAL(wp), PARAMETER :: arhonh3 = 1530.0_wp !< NH3 185 REAL(wp), PARAMETER :: arhooc = 2000.0_wp !< organic carbon 186 REAL(wp), PARAMETER :: arhoss = 2165.0_wp !< sea salt (NaCl) 207 REAL(wp), PARAMETER :: arhobc = 2000.0_wp !< black carbon 208 REAL(wp), PARAMETER :: arhodu = 2650.0_wp !< mineral dust 209 REAL(wp), PARAMETER :: arhoh2o = 1000.0_wp !< H2O 210 REAL(wp), PARAMETER :: arhoh2so4 = 1830.0_wp !< SO4 211 REAL(wp), PARAMETER :: arhohno3 = 1479.0_wp !< HNO3 212 REAL(wp), PARAMETER :: arhonh3 = 1530.0_wp !< NH3 213 REAL(wp), PARAMETER :: arhooc = 2000.0_wp !< organic carbon 214 REAL(wp), PARAMETER :: arhoss = 2165.0_wp !< sea salt (NaCl) 215 ! 187 216 !-- Volume of molecule in m3/# 188 217 REAL(wp), PARAMETER :: amvh2o = amh2o /avo / arhoh2o !< H2O 189 218 REAL(wp), PARAMETER :: amvh2so4 = amh2so4 / avo / arhoh2so4 !< SO4 190 REAL(wp), PARAMETER :: amvhno3 = amhno3 / avo / arhohno3 !< HNO3 191 REAL(wp), PARAMETER :: amvnh3 = amnh3 / avo / arhonh3 !< NH3 219 REAL(wp), PARAMETER :: amvhno3 = amhno3 / avo / arhohno3 !< HNO3 220 REAL(wp), PARAMETER :: amvnh3 = amnh3 / avo / arhonh3 !< NH3 192 221 REAL(wp), PARAMETER :: amvoc = amoc / avo / arhooc !< OC 193 222 REAL(wp), PARAMETER :: amvss = amss / avo / arhoss !< sea salt 194 223 ! 224 !-- Constants for the dry deposition model by Petroff and Zhang (2010): 225 !-- obstacle characteristic dimension "L" (cm) (plane obstacle by default) and empirical constants 226 !-- C_B, C_IN, C_IM, beta_IM and C_IT for each land use category (15, as in Zhang et al. (2001)) 227 REAL(wp), DIMENSION(1:15), PARAMETER :: l_p10 = & 228 (/0.15, 4.0, 0.15, 3.0, 3.0, 0.5, 3.0, -99., 0.5, 2.0, 1.0, -99., -99., -99., 3.0/) 229 REAL(wp), DIMENSION(1:15), PARAMETER :: c_b_p10 = & 230 (/0.887, 1.262, 0.887, 1.262, 1.262, 0.996, 0.996, -99., 0.7, 0.93, 0.996, -99., -99., -99., 1.262/) 231 REAL(wp), DIMENSION(1:15), PARAMETER :: c_in_p10 = & 232 (/0.81, 0.216, 0.81, 0.216, 0.216, 0.191, 0.162, -99., 0.7, 0.14, 0.162, -99., -99., -99., 0.216/) 233 REAL(wp), DIMENSION(1:15), PARAMETER :: c_im_p10 = & 234 (/0.162, 0.13, 0.162, 0.13, 0.13, 0.191, 0.081, -99., 0.191, 0.086, 0.081, -99., -99., -99., 0.13/) 235 REAL(wp), DIMENSION(1:15), PARAMETER :: beta_im_p10 = & 236 (/0.6, 0.47, 0.6, 0.47, 0.47, 0.47, 0.47, -99., 0.6, 0.47, 0.47, -99., -99., -99., 0.47/) 237 REAL(wp), DIMENSION(1:15), PARAMETER :: c_it_p10 = & 238 (/0.0, 0.056, 0.0, 0.056, 0.056, 0.042, 0.056, -99., 0.042, 0.014, 0.056, -99., -99., -99., 0.056/) 239 ! 240 !-- Constants for the dry deposition model by Zhang et al. (2001): 241 !-- empirical constants "alpha" and "gamma" and characteristic radius "A" for 242 !-- each land use category (15) and season (5) 243 REAL(wp), DIMENSION(1:15), PARAMETER :: alpha_z01 = & 244 (/1.0, 0.6, 1.1, 0.8, 0.8, 1.2, 1.2, 50.0, 50.0, 1.3, 2.0, 50.0, 100.0, 100.0, 1.5/) 245 REAL(wp), DIMENSION(1:15), PARAMETER :: gamma_z01 = & 246 (/0.56, 0.58, 0.56, 0.56, 0.56, 0.54, 0.54, 0.54, 0.54, 0.54, 0.54, 0.54, 0.50, 0.50, 0.56/) 247 REAL(wp), DIMENSION(1:15,1:5), PARAMETER :: A_z01 = RESHAPE( (/& 248 2.0, 5.0, 2.0, 5.0, 5.0, 2.0, 2.0, -99., -99., 10.0, 10.0, -99., -99., -99., 10.0,& ! SC1 249 2.0, 5.0, 2.0, 5.0, 5.0, 2.0, 2.0, -99., -99., 10.0, 10.0, -99., -99., -99., 10.0,& ! SC2 250 2.0, 5.0, 5.0, 10.0, 5.0, 5.0, 5.0, -99., -99., 10.0, 10.0, -99., -99., -99., 10.0,& ! SC3 251 2.0, 5.0, 5.0, 10.0, 5.0, 5.0, 5.0, -99., -99., 10.0, 10.0, -99., -99., -99., 10.0,& ! SC4 252 2.0, 5.0, 2.0, 5.0, 5.0, 2.0, 2.0, -99., -99., 10.0, 10.0, -99., -99., -99., 10.0 & ! SC5 253 /), (/ 15, 5 /) ) 254 !-- Land use categories (based on Z01 but the same applies here also for P10): 255 !-- 1 = evergreen needleleaf trees, 256 !-- 2 = evergreen broadleaf trees, 257 !-- 3 = deciduous needleleaf trees, 258 !-- 4 = deciduous broadleaf trees, 259 !-- 5 = mixed broadleaf and needleleaf trees (deciduous broadleaf trees for P10), 260 !-- 6 = grass (short grass for P10), 261 !-- 7 = crops, mixed farming, 262 !-- 8 = desert, 263 !-- 9 = tundra, 264 !-- 10 = shrubs and interrupted woodlands (thorn shrubs for P10), 265 !-- 11 = wetland with plants (long grass for P10) 266 !-- 12 = ice cap and glacier, 267 !-- 13 = inland water (inland lake for P10) 268 !-- 14 = ocean (water for P10), 269 !-- 15 = urban 270 ! 271 !-- SALSA variables: 272 CHARACTER(LEN=20) :: bc_salsa_b = 'neumann' !< bottom boundary condition 273 CHARACTER(LEN=20) :: bc_salsa_t = 'neumann' !< top boundary condition 274 CHARACTER(LEN=20) :: depo_pcm_par = 'zhang2001' !< or 'petroff2010' 275 CHARACTER(LEN=20) :: depo_pcm_type = 'deciduous_broadleaf' !< leaf type 276 CHARACTER(LEN=20) :: depo_surf_par = 'zhang2001' !< or 'petroff2010' 277 CHARACTER(LEN=100) :: input_file_dynamic = 'PIDS_DYNAMIC' !< file name for dynamic input 278 CHARACTER(LEN=100) :: input_file_salsa = 'PIDS_SALSA' !< file name for emission data 279 CHARACTER(LEN=20) :: salsa_emission_mode = 'no_emission' !< 'no_emission', 'uniform', 280 !< 'parameterized', 'read_from_file' 281 282 CHARACTER(LEN=20), DIMENSION(4) :: decycle_method = & 283 (/'dirichlet','dirichlet','dirichlet','dirichlet'/) 284 !< Decycling method at horizontal boundaries 285 !< 1=left, 2=right, 3=south, 4=north 286 !< dirichlet = initial profiles for the ghost and first 3 layers 287 !< neumann = zero gradient 288 289 CHARACTER(LEN=3), DIMENSION(maxspec) :: listspec = & !< Active aerosols 290 (/'SO4',' ',' ',' ',' ',' ',' '/) 291 292 INTEGER(iwp) :: depo_pcm_type_num = 0 !< index for the dry deposition type on the plant canopy 293 INTEGER(iwp) :: dots_salsa = 0 !< starting index for salsa-timeseries 294 INTEGER(iwp) :: end_subrange_1a = 1 !< last index for bin subrange 1a 295 INTEGER(iwp) :: end_subrange_2a = 1 !< last index for bin subrange 2a 296 INTEGER(iwp) :: end_subrange_2b = 1 !< last index for bin subrange 2b 297 INTEGER(iwp) :: ibc_salsa_b !< index for the bottom boundary condition 298 INTEGER(iwp) :: ibc_salsa_t !< index for the top boundary condition 299 INTEGER(iwp) :: index_bc = -1 !< index for black carbon (BC) 300 INTEGER(iwp) :: index_du = -1 !< index for dust 301 INTEGER(iwp) :: igctyp = 0 !< Initial gas concentration type 302 !< 0 = uniform (read from PARIN) 303 !< 1 = read vertical profile from an input file 304 INTEGER(iwp) :: index_nh = -1 !< index for NH3 305 INTEGER(iwp) :: index_no = -1 !< index for HNO3 306 INTEGER(iwp) :: index_oc = -1 !< index for organic carbon (OC) 307 INTEGER(iwp) :: isdtyp = 0 !< Initial size distribution type 308 !< 0 = uniform (read from PARIN) 309 !< 1 = read vertical profile of the mode number 310 !< concentration from an input file 311 INTEGER(iwp) :: index_so4 = -1 !< index for SO4 or H2SO4 312 INTEGER(iwp) :: index_ss = -1 !< index for sea salt 313 INTEGER(iwp) :: lod_gas_emissions = 0 !< level of detail of the gaseous emission data 314 INTEGER(iwp) :: nbins_aerosol = 1 !< total number of size bins 315 INTEGER(iwp) :: ncc = 1 !< number of chemical components used 316 INTEGER(iwp) :: ncomponents_mass = 1 !< total number of chemical compounds (ncc+1) 317 !< if particle water is advected) 318 INTEGER(iwp) :: nj3 = 1 !< J3 parametrization (nucleation) 319 !< 1 = condensational sink (Kerminen&Kulmala, 2002) 320 !< 2 = coagulational sink (Lehtinen et al. 2007) 321 !< 3 = coagS+self-coagulation (Anttila et al. 2010) 322 INTEGER(iwp) :: nsnucl = 0 !< Choice of the nucleation scheme: 323 !< 0 = off 324 !< 1 = binary nucleation 325 !< 2 = activation type nucleation 326 !< 3 = kinetic nucleation 327 !< 4 = ternary nucleation 328 !< 5 = nucleation with ORGANICs 329 !< 6 = activation type of nucleation with H2SO4+ORG 330 !< 7 = heteromolecular nucleation with H2SO4*ORG 331 !< 8 = homomolecular nucleation of H2SO4 332 !< + heteromolecular nucleation with H2SO4*ORG 333 !< 9 = homomolecular nucleation of H2SO4 and ORG 334 !< + heteromolecular nucleation with H2SO4*ORG 335 INTEGER(iwp) :: start_subrange_1a = 1 !< start index for bin subranges: subrange 1a 336 INTEGER(iwp) :: start_subrange_2a = 1 !< subrange 2a 337 INTEGER(iwp) :: start_subrange_2b = 1 !< subrange 2b 338 339 INTEGER(iwp), DIMENSION(nreg) :: nbin = (/ 3, 7/) !< Number of size bins per subrange: 1 & 2 340 341 INTEGER(iwp), DIMENSION(ngases_salsa) :: gas_index_chem = & 342 (/ 1, 1, 1, 1, 1/) !< gas indices in chemistry_model_mod 343 !< 1 = H2SO4, 2 = HNO3, 3 = NH3, 4 = OCNV, 5 = OCSV 344 INTEGER(iwp), DIMENSION(ngases_salsa) :: emission_index_chem !< gas indices in the gas emission file 345 346 INTEGER(iwp), DIMENSION(:,:), ALLOCATABLE :: k_topo_top !< vertical index of the topography top 195 347 ! 196 348 !-- SALSA switches: 197 INTEGER(iwp) :: nj3 = 1 !< J3 parametrization (nucleation) 198 !< 1 = condensational sink (Kerminen&Kulmala, 2002) 199 !< 2 = coagulational sink (Lehtinen et al. 2007) 200 !< 3 = coagS+self-coagulation (Anttila et al. 2010) 201 INTEGER(iwp) :: nsnucl = 0 !< Choice of the nucleation scheme: 202 !< 0 = off 203 !< 1 = binary nucleation 204 !< 2 = activation type nucleation 205 !< 3 = kinetic nucleation 206 !< 4 = ternary nucleation 207 !< 5 = nucleation with ORGANICs 208 !< 6 = activation type of nucleation with 209 !< H2SO4+ORG 210 !< 7 = heteromolecular nucleation with H2SO4*ORG 211 !< 8 = homomolecular nucleation of H2SO4 + 212 !< heteromolecular nucleation with H2SO4*ORG 213 !< 9 = homomolecular nucleation of H2SO4 and ORG 214 !< +heteromolecular nucleation with H2SO4*ORG 215 LOGICAL :: advect_particle_water = .TRUE. !< advect water concentration of 216 !< particles 217 LOGICAL :: decycle_lr = .FALSE. !< Undo cyclic boundary 218 !< conditions: left and right 219 LOGICAL :: decycle_ns = .FALSE. !< north and south boundaries 220 LOGICAL :: feedback_to_palm = .FALSE. !< allow feedback due to 221 !< hydration and/or condensation 222 !< of H20 223 LOGICAL :: no_insoluble = .FALSE. !< Switch to exclude insoluble 224 !< chemical components 225 LOGICAL :: read_restart_data_salsa = .FALSE. !< read restart data for salsa 226 LOGICAL :: salsa_gases_from_chem = .FALSE. !< Transfer the gaseous 227 !< components to SALSA from 228 !< from chemistry model 229 LOGICAL :: van_der_waals_coagc = .FALSE. !< Enhancement of coagulation 230 !< kernel by van der Waals and 231 !< viscous forces 232 LOGICAL :: write_binary_salsa = .FALSE. !< read binary for salsa 349 LOGICAL :: advect_particle_water = .TRUE. !< advect water concentration of particles 350 LOGICAL :: decycle_lr = .FALSE. !< Undo cyclic boundary conditions: left and right 351 LOGICAL :: decycle_ns = .FALSE. !< north and south boundaries 352 LOGICAL :: feedback_to_palm = .FALSE. !< allow feedback due to condensation of H2O 353 LOGICAL :: nest_salsa = .FALSE. !< apply nesting for salsa 354 LOGICAL :: no_insoluble = .FALSE. !< Switch to exclude insoluble chemical components 355 LOGICAL :: read_restart_data_salsa = .FALSE. !< read restart data for salsa 356 LOGICAL :: salsa_gases_from_chem = .FALSE. !< Transfer the gaseous components to SALSA from 357 !< from chemistry model 358 LOGICAL :: van_der_waals_coagc = .FALSE. !< Enhancement of coagulation kernel by van der 359 !< Waals and viscous forces 360 LOGICAL :: write_binary_salsa = .FALSE. !< read binary for salsa 361 ! 233 362 !-- Process switches: nl* is read from the NAMELIST and is NOT changed. 234 !-- ls* is the switch used and will get the value of nl* 363 !-- ls* is the switch used and will get the value of nl* 235 364 !-- except for special circumstances (spinup period etc.) 236 LOGICAL :: nlcoag = .FALSE. !< Coagulation master switch 237 LOGICAL :: lscoag = .FALSE. !< 238 LOGICAL :: nlcnd = .FALSE. !< Condensation master switch 239 LOGICAL :: lscnd = .FALSE. !< 240 LOGICAL :: nlcndgas = .FALSE. !< Condensation of precursor gases 241 LOGICAL :: lscndgas = .FALSE. !< 242 LOGICAL :: nlcndh2oae = .FALSE. !< Condensation of H2O on aerosol 243 LOGICAL :: lscndh2oae = .FALSE. !< particles (FALSE -> equilibrium calc.) 244 LOGICAL :: nldepo = .FALSE. !< Deposition master switch 245 LOGICAL :: lsdepo = .FALSE. !< 246 LOGICAL :: nldepo_topo = .FALSE. !< Deposition on vegetation master switch 247 LOGICAL :: lsdepo_topo = .FALSE. !< 248 LOGICAL :: nldepo_vege = .FALSE. !< Deposition on walls master switch 249 LOGICAL :: lsdepo_vege = .FALSE. !< 250 LOGICAL :: nldistupdate = .TRUE. !< Size distribution update master switch 251 LOGICAL :: lsdistupdate = .FALSE. !< 252 ! 253 !-- SALSA variables: 254 CHARACTER (LEN=20) :: bc_salsa_b = 'neumann' !< bottom boundary condition 255 CHARACTER (LEN=20) :: bc_salsa_t = 'neumann' !< top boundary condition 256 CHARACTER (LEN=20) :: depo_vege_type = 'zhang2001' !< or 'petroff2010' 257 CHARACTER (LEN=20) :: depo_topo_type = 'zhang2001' !< or 'petroff2010' 258 CHARACTER (LEN=20), DIMENSION(4) :: decycle_method = & 259 (/'dirichlet','dirichlet','dirichlet','dirichlet'/) 260 !< Decycling method at horizontal boundaries, 261 !< 1=left, 2=right, 3=south, 4=north 262 !< dirichlet = initial size distribution and 263 !< chemical composition set for the ghost and 264 !< first three layers 265 !< neumann = zero gradient 266 CHARACTER (LEN=3), DIMENSION(maxspec) :: listspec = & !< Active aerosols 267 (/'SO4',' ',' ',' ',' ',' ',' '/) 268 CHARACTER (LEN=20) :: salsa_source_mode = 'no_source' 269 !< 'read_from_file', 270 !< 'constant' or 'no_source' 271 INTEGER(iwp) :: dots_salsa = 0 !< starting index for salsa-timeseries 272 INTEGER(iwp) :: fn1a = 1 !< last index for bin subranges: subrange 1a 273 INTEGER(iwp) :: fn2a = 1 !< subrange 2a 274 INTEGER(iwp) :: fn2b = 1 !< subrange 2b 275 INTEGER(iwp), DIMENSION(ngast) :: gas_index_chem = (/ 1, 1, 1, 1, 1/) !< 276 !< Index of gaseous compounds in the chemistry 277 !< model. In SALSA, 1 = H2SO4, 2 = HNO3, 278 !< 3 = NH3, 4 = OCNV, 5 = OCSV 279 INTEGER(iwp) :: ibc_salsa_b !< 280 INTEGER(iwp) :: ibc_salsa_t !< 281 INTEGER(iwp) :: igctyp = 0 !< Initial gas concentration type 282 !< 0 = uniform (use H2SO4_init, HNO3_init, 283 !< NH3_init, OCNV_init and OCSV_init) 284 !< 1 = read vertical profile from an input file 285 INTEGER(iwp) :: in1a = 1 !< start index for bin subranges: subrange 1a 286 INTEGER(iwp) :: in2a = 1 !< subrange 2a 287 INTEGER(iwp) :: in2b = 1 !< subrange 2b 288 INTEGER(iwp) :: isdtyp = 0 !< Initial size distribution type 289 !< 0 = uniform 290 !< 1 = read vertical profile of the mode number 291 !< concentration from an input file 292 INTEGER(iwp) :: ibc = -1 !< Indice for: black carbon (BC) 293 INTEGER(iwp) :: idu = -1 !< dust 294 INTEGER(iwp) :: inh = -1 !< NH3 295 INTEGER(iwp) :: ino = -1 !< HNO3 296 INTEGER(iwp) :: ioc = -1 !< organic carbon (OC) 297 INTEGER(iwp) :: iso4 = -1 !< SO4 or H2SO4 298 INTEGER(iwp) :: iss = -1 !< sea salt 299 INTEGER(iwp) :: lod_aero = 0 !< level of detail for aerosol emissions 300 INTEGER(iwp) :: lod_gases = 0 !< level of detail for gaseous emissions 301 INTEGER(iwp), DIMENSION(nreg) :: nbin = (/ 3, 7/) !< Number of size bins 302 !< for each aerosol size subrange 303 INTEGER(iwp) :: nbins = 1 !< total number of size bins 304 INTEGER(iwp) :: ncc = 1 !< number of chemical components used 305 INTEGER(iwp) :: ncc_tot = 1!< total number of chemical compounds (ncc+1 306 !< if particle water is advected) 307 REAL(wp) :: act_coeff = 1.0E-7_wp !< Activation coefficient 308 REAL(wp), ALLOCATABLE, DIMENSION(:,:) :: emission_mass_fracs !< array for 309 !< aerosol composition per emission category 310 !< 1:SO4 2:OC 3:BC 4:DU 5:SS 6:NO 7:NH 311 REAL(wp) :: dt_salsa = 0.00001_wp !< Time step of SALSA 312 REAL(wp) :: H2SO4_init = nclim !< Init value for sulphuric acid gas 313 REAL(wp) :: HNO3_init = nclim !< Init value for nitric acid gas 314 REAL(wp) :: last_salsa_time = 0.0_wp !< time of the previous salsa 315 !< timestep 316 REAL(wp) :: nf2a = 1.0_wp !< Number fraction allocated to a- 317 !< bins in subrange 2 318 !< (b-bins will get 1-nf2a) 319 REAL(wp) :: NH3_init = nclim !< Init value for ammonia gas 320 REAL(wp) :: OCNV_init = nclim !< Init value for non-volatile 321 !< organic gases 322 REAL(wp) :: OCSV_init = nclim !< Init value for semi-volatile 323 !< organic gases 365 LOGICAL :: nlcoag = .FALSE. !< Coagulation master switch 366 LOGICAL :: lscoag = .FALSE. !< 367 LOGICAL :: nlcnd = .FALSE. !< Condensation master switch 368 LOGICAL :: lscnd = .FALSE. !< 369 LOGICAL :: nlcndgas = .FALSE. !< Condensation of precursor gases 370 LOGICAL :: lscndgas = .FALSE. !< 371 LOGICAL :: nlcndh2oae = .FALSE. !< Condensation of H2O on aerosol 372 LOGICAL :: lscndh2oae = .FALSE. !< particles (FALSE -> equilibrium calc.) 373 LOGICAL :: nldepo = .FALSE. !< Deposition master switch 374 LOGICAL :: lsdepo = .FALSE. !< 375 LOGICAL :: nldepo_surf = .FALSE. !< Deposition on vegetation master switch 376 LOGICAL :: lsdepo_surf = .FALSE. !< 377 LOGICAL :: nldepo_pcm = .FALSE. !< Deposition on walls master switch 378 LOGICAL :: lsdepo_pcm = .FALSE. !< 379 LOGICAL :: nldistupdate = .TRUE. !< Size distribution update master switch 380 LOGICAL :: lsdistupdate = .FALSE. !< 381 LOGICAL :: lspartition = .FALSE. !< Partition of HNO3 and NH3 382 383 REAL(wp) :: act_coeff = 1.0E-7_wp !< Activation coefficient 384 REAL(wp) :: dt_salsa = 0.00001_wp !< Time step of SALSA 385 REAL(wp) :: h2so4_init = nclim !< Init value for sulphuric acid gas 386 REAL(wp) :: hno3_init = nclim !< Init value for nitric acid gas 387 REAL(wp) :: last_salsa_time = 0.0_wp !< previous salsa call 388 REAL(wp) :: next_aero_emission_update = 0.0_wp !< previous emission update 389 REAL(wp) :: next_gas_emission_update = 0.0_wp !< previous emission update 390 REAL(wp) :: nf2a = 1.0_wp !< Number fraction allocated to 2a-bins 391 REAL(wp) :: nh3_init = nclim !< Init value for ammonia gas 392 REAL(wp) :: ocnv_init = nclim !< Init value for non-volatile organic gases 393 REAL(wp) :: ocsv_init = nclim !< Init value for semi-volatile organic gases 394 REAL(wp) :: rhlim = 1.20_wp !< RH limit in %/100. Prevents unrealistical RH 395 REAL(wp) :: skip_time_do_salsa = 0.0_wp !< Starting time of SALSA (s) 396 ! 397 !-- Initial log-normal size distribution: mode diameter (dpg, metres), 398 !-- standard deviation (sigmag) and concentration (n_lognorm, #/m3) 399 REAL(wp), DIMENSION(nmod) :: dpg = & 400 (/0.013_wp, 0.054_wp, 0.86_wp, 0.2_wp, 0.2_wp, 0.2_wp, 0.2_wp/) 401 REAL(wp), DIMENSION(nmod) :: sigmag = & 402 (/1.8_wp, 2.16_wp, 2.21_wp, 2.0_wp, 2.0_wp, 2.0_wp, 2.0_wp/) 403 REAL(wp), DIMENSION(nmod) :: n_lognorm = & 404 (/1.04e+11_wp, 3.23E+10_wp, 5.4E+6_wp, 0.0_wp, 0.0_wp, 0.0_wp, 0.0_wp/) 405 ! 406 !-- Initial mass fractions / chemical composition of the size distribution 407 REAL(wp), DIMENSION(maxspec) :: mass_fracs_a = & !< mass fractions between 408 (/1.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0/) !< aerosol species for A bins 409 REAL(wp), DIMENSION(maxspec) :: mass_fracs_b = & !< mass fractions between 410 (/0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0/) !< aerosol species for B bins 324 411 REAL(wp), DIMENSION(nreg+1) :: reglim = & !< Min&max diameters of size subranges 325 412 (/ 3.0E-9_wp, 5.0E-8_wp, 1.0E-5_wp/) 326 REAL(wp) :: rhlim = 1.20_wp !< RH limit in %/100. Prevents 327 !< unrealistically high RH in condensation 328 REAL(wp) :: skip_time_do_salsa = 0.0_wp !< Starting time of SALSA (s) 329 !-- Initial log-normal size distribution: mode diameter (dpg, micrometres), 330 !-- standard deviation (sigmag) and concentration (n_lognorm, #/cm3) 331 REAL(wp), DIMENSION(nmod) :: dpg = (/0.013_wp, 0.054_wp, 0.86_wp, & 332 0.2_wp, 0.2_wp, 0.2_wp, 0.2_wp/) 333 REAL(wp), DIMENSION(nmod) :: sigmag = (/1.8_wp, 2.16_wp, 2.21_wp, & 334 2.0_wp, 2.0_wp, 2.0_wp, 2.0_wp/) 335 REAL(wp), DIMENSION(nmod) :: n_lognorm = (/1.04e+5_wp, 3.23E+4_wp, 5.4_wp,& 336 0.0_wp, 0.0_wp, 0.0_wp, 0.0_wp/) 337 !-- Initial mass fractions / chemical composition of the size distribution 338 REAL(wp), DIMENSION(maxspec) :: mass_fracs_a = & !< mass fractions between 339 (/1.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0/) !< aerosol species for A bins 340 REAL(wp), DIMENSION(maxspec) :: mass_fracs_b = & !< mass fractions between 341 (/0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0/) !< aerosol species for B bins 342 343 REAL(wp), ALLOCATABLE, DIMENSION(:) :: bin_low_limits !< to deliver 344 !< information about 345 !< the lower 346 !< diameters per bin 347 REAL(wp), ALLOCATABLE, DIMENSION(:) :: nsect !< Background number 348 !< concentration per bin 349 REAL(wp), ALLOCATABLE, DIMENSION(:) :: massacc !< Mass accomodation 350 !< coefficients per bin 351 ! 352 !-- SALSA derived datatypes: 353 ! 354 !-- Prognostic variable: Aerosol size bin information (number (#/m3) and 355 !-- mass (kg/m3) concentration) and the concentration of gaseous tracers (#/m3). 356 !-- Gas tracers are contained sequentially in dimension 4 as: 357 !-- 1. H2SO4, 2. HNO3, 3. NH3, 4. OCNV (non-volatile organics), 358 !-- 5. OCSV (semi-volatile) 413 ! 414 !-- Initial log-normal size distribution: mode diameter (dpg, metres), standard deviation (sigmag) 415 !-- concentration (n_lognorm, #/m3) and mass fractions of all chemical components (listed in 416 !-- listspec) for both a (soluble) and b (insoluble) bins. 417 REAL(wp), DIMENSION(nmod) :: aerosol_flux_dpg = & 418 (/0.013_wp, 0.054_wp, 0.86_wp, 0.2_wp, 0.2_wp, 0.2_wp, 0.2_wp/) 419 REAL(wp), DIMENSION(nmod) :: aerosol_flux_sigmag = & 420 (/1.8_wp, 2.16_wp, 2.21_wp, 2.0_wp, 2.0_wp, 2.0_wp, 2.0_wp/) 421 REAL(wp), DIMENSION(nmod) :: surface_aerosol_flux = & 422 (/1.04e+11_wp, 3.23E+10_wp, 5.4E+6_wp, 0.0_wp, 0.0_wp, 0.0_wp, 0.0_wp/) 423 REAL(wp), DIMENSION(maxspec) :: aerosol_flux_mass_fracs_a = & 424 (/1.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0/) 425 REAL(wp), DIMENSION(maxspec) :: aerosol_flux_mass_fracs_b = & 426 (/0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0/) 427 428 REAL(wp), DIMENSION(:), ALLOCATABLE :: bin_low_limits !< to deliver information about 429 !< the lower diameters per bin 430 REAL(wp), DIMENSION(:), ALLOCATABLE :: bc_am_t_val !< vertical gradient of: aerosol mass 431 REAL(wp), DIMENSION(:), ALLOCATABLE :: bc_an_t_val !< of: aerosol number 432 REAL(wp), DIMENSION(:), ALLOCATABLE :: bc_gt_t_val !< salsa gases near domain top 433 REAL(wp), DIMENSION(:), ALLOCATABLE :: gas_emission_time !< Time array in gas emission data (s) 434 REAL(wp), DIMENSION(:), ALLOCATABLE :: nsect !< Background number concentrations 435 REAL(wp), DIMENSION(:), ALLOCATABLE :: massacc !< Mass accomodation coefficients 436 ! 437 !-- SALSA derived datatypes: 438 ! 439 !-- For matching LSM and the deposition module surface types 440 TYPE match_lsm_depo 441 INTEGER(iwp), DIMENSION(:), ALLOCATABLE :: match 442 END TYPE match_lsm_depo 443 ! 444 !-- Aerosol emission data attributes 445 TYPE salsa_emission_attribute_type 446 447 CHARACTER(LEN=25) :: units 448 449 CHARACTER(LEN=25), DIMENSION(:), ALLOCATABLE :: cat_name !< 450 CHARACTER(LEN=25), DIMENSION(:), ALLOCATABLE :: cc_name !< 451 CHARACTER(LEN=25), DIMENSION(:), ALLOCATABLE :: unit_time !< 452 CHARACTER(LEN=100), DIMENSION(:), ALLOCATABLE :: var_names !< 453 454 INTEGER(iwp) :: lod = 0 !< level of detail 455 INTEGER(iwp) :: nbins = 10 !< number of aerosol size bins 456 INTEGER(iwp) :: ncat = 0 !< number of emission categories 457 INTEGER(iwp) :: ncc = 7 !< number of aerosol chemical components 458 INTEGER(iwp) :: nhoursyear = 0 !< number of hours: HOURLY mode 459 INTEGER(iwp) :: nmonthdayhour = 0 !< number of month days and hours: MDH mode 460 INTEGER(iwp) :: num_vars !< number of variables 461 INTEGER(iwp) :: nt = 0 !< number of time steps 462 INTEGER(iwp) :: nz = 0 !< number of vertical levels 463 INTEGER(iwp) :: tind !< time index for reference time in salsa emission data 464 465 INTEGER(iwp), DIMENSION(maxspec) :: cc_input_to_model !< 466 467 INTEGER(iwp), DIMENSION(:), ALLOCATABLE :: cat_index !< Index of emission categories 468 INTEGER(iwp), DIMENSION(:), ALLOCATABLE :: cc_index !< Index of chemical components 469 470 REAL(wp) :: conversion_factor !< unit conversion factor for aerosol emissions 471 472 REAL(wp), DIMENSION(:), ALLOCATABLE :: dmid !< mean diameters of size bins (m) 473 REAL(wp), DIMENSION(:), ALLOCATABLE :: rho !< average density (kg/m3) 474 REAL(wp), DIMENSION(:), ALLOCATABLE :: time !< time (s) 475 REAL(wp), DIMENSION(:), ALLOCATABLE :: time_factor !< emission time factor 476 REAL(wp), DIMENSION(:), ALLOCATABLE :: z !< height (m) 477 478 REAL(wp), DIMENSION(:,:), ALLOCATABLE :: etf !< emission time factor 479 REAL(wp), DIMENSION(:,:), ALLOCATABLE :: stack_height 480 481 END TYPE salsa_emission_attribute_type 482 ! 483 !-- The default size distribution and mass composition per emission category: 484 !-- 1 = traffic, 2 = road dust, 3 = wood combustion, 4 = other 485 !-- Mass fractions: H2SO4, OC, BC, DU, SS, HNO3, NH3 486 TYPE salsa_emission_mode_type 487 488 INTEGER(iwp) :: ndm = 3 !< number of default modes 489 INTEGER(iwp) :: ndc = 4 !< number of default categories 490 491 CHARACTER(LEN=25), DIMENSION(1:4) :: cat_name_table = (/'traffic exhaust', & 492 'road dust ', & 493 'wood combustion', & 494 'other '/) 495 496 INTEGER(iwp), DIMENSION(1:4) :: cat_input_to_model !< 497 498 REAL(wp), DIMENSION(1:3) :: dpg_table = (/ 13.5E-9_wp, 1.4E-6_wp, 5.4E-8_wp/) !< 499 REAL(wp), DIMENSION(1:3) :: ntot_table !< 500 REAL(wp), DIMENSION(1:3) :: sigmag_table = (/ 1.6_wp, 1.4_wp, 1.7_wp /) !< 501 502 REAL(wp), DIMENSION(1:maxspec,1:4) :: mass_frac_table = & !< 503 RESHAPE( (/ 0.04_wp, 0.48_wp, 0.48_wp, 0.0_wp, 0.0_wp, 0.0_wp, 0.0_wp, & 504 0.0_wp, 0.05_wp, 0.0_wp, 0.95_wp, 0.0_wp, 0.0_wp, 0.0_wp, & 505 0.0_wp, 0.5_wp, 0.5_wp, 0.0_wp, 0.0_wp, 0.0_wp, 0.0_wp, & 506 0.0_wp, 0.5_wp, 0.5_wp, 0.0_wp, 0.0_wp, 0.0_wp, 0.0_wp & 507 /), (/maxspec,4/) ) 508 509 REAL(wp), DIMENSION(1:3,1:4) :: pm_frac_table = & !< rel. mass 510 RESHAPE( (/ 0.016_wp, 0.000_wp, 0.984_wp, & 511 0.000_wp, 1.000_wp, 0.000_wp, & 512 0.000_wp, 0.000_wp, 1.000_wp, & 513 1.000_wp, 0.000_wp, 1.000_wp & 514 /), (/3,4/) ) 515 516 END TYPE salsa_emission_mode_type 517 ! 518 !-- Aerosol emission data values 519 TYPE salsa_emission_value_type 520 521 REAL(wp) :: fill !< fill value 522 523 REAL(wp), DIMENSION(:), ALLOCATABLE :: preproc_mass_fracs !< mass fractions 524 525 REAL(wp), DIMENSION(:,:), ALLOCATABLE :: def_mass_fracs !< mass fractions per emis. category 526 527 REAL(wp), DIMENSION(:,:,:), ALLOCATABLE :: def_data !< surface emission values in PM 528 REAL(wp), DIMENSION(:,:,:), ALLOCATABLE :: preproc_data !< surface emission values per bin 529 530 END TYPE salsa_emission_value_type 531 ! 532 !-- Prognostic variable: Aerosol size bin information (number (#/m3) and mass (kg/m3) concentration) 533 !-- and the concentration of gaseous tracers (#/m3). Gas tracers are contained sequentially in 534 !-- dimension 4 as: 535 !-- 1. H2SO4, 2. HNO3, 3. NH3, 4. OCNV (non-volatile organics), 5. OCSV (semi-volatile) 359 536 TYPE salsa_variable 360 REAL(wp), POINTER, DIMENSION(:,:,:), CONTIGUOUS :: conc 361 REAL(wp), POINTER, DIMENSION(:,:,:), CONTIGUOUS :: conc_p 362 REAL(wp), POINTER, DIMENSION(:,:,:), CONTIGUOUS :: tconc_m 363 REAL(wp), ALLOCATABLE, DIMENSION(:,:) :: flux_s, diss_s 364 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:) :: flux_l, diss_l 365 REAL(wp), ALLOCATABLE, DIMENSION(:) :: init 366 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:) :: source 367 REAL(wp), ALLOCATABLE, DIMENSION(:,:) :: sums_ws_l 537 538 REAL(wp), ALLOCATABLE, DIMENSION(:) :: init !< 539 540 REAL(wp), ALLOCATABLE, DIMENSION(:,:) :: diss_s !< 541 REAL(wp), ALLOCATABLE, DIMENSION(:,:) :: flux_s !< 542 REAL(wp), ALLOCATABLE, DIMENSION(:,:) :: source !< 543 REAL(wp), ALLOCATABLE, DIMENSION(:,:) :: sums_ws_l !< 544 545 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:) :: diss_l !< 546 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:) :: flux_l !< 547 548 REAL(wp), POINTER, DIMENSION(:,:,:), CONTIGUOUS :: conc !< 549 REAL(wp), POINTER, DIMENSION(:,:,:), CONTIGUOUS :: conc_p !< 550 REAL(wp), POINTER, DIMENSION(:,:,:), CONTIGUOUS :: tconc_m !< 551 368 552 END TYPE salsa_variable 369 370 !-- Map bin indices between parallel size distributions 371 TYPE t_parallelbin 372 INTEGER(iwp) :: cur ! Index for current distribution 373 INTEGER(iwp) :: par ! Index for corresponding parallel distribution 374 END TYPE t_parallelbin 375 376 !-- Datatype used to store information about the binned size distributions of 377 !-- aerosols 553 ! 554 !-- Datatype used to store information about the binned size distributions of aerosols 378 555 TYPE t_section 556 557 REAL(wp) :: dmid !< bin middle diameter (m) 379 558 REAL(wp) :: vhilim !< bin volume at the high limit 380 559 REAL(wp) :: vlolim !< bin volume at the low limit 381 560 REAL(wp) :: vratiohi !< volume ratio between the center and high limit 382 561 REAL(wp) :: vratiolo !< volume ratio between the center and low limit 383 REAL(wp) :: dmid !< bin middle diameter (m)384 562 !****************************************************** 385 563 ! ^ Do NOT change the stuff above after initialization ! 386 564 !****************************************************** 565 REAL(wp) :: core !< Volume of dry particle 387 566 REAL(wp) :: dwet !< Wet diameter or mean droplet diameter (m) 388 REAL(wp), DIMENSION(maxspec+1) :: volc !< Volume concentrations 389 !< (m^3/m^3) of aerosols + water. Since most of 390 !< the stuff in SALSA is hard coded, these *have to 391 !< be* in the order 392 !< 1:SO4, 2:OC, 3:BC, 4:DU, 5:SS, 6:NO, 7:NH, 8:H2O 567 REAL(wp) :: numc !< Number concentration of particles/droplets (#/m3) 393 568 REAL(wp) :: veqh2o !< Equilibrium H2O concentration for each particle 394 REAL(wp) :: numc !< Number concentration of particles/droplets (#/m3) 395 REAL(wp) :: core !< Volume of dry particle 396 END TYPE t_section 397 ! 398 !-- Local aerosol properties in SALSA 399 TYPE(t_section), ALLOCATABLE :: aero(:) 400 ! 401 !-- SALSA tracers: 402 !-- Tracers as x = x(k,j,i,bin). The 4th dimension contains all the size bins 403 !-- sequentially for each aerosol species + water. 404 ! 405 !-- Prognostic tracers: 406 ! 407 !-- Number concentration (#/m3) 408 TYPE(salsa_variable), ALLOCATABLE, DIMENSION(:), TARGET :: aerosol_number 409 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: nconc_1 410 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: nconc_2 411 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: nconc_3 412 ! 413 !-- Mass concentration (kg/m3) 414 TYPE(salsa_variable), ALLOCATABLE, DIMENSION(:), TARGET :: aerosol_mass 415 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: mconc_1 416 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: mconc_2 417 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: mconc_3 418 ! 419 !-- Gaseous tracers (#/m3) 420 TYPE(salsa_variable), ALLOCATABLE, DIMENSION(:), TARGET :: salsa_gas 421 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: gconc_1 422 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: gconc_2 423 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: gconc_3 569 570 REAL(wp), DIMENSION(maxspec+1) :: volc !< Volume concentrations (m^3/m^3) of aerosols + 571 !< water. Since most of the stuff in SALSA is hard 572 !< coded, these *have to be* in the order 573 !< 1:SO4, 2:OC, 3:BC, 4:DU, 5:SS, 6:NO, 7:NH, 8:H2O 574 END TYPE t_section 575 576 TYPE(salsa_emission_attribute_type) :: aero_emission_att !< emission attributes 577 TYPE(salsa_emission_value_type) :: aero_emission !< emission values 578 TYPE(salsa_emission_mode_type) :: def_modes !< default emission modes 579 580 TYPE(t_section), DIMENSION(:), ALLOCATABLE :: aero !< local aerosol properties 581 582 TYPE(match_lsm_depo) :: lsm_to_depo_h 583 584 TYPE(match_lsm_depo), DIMENSION(0:3) :: lsm_to_depo_v 585 ! 586 !-- SALSA variables: as x = x(k,j,i,bin). 587 !-- The 4th dimension contains all the size bins sequentially for each aerosol species + water. 588 ! 589 !-- Prognostic variables: 590 ! 591 !-- Number concentration (#/m3) 592 TYPE(salsa_variable), ALLOCATABLE, DIMENSION(:), TARGET :: aerosol_number !< 593 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: nconc_1 !< 594 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: nconc_2 !< 595 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: nconc_3 !< 596 ! 597 !-- Mass concentration (kg/m3) 598 TYPE(salsa_variable), ALLOCATABLE, DIMENSION(:), TARGET :: aerosol_mass !< 599 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: mconc_1 !< 600 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: mconc_2 !< 601 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: mconc_3 !< 602 ! 603 !-- Gaseous concentrations (#/m3) 604 TYPE(salsa_variable), ALLOCATABLE, DIMENSION(:), TARGET :: salsa_gas !< 605 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: gconc_1 !< 606 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: gconc_2 !< 607 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: gconc_3 !< 424 608 ! 425 609 !-- Diagnostic tracers 426 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:) :: sedim_vd !< sedimentation 427 !< velocity per size 428 !< bin (m/s) 429 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:) :: Ra_dry !< dry radius (m) 430 610 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:) :: sedim_vd !< sedimentation velocity per bin (m/s) 611 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:) :: ra_dry !< aerosol dry radius (m) 612 431 613 !-- Particle component index tables 432 TYPE(component_index) :: prtcl !< Contains "getIndex" which gives the index 433 !< for a given aerosol component name, i.e. 434 !< 1:SO4, 2:OC, 3:BC, 4:DU, 435 !< 5:SS, 6:NO, 7:NH, 8:H2O 436 ! 614 TYPE(component_index) :: prtcl !< Contains "getIndex" which gives the index for a given aerosol 615 !< component name: 1:SO4, 2:OC, 3:BC, 4:DU, 5:SS, 6:NO, 7:NH, 8:H2O 616 ! 437 617 !-- Data output arrays: 618 ! 438 619 !-- Gases: 439 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: g_H2SO4_av !< H2SO4 440 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: g_HNO3_av !< HNO3 441 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: g_NH3_av !< NH3 442 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: g_OCNV_av !< non-vola- 443 !< tile OC 444 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: g_OCSV_av !< semi-vol. 445 !< OC 446 !-- Integrated: 447 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: LDSA_av !< lung- 448 !< deposited 449 !< surface area 450 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: Ntot_av !< total number 451 !< conc. 452 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: PM25_av !< PM2.5 453 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: PM10_av !< PM10 454 !-- In the particle phase: 455 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_BC_av !< black carbon 456 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_DU_av !< dust 457 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_H2O_av !< liquid water 458 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_NH_av !< ammonia 459 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_NO_av !< nitrates 460 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_OC_av !< org. carbon 461 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_SO4_av !< sulphates 462 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_SS_av !< sea salt 463 !-- Bins: 464 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: mbins_av !< bin mass 465 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: Nbins_av !< bin number 466 467 620 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: g_h2so4_av !< H2SO4 621 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: g_hno3_av !< HNO3 622 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: g_nh3_av !< NH3 623 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: g_ocnv_av !< non-volatile OC 624 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: g_ocsv_av !< semi-volatile OC 625 ! 626 !-- Integrated: 627 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: ldsa_av !< lung-deposited surface area 628 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: ntot_av !< total number concentration 629 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: pm25_av !< PM2.5 630 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: pm10_av !< PM10 631 ! 632 !-- In the particle phase: 633 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_bc_av !< black carbon 634 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_du_av !< dust 635 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_h2o_av !< liquid water 636 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_nh_av !< ammonia 637 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_no_av !< nitrates 638 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_oc_av !< org. carbon 639 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_so4_av !< sulphates 640 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:), TARGET :: s_ss_av !< sea salt 641 ! 642 !-- Bin specific mass and number concentrations: 643 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: mbins_av !< bin mas 644 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:), TARGET :: nbins_av !< bin number 645 468 646 ! 469 647 !-- PALM interfaces: … … 474 652 MODULE PROCEDURE salsa_boundary_conds_decycle 475 653 END INTERFACE salsa_boundary_conds 476 ! 654 ! 477 655 !-- Data output checks for 2D/3D data to be done in check_parameters 478 656 INTERFACE salsa_check_data_output 479 657 MODULE PROCEDURE salsa_check_data_output 480 658 END INTERFACE salsa_check_data_output 481 482 659 ! 483 660 !-- Input parameter checks to be done in check_parameters … … 485 662 MODULE PROCEDURE salsa_check_parameters 486 663 END INTERFACE salsa_check_parameters 487 488 664 ! 489 665 !-- Averaging of 3D data for output … … 491 667 MODULE PROCEDURE salsa_3d_data_averaging 492 668 END INTERFACE salsa_3d_data_averaging 493 494 669 ! 495 670 !-- Data output of 2D quantities … … 497 672 MODULE PROCEDURE salsa_data_output_2d 498 673 END INTERFACE salsa_data_output_2d 499 500 674 ! 501 675 !-- Data output of 3D data … … 503 677 MODULE PROCEDURE salsa_data_output_3d 504 678 END INTERFACE salsa_data_output_3d 505 506 679 ! 507 680 !-- Data output of 3D data … … 509 682 MODULE PROCEDURE salsa_data_output_mask 510 683 END INTERFACE salsa_data_output_mask 511 512 684 ! 513 685 !-- Definition of data output quantities … … 515 687 MODULE PROCEDURE salsa_define_netcdf_grid 516 688 END INTERFACE salsa_define_netcdf_grid 517 518 689 ! 519 690 !-- Output of information to the header file … … 521 692 MODULE PROCEDURE salsa_header 522 693 END INTERFACE salsa_header 523 524 ! 525 !-- Initialization actions 694 ! 695 !-- Initialization actions 526 696 INTERFACE salsa_init 527 697 MODULE PROCEDURE salsa_init 528 698 END INTERFACE salsa_init 529 530 699 ! 531 700 !-- Initialization of arrays … … 533 702 MODULE PROCEDURE salsa_init_arrays 534 703 END INTERFACE salsa_init_arrays 535 536 704 ! 537 705 !-- Writing of binary output for restart runs !!! renaming?! … … 539 707 MODULE PROCEDURE salsa_wrd_local 540 708 END INTERFACE salsa_wrd_local 541 542 709 ! 543 710 !-- Reading of NAMELIST parameters … … 545 712 MODULE PROCEDURE salsa_parin 546 713 END INTERFACE salsa_parin 547 548 714 ! 549 715 !-- Reading of parameters for restart runs … … 551 717 MODULE PROCEDURE salsa_rrd_local 552 718 END INTERFACE salsa_rrd_local 553 554 719 ! 555 720 !-- Swapping of time levels (required for prognostic variables) … … 557 722 MODULE PROCEDURE salsa_swap_timelevel 558 723 END INTERFACE salsa_swap_timelevel 559 724 ! 725 !-- Interface between PALM and salsa 560 726 INTERFACE salsa_driver 561 727 MODULE PROCEDURE salsa_driver 562 728 END INTERFACE salsa_driver 563 729 ! 730 !-- Prognostics equations for salsa variables 731 INTERFACE salsa_prognostic_equations 732 MODULE PROCEDURE salsa_prognostic_equations 733 MODULE PROCEDURE salsa_prognostic_equations_ij 734 END INTERFACE salsa_prognostic_equations 735 ! 736 !-- Tendency salsa variables 564 737 INTERFACE salsa_tendency 565 738 MODULE PROCEDURE salsa_tendency 566 739 MODULE PROCEDURE salsa_tendency_ij 567 740 END INTERFACE salsa_tendency 568 569 570 741 742 571 743 SAVE 572 744 573 745 PRIVATE 574 746 ! 575 !-- Public functions: 576 PUBLIC salsa_boundary_conds, salsa_check_data_output, & 577 salsa_check_parameters, salsa_3d_data_averaging, & 578 salsa_data_output_2d, salsa_data_output_3d, salsa_data_output_mask, & 579 salsa_define_netcdf_grid, salsa_diagnostics, salsa_driver, & 580 salsa_header, salsa_init, salsa_init_arrays, salsa_parin, & 581 salsa_rrd_local, salsa_swap_timelevel, salsa_tendency, & 582 salsa_wrd_local 747 !-- Public functions: 748 PUBLIC salsa_boundary_conds, salsa_check_data_output, salsa_check_parameters, & 749 salsa_3d_data_averaging, salsa_data_output_2d, salsa_data_output_3d, & 750 salsa_data_output_mask, salsa_define_netcdf_grid, salsa_diagnostics, salsa_driver, & 751 salsa_emission_update, salsa_header, salsa_init, salsa_init_arrays, salsa_parin, & 752 salsa_rrd_local, salsa_swap_timelevel, salsa_prognostic_equations, salsa_wrd_local 583 753 ! 584 754 !-- Public parameters, constants and initial values 585 PUBLIC dots_salsa, dt_salsa, last_salsa_time, lsdepo, salsa, & 586 salsa_gases_from_chem, skip_time_do_salsa 755 PUBLIC bc_am_t_val, bc_an_t_val, bc_gt_t_val, dots_salsa, dt_salsa, & 756 ibc_salsa_b, last_salsa_time, lsdepo, nest_salsa, salsa, salsa_gases_from_chem, & 757 skip_time_do_salsa 587 758 ! 588 759 !-- Public prognostic variables 589 PUBLIC aerosol_mass, aerosol_number, fn2a, fn2b, gconc_2, in1a, in2b, & 590 mconc_2, nbins, ncc, ncc_tot, nclim, nconc_2, ngast, prtcl, Ra_dry, & 591 salsa_gas, sedim_vd 592 760 PUBLIC aerosol_mass, aerosol_number, gconc_2, mconc_2, nbins_aerosol, ncc, ncomponents_mass, & 761 nclim, nconc_2, ngases_salsa, prtcl, ra_dry, salsa_gas, sedim_vd 762 593 763 594 764 CONTAINS … … 603 773 IMPLICIT NONE 604 774 605 CHARACTER (LEN=80) :: line !< dummy string that contains the current line 606 !< of the parameter file 607 608 NAMELIST /salsa_parameters/ & 609 advect_particle_water, & ! Switch for advecting 610 ! particle water. If .FALSE., 611 ! equilibration is called at 612 ! each time step. 613 bc_salsa_b, & ! bottom boundary condition 614 bc_salsa_t, & ! top boundary condition 615 decycle_lr, & ! decycle SALSA components 616 decycle_method, & ! decycle method applied: 617 ! 1=left 2=right 3=south 4=north 618 decycle_ns, & ! decycle SALSA components 619 depo_vege_type, & ! Parametrisation type 620 depo_topo_type, & ! Parametrisation type 621 dpg, & ! Mean diameter for the initial 622 ! log-normal modes 623 dt_salsa, & ! SALSA timestep in seconds 624 feedback_to_palm, & ! allow feedback due to 625 ! hydration / condensation 626 H2SO4_init, & ! Init value for sulphuric acid 627 HNO3_init, & ! Init value for nitric acid 628 igctyp, & ! Initial gas concentration type 629 isdtyp, & ! Initial size distribution type 630 listspec, & ! List of actived aerosols 631 ! (string list) 632 mass_fracs_a, & ! Initial relative contribution 633 ! of each species to particle 634 ! volume in a-bins, 0 for unused 635 mass_fracs_b, & ! Initial relative contribution 636 ! of each species to particle 637 ! volume in b-bins, 0 for unused 638 n_lognorm, & ! Number concentration for the 639 ! log-normal modes 640 nbin, & ! Number of size bins for 641 ! aerosol size subranges 1 & 2 642 nf2a, & ! Number fraction of particles 643 ! allocated to a-bins in 644 ! subrange 2 b-bins will get 645 ! 1-nf2a 646 NH3_init, & ! Init value for ammonia 647 nj3, & ! J3 parametrization 648 ! 1 = condensational sink 649 ! (Kerminen&Kulmala, 2002) 650 ! 2 = coagulational sink 651 ! (Lehtinen et al. 2007) 652 ! 3 = coagS+self-coagulation 653 ! (Anttila et al. 2010) 654 nlcnd, & ! Condensation master switch 655 nlcndgas, & ! Condensation of gases 656 nlcndh2oae, & ! Condensation of H2O 657 nlcoag, & ! Coagulation master switch 658 nldepo, & ! Deposition master switch 659 nldepo_vege, & ! Deposition on vegetation 660 ! master switch 661 nldepo_topo, & ! Deposition on topo master 662 ! switch 663 nldistupdate, & ! Size distribution update 664 ! master switch 665 nsnucl, & ! Nucleation scheme: 666 ! 0 = off, 667 ! 1 = binary nucleation 668 ! 2 = activation type nucleation 669 ! 3 = kinetic nucleation 670 ! 4 = ternary nucleation 671 ! 5 = nucleation with organics 672 ! 6 = activation type of 673 ! nucleation with H2SO4+ORG 674 ! 7 = heteromolecular nucleation 675 ! with H2SO4*ORG 676 ! 8 = homomolecular nucleation 677 ! of H2SO4 + heteromolecular 678 ! nucleation with H2SO4*ORG 679 ! 9 = homomolecular nucleation 680 ! of H2SO4 and ORG + hetero- 681 ! molecular nucleation with 682 ! H2SO4*ORG 683 OCNV_init, & ! Init value for non-volatile 684 ! organic gases 685 OCSV_init, & ! Init value for semi-volatile 686 ! organic gases 687 read_restart_data_salsa, & ! read restart data for 688 ! salsa 689 reglim, & ! Min&max diameter limits of 690 ! size subranges 691 salsa, & ! Master switch for SALSA 692 salsa_source_mode,& ! 'read_from_file' or 'constant' 693 ! or 'no_source' 694 sigmag, & ! stdev for the initial log- 695 ! normal modes 696 skip_time_do_salsa, & ! Starting time of SALSA (s) 697 van_der_waals_coagc,& ! include van der Waals forces 698 write_binary_salsa ! Write binary for salsa 699 700 775 CHARACTER(LEN=80) :: line !< dummy string that contains the current line 776 !< of the parameter file 777 778 NAMELIST /salsa_parameters/ aerosol_flux_dpg, aerosol_flux_mass_fracs_a, & 779 aerosol_flux_mass_fracs_b, aerosol_flux_sigmag, & 780 advect_particle_water, bc_salsa_b, bc_salsa_t, decycle_lr, & 781 decycle_method, decycle_ns, depo_pcm_par, depo_pcm_type, & 782 depo_surf_par, dpg, dt_salsa, feedback_to_palm, h2so4_init, & 783 hno3_init, igctyp, isdtyp, listspec, mass_fracs_a, & 784 mass_fracs_b, n_lognorm, nbin, nest_salsa, nf2a, nh3_init, & 785 nj3, nlcnd, nlcndgas, nlcndh2oae, nlcoag, nldepo, nldepo_pcm, & 786 nldepo_surf, nldistupdate, nsnucl, ocnv_init, ocsv_init, & 787 read_restart_data_salsa, reglim, salsa, salsa_emission_mode, & 788 sigmag, skip_time_do_salsa, surface_aerosol_flux, & 789 van_der_waals_coagc, write_binary_salsa 790 701 791 line = ' ' 702 703 792 ! 704 793 !-- Try to find salsa package … … 709 798 ENDDO 710 799 BACKSPACE ( 11 ) 711 712 800 ! 713 801 !-- Read user-defined namelist 714 802 READ ( 11, salsa_parameters ) 715 716 803 ! 717 804 !-- Enable salsa (salsa switch in modules.f90) … … 719 806 720 807 10 CONTINUE 721 808 722 809 END SUBROUTINE salsa_parin 723 810 724 725 811 !------------------------------------------------------------------------------! 726 812 ! Description: … … 730 816 SUBROUTINE salsa_check_parameters 731 817 732 USE control_parameters, &818 USE control_parameters, & 733 819 ONLY: message_string 734 820 735 821 IMPLICIT NONE 736 822 737 823 ! 738 824 !-- Checks go here (cf. check_parameters.f90). 739 825 IF ( salsa .AND. .NOT. humidity ) THEN 740 WRITE( message_string, * ) 'salsa = ', salsa, ' is ', & 741 'not allowed with humidity = ', humidity 742 CALL message( 'check_parameters', 'SA0009', 1, 2, 0, 6, 0 ) 826 WRITE( message_string, * ) 'salsa = ', salsa, ' is not allowed with humidity = ', humidity 827 CALL message( 'salsa_check_parameters', 'PA0594', 1, 2, 0, 6, 0 ) 743 828 ENDIF 744 829 745 830 IF ( bc_salsa_b == 'dirichlet' ) THEN 746 831 ibc_salsa_b = 0 … … 748 833 ibc_salsa_b = 1 749 834 ELSE 750 message_string = 'unknown boundary condition: bc_salsa_b = "' & 751 // TRIM( bc_salsa_t ) // '"' 752 CALL message( 'check_parameters', 'SA0011', 1, 2, 0, 6, 0 ) 835 message_string = 'unknown boundary condition: bc_salsa_b = "' // TRIM( bc_salsa_t ) // '"' 836 CALL message( 'salsa_check_parameters', 'PA0595', 1, 2, 0, 6, 0 ) 753 837 ENDIF 754 838 755 839 IF ( bc_salsa_t == 'dirichlet' ) THEN 756 840 ibc_salsa_t = 0 757 841 ELSEIF ( bc_salsa_t == 'neumann' ) THEN 758 842 ibc_salsa_t = 1 843 ELSEIF ( bc_salsa_t == 'nested' ) THEN 844 ibc_salsa_t = 2 759 845 ELSE 760 message_string = 'unknown boundary condition: bc_salsa_t = "' & 761 // TRIM( bc_salsa_t ) // '"' 762 CALL message( 'check_parameters', 'SA0012', 1, 2, 0, 6, 0 ) 846 message_string = 'unknown boundary condition: bc_salsa_t = "' // TRIM( bc_salsa_t ) // '"' 847 CALL message( 'salsa_check_parameters', 'PA0596', 1, 2, 0, 6, 0 ) 763 848 ENDIF 764 849 765 850 IF ( nj3 < 1 .OR. nj3 > 3 ) THEN 766 851 message_string = 'unknown nj3 (must be 1-3)' 767 CALL message( ' check_parameters', 'SA0044', 1, 2, 0, 6, 0 )852 CALL message( 'salsa_check_parameters', 'PA0597', 1, 2, 0, 6, 0 ) 768 853 ENDIF 769 854 855 IF ( salsa_emission_mode == 'read_from_file' .AND. ibc_salsa_b == 0 ) THEN 856 message_string = 'salsa_emission_mode == read_from_file requires bc_salsa_b = "Neumann"' 857 CALL message( 'salsa_check_parameters','PA0598', 1, 2, 0, 6, 0 ) 858 ENDIF 859 770 860 END SUBROUTINE salsa_check_parameters 771 861 … … 775 865 ! ------------ 776 866 !> Subroutine defining appropriate grid for netcdf variables. 777 !> It is called out from subroutine netcdf. 867 !> It is called out from subroutine netcdf. 778 868 !> Same grid as for other scalars (see netcdf_interface_mod.f90) 779 869 !------------------------------------------------------------------------------! 780 870 SUBROUTINE salsa_define_netcdf_grid( var, found, grid_x, grid_y, grid_z ) 781 871 782 872 IMPLICIT NONE 783 873 784 CHARACTER (LEN=*), INTENT(OUT) :: grid_x !<785 CHARACTER (LEN=*), INTENT(OUT) :: grid_y !<786 CHARACTER (LEN=*), INTENT(OUT) :: grid_z !<787 CHARACTER 788 874 CHARACTER(LEN=*), INTENT(OUT) :: grid_x !< 875 CHARACTER(LEN=*), INTENT(OUT) :: grid_y !< 876 CHARACTER(LEN=*), INTENT(OUT) :: grid_z !< 877 CHARACTER(LEN=*), INTENT(IN) :: var !< 878 789 879 LOGICAL, INTENT(OUT) :: found !< 790 880 791 881 found = .TRUE. 792 882 ! … … 794 884 795 885 IF ( var(1:2) == 'g_' ) THEN 796 grid_x = 'x' 797 grid_y = 'y' 798 grid_z = 'zu' 886 grid_x = 'x' 887 grid_y = 'y' 888 grid_z = 'zu' 799 889 ELSEIF ( var(1:4) == 'LDSA' ) THEN 800 grid_x = 'x' 801 grid_y = 'y' 890 grid_x = 'x' 891 grid_y = 'y' 802 892 grid_z = 'zu' 803 893 ELSEIF ( var(1:5) == 'm_bin' ) THEN 804 grid_x = 'x' 805 grid_y = 'y' 894 grid_x = 'x' 895 grid_y = 'y' 806 896 grid_z = 'zu' 807 897 ELSEIF ( var(1:5) == 'N_bin' ) THEN 808 grid_x = 'x' 809 grid_y = 'y' 898 grid_x = 'x' 899 grid_y = 'y' 810 900 grid_z = 'zu' 811 901 ELSEIF ( var(1:4) == 'Ntot' ) THEN 812 grid_x = 'x' 813 grid_y = 'y' 902 grid_x = 'x' 903 grid_y = 'y' 814 904 grid_z = 'zu' 815 905 ELSEIF ( var(1:2) == 'PM' ) THEN 816 grid_x = 'x' 817 grid_y = 'y' 906 grid_x = 'x' 907 grid_y = 'y' 818 908 grid_z = 'zu' 819 909 ELSEIF ( var(1:2) == 's_' ) THEN 820 grid_x = 'x' 821 grid_y = 'y' 910 grid_x = 'x' 911 grid_y = 'y' 822 912 grid_z = 'zu' 823 913 ELSE … … 830 920 END SUBROUTINE salsa_define_netcdf_grid 831 921 832 833 922 !------------------------------------------------------------------------------! 834 923 ! Description: … … 846 935 WRITE( io, 2 ) skip_time_do_salsa 847 936 WRITE( io, 3 ) dt_salsa 848 WRITE( io, 12 ) SHAPE( aerosol_number(1)%conc ), nbins937 WRITE( io, 4 ) SHAPE( aerosol_number(1)%conc ), nbins_aerosol 849 938 IF ( advect_particle_water ) THEN 850 WRITE( io, 16 ) SHAPE( aerosol_mass(1)%conc ), ncc_tot*nbins,&939 WRITE( io, 5 ) SHAPE( aerosol_mass(1)%conc ), ncomponents_mass*nbins_aerosol, & 851 940 advect_particle_water 852 941 ELSE 853 WRITE( io, 16 ) SHAPE( aerosol_mass(1)%conc ), ncc*nbins, & 854 advect_particle_water 942 WRITE( io, 5 ) SHAPE( aerosol_mass(1)%conc ), ncc*nbins_aerosol, advect_particle_water 855 943 ENDIF 856 944 IF ( .NOT. salsa_gases_from_chem ) THEN 857 WRITE( io, 17 ) SHAPE( aerosol_mass(1)%conc ), ngast, & 858 salsa_gases_from_chem 945 WRITE( io, 6 ) SHAPE( aerosol_mass(1)%conc ), ngases_salsa, salsa_gases_from_chem 859 946 ENDIF 860 WRITE( io, 4 )947 WRITE( io, 7 ) 861 948 IF ( nsnucl > 0 ) THEN 862 WRITE( io, 5) nsnucl, nj3949 WRITE( io, 8 ) nsnucl, nj3 863 950 ENDIF 864 951 IF ( nlcoag ) THEN 865 WRITE( io, 6 )952 WRITE( io, 9 ) 866 953 ENDIF 867 954 IF ( nlcnd ) THEN 868 WRITE( io, 7 ) nlcndgas, nlcndh2oae 955 WRITE( io, 10 ) nlcndgas, nlcndh2oae 956 ENDIF 957 IF ( lspartition ) THEN 958 WRITE( io, 11 ) 869 959 ENDIF 870 960 IF ( nldepo ) THEN 871 WRITE( io, 1 4 ) nldepo_vege, nldepo_topo961 WRITE( io, 12 ) nldepo_pcm, nldepo_surf 872 962 ENDIF 873 WRITE( io, 8) reglim, nbin, bin_low_limits874 WRITE( io, 15) nsect875 WRITE( io, 1 3) ncc, listspec, mass_fracs_a, mass_fracs_b963 WRITE( io, 13 ) reglim, nbin, bin_low_limits 964 IF ( isdtyp == 0 ) WRITE( io, 14 ) nsect 965 WRITE( io, 15 ) ncc, listspec, mass_fracs_a, mass_fracs_b 876 966 IF ( .NOT. salsa_gases_from_chem ) THEN 877 WRITE( io, 18 ) ngast, H2SO4_init, HNO3_init, NH3_init, OCNV_init, & 878 OCSV_init 967 WRITE( io, 16 ) ngases_salsa, h2so4_init, hno3_init, nh3_init, ocnv_init, ocsv_init 879 968 ENDIF 880 WRITE( io, 9) isdtyp, igctyp969 WRITE( io, 17 ) isdtyp, igctyp 881 970 IF ( isdtyp == 0 ) THEN 882 WRITE( io, 1 0) dpg, sigmag, n_lognorm971 WRITE( io, 18 ) dpg, sigmag, n_lognorm 883 972 ELSE 884 WRITE( io, 1 1)973 WRITE( io, 19 ) 885 974 ENDIF 886 887 888 1 FORMAT (//' SALSA information:'/ & 975 IF ( nest_salsa ) WRITE( io, 20 ) nest_salsa 976 WRITE( io, 21 ) salsa_emission_mode 977 978 979 1 FORMAT (//' SALSA information:'/ & 889 980 ' ------------------------------'/) 890 981 2 FORMAT (' Starts at: skip_time_do_salsa = ', F10.2, ' s') 891 982 3 FORMAT (/' Timestep: dt_salsa = ', F6.2, ' s') 892 12 FORMAT (/' Array shape (z,y,x,bins):'/&983 4 FORMAT (/' Array shape (z,y,x,bins):'/ & 893 984 ' aerosol_number: ', 4(I3)) 894 16 FORMAT (/' aerosol_mass: ', 4(I3),/&985 5 FORMAT (/' aerosol_mass: ', 4(I3),/ & 895 986 ' (advect_particle_water = ', L1, ')') 896 17 FORMAT (' salsa_gas: ', 4(I3),/&987 6 FORMAT (' salsa_gas: ', 4(I3),/ & 897 988 ' (salsa_gases_from_chem = ', L1, ')') 898 4 FORMAT (/' Aerosol dynamic processes included: ') 899 5 FORMAT (/' nucleation (scheme = ', I1, ' and J3 parametrization = ',& 900 I1, ')') 901 6 FORMAT (/' coagulation') 902 7 FORMAT (/' condensation (of precursor gases = ', L1, & 903 ' and water vapour = ', L1, ')' ) 904 14 FORMAT (/' dry deposition (on vegetation = ', L1, & 905 ' and on topography = ', L1, ')') 906 8 FORMAT (/' Aerosol bin subrange limits (in metres): ', 3(ES10.2E3), / & 907 ' Number of size bins for each aerosol subrange: ', 2I3,/ & 989 7 FORMAT (/' Aerosol dynamic processes included: ') 990 8 FORMAT (/' nucleation (scheme = ', I1, ' and J3 parametrization = ', I1, ')') 991 9 FORMAT (/' coagulation') 992 10 FORMAT (/' condensation (of precursor gases = ', L1, ' and water vapour = ', L1, ')' ) 993 11 FORMAT (/' dissolutional growth by HNO3 and NH3') 994 12 FORMAT (/' dry deposition (on vegetation = ', L1, ' and on topography = ', L1, ')') 995 13 FORMAT (/' Aerosol bin subrange limits (in metres): ', 3(ES10.2E3), / & 996 ' Number of size bins for each aerosol subrange: ', 2I3,/ & 908 997 ' Aerosol bin limits (in metres): ', 9(ES10.2E3)) 909 15 FORMAT (' Initial number concentration in bins at the lowest level', & 910 ' (#/m**3):', 9(ES10.2E3)) 911 13 FORMAT (/' Number of chemical components used: ', I1,/ & 912 ' Species: ',7(A6),/ & 913 ' Initial relative contribution of each species to particle', & 914 ' volume in:',/ & 915 ' a-bins: ', 7(F6.3),/ & 998 14 FORMAT (' Initial number concentration in bins at the lowest level (#/m**3):', 9(ES10.2E3)) 999 15 FORMAT (/' Number of chemical components used: ', I1,/ & 1000 ' Species: ',7(A6),/ & 1001 ' Initial relative contribution of each species to particle volume in:',/ & 1002 ' a-bins: ', 7(F6.3),/ & 916 1003 ' b-bins: ', 7(F6.3)) 917 1 8 FORMAT (/' Number of gaseous tracers used: ', I1,/&918 ' Initial gas concentrations:',/ &919 ' H2SO4: ',ES12.4E3, ' #/m**3',/ &920 ' HNO3: ',ES12.4E3, ' #/m**3',/ &921 ' NH3: ',ES12.4E3, ' #/m**3',/ &922 ' OCNV: ',ES12.4E3, ' #/m**3',/ &1004 16 FORMAT (/' Number of gaseous tracers used: ', I1,/ & 1005 ' Initial gas concentrations:',/ & 1006 ' H2SO4: ',ES12.4E3, ' #/m**3',/ & 1007 ' HNO3: ',ES12.4E3, ' #/m**3',/ & 1008 ' NH3: ',ES12.4E3, ' #/m**3',/ & 1009 ' OCNV: ',ES12.4E3, ' #/m**3',/ & 923 1010 ' OCSV: ',ES12.4E3, ' #/m**3') 924 9 FORMAT (/' Initialising concentrations: ', /&925 ' Aerosol size distribution: isdtyp = ', I1,/ &1011 17 FORMAT (/' Initialising concentrations: ', / & 1012 ' Aerosol size distribution: isdtyp = ', I1,/ & 926 1013 ' Gas concentrations: igctyp = ', I1 ) 927 10 FORMAT ( ' Mode diametres: dpg(nmod) = ', 7(F7.3),/ & 928 ' Standard deviation: sigmag(nmod) = ', 7(F7.2),/ & 929 ' Number concentration: n_lognorm(nmod) = ', 7(ES12.4E3) ) 930 11 FORMAT (/' Size distribution read from a file.') 1014 18 FORMAT ( ' Mode diametres: dpg(nmod) = ', 7(F7.3), ' (m)', / & 1015 ' Standard deviation: sigmag(nmod) = ', 7(F7.2),/ & 1016 ' Number concentration: n_lognorm(nmod) = ', 7(ES12.4E3), ' (#/m3)' ) 1017 19 FORMAT (/' Size distribution read from a file.') 1018 20 FORMAT (/' Nesting for salsa variables: ', L1 ) 1019 21 FORMAT (/' Emissions: salsa_emission_mode = ', A ) 931 1020 932 1021 END SUBROUTINE salsa_header … … 938 1027 !------------------------------------------------------------------------------! 939 1028 SUBROUTINE salsa_init_arrays 940 941 USE surface_mod, & 942 ONLY: surf_def_h, surf_def_v, surf_lsm_h, surf_lsm_v, surf_usm_h, & 943 surf_usm_v 1029 1030 USE chem_gasphase_mod, & 1031 ONLY: nvar 1032 1033 USE surface_mod, & 1034 ONLY: surf_def_h, surf_def_v, surf_lsm_h, surf_lsm_v, surf_usm_h, surf_usm_v 944 1035 945 1036 IMPLICIT NONE 946 947 INTEGER(iwp) :: gases_available !< Number of available gas components in 948 !< the chemistry model 949 INTEGER(iwp) :: i !< loop index for allocating 950 INTEGER(iwp) :: l !< loop index for allocating: surfaces 951 INTEGER(iwp) :: lsp !< loop index for chem species in the chemistry model 952 1037 1038 INTEGER(iwp) :: gases_available !< Number of available gas components in the chemistry model 1039 INTEGER(iwp) :: i !< loop index for allocating 1040 INTEGER(iwp) :: l !< loop index for allocating: surfaces 1041 INTEGER(iwp) :: lsp !< loop index for chem species in the chemistry model 1042 953 1043 gases_available = 0 954 955 1044 ! 956 1045 !-- Allocate prognostic variables (see salsa_swap_timelevel) 957 958 1046 ! 959 1047 !-- Set derived indices: 960 !-- (This does the same as the subroutine salsa_initialize in SALSA/ 961 !-- UCLALES-SALSA) 962 in1a = 1 ! 1st index of subrange 1a 963 in2a = in1a + nbin(1) ! 1st index of subrange 2a 964 fn1a = in2a - 1 ! last index of subrange 1a 965 fn2a = fn1a + nbin(2) ! last index of subrange 2a 966 967 ! 968 !-- If the fraction of insoluble aerosols in subrange 2 is zero: do not allocate 969 !-- arrays for them 1048 !-- (This does the same as the subroutine salsa_initialize in SALSA/UCLALES-SALSA) 1049 start_subrange_1a = 1 ! 1st index of subrange 1a 1050 start_subrange_2a = start_subrange_1a + nbin(1) ! 1st index of subrange 2a 1051 end_subrange_1a = start_subrange_2a - 1 ! last index of subrange 1a 1052 end_subrange_2a = end_subrange_1a + nbin(2) ! last index of subrange 2a 1053 1054 ! 1055 !-- If the fraction of insoluble aerosols in subrange 2 is zero: do not allocate arrays for them 970 1056 IF ( nf2a > 0.999999_wp .AND. SUM( mass_fracs_b ) < 0.00001_wp ) THEN 971 1057 no_insoluble = .TRUE. 972 in2b = fn2a+1! 1st index of subrange 2b973 fn2b = fn2a! last index of subrange 2b1058 start_subrange_2b = end_subrange_2a+1 ! 1st index of subrange 2b 1059 end_subrange_2b = end_subrange_2a ! last index of subrange 2b 974 1060 ELSE 975 in2b = in2a + nbin(2)! 1st index of subrange 2b976 fn2b = fn2a + nbin(2)! last index of subrange 2b1061 start_subrange_2b = start_subrange_2a + nbin(2) ! 1st index of subrange 2b 1062 end_subrange_2b = end_subrange_2a + nbin(2) ! last index of subrange 2b 977 1063 ENDIF 978 979 980 nbins = fn2b ! total number of aerosol size bins 981 ! 1064 1065 nbins_aerosol = end_subrange_2b ! total number of aerosol size bins 1066 ! 982 1067 !-- Create index tables for different aerosol components 983 1068 CALL component_index_constructor( prtcl, ncc, maxspec, listspec ) 984 985 nc c_tot= ncc986 IF ( advect_particle_water ) nc c_tot= ncc + 1 ! Add water987 1069 1070 ncomponents_mass = ncc 1071 IF ( advect_particle_water ) ncomponents_mass = ncc + 1 ! Add water 1072 988 1073 ! 989 1074 !-- Allocate: 990 ALLOCATE( aero(nbins), bin_low_limits(nbins), nsect(nbins), massacc(nbins) ) 991 IF ( nldepo ) ALLOCATE( sedim_vd(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins) ) 992 ALLOCATE( Ra_dry(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins) ) 993 994 ! 1075 ALLOCATE( aero(nbins_aerosol), bc_am_t_val(nbins_aerosol*ncomponents_mass), & 1076 bc_an_t_val(ngases_salsa), bc_gt_t_val(nbins_aerosol), bin_low_limits(nbins_aerosol),& 1077 nsect(nbins_aerosol), massacc(nbins_aerosol) ) 1078 ALLOCATE( k_topo_top(nysg:nyng,nxlg:nxrg) ) 1079 IF ( nldepo ) ALLOCATE( sedim_vd(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins_aerosol) ) 1080 ALLOCATE( ra_dry(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins_aerosol) ) 1081 1082 ! 995 1083 !-- Aerosol number concentration 996 ALLOCATE( aerosol_number(nbins ) )997 ALLOCATE( nconc_1(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins ),&998 nconc_2(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins ),&999 nconc_3(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins ) )1084 ALLOCATE( aerosol_number(nbins_aerosol) ) 1085 ALLOCATE( nconc_1(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins_aerosol), & 1086 nconc_2(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins_aerosol), & 1087 nconc_3(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins_aerosol) ) 1000 1088 nconc_1 = 0.0_wp 1001 1089 nconc_2 = 0.0_wp 1002 1090 nconc_3 = 0.0_wp 1003 1004 DO i = 1, nbins 1091 1092 DO i = 1, nbins_aerosol 1005 1093 aerosol_number(i)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => nconc_1(:,:,:,i) 1006 1094 aerosol_number(i)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => nconc_2(:,:,:,i) … … 1012 1100 aerosol_number(i)%init(nzb:nzt+1), & 1013 1101 aerosol_number(i)%sums_ws_l(nzb:nzt+1,0:threads_per_task-1) ) 1014 ENDDO 1015 1016 ! 1017 !-- Aerosol mass concentration 1018 ALLOCATE( aerosol_mass(nc c_tot*nbins) )1019 ALLOCATE( mconc_1(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nc c_tot*nbins),&1020 mconc_2(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nc c_tot*nbins),&1021 mconc_3(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nc c_tot*nbins) )1102 ENDDO 1103 1104 ! 1105 !-- Aerosol mass concentration 1106 ALLOCATE( aerosol_mass(ncomponents_mass*nbins_aerosol) ) 1107 ALLOCATE( mconc_1(nzb:nzt+1,nysg:nyng,nxlg:nxrg,ncomponents_mass*nbins_aerosol), & 1108 mconc_2(nzb:nzt+1,nysg:nyng,nxlg:nxrg,ncomponents_mass*nbins_aerosol), & 1109 mconc_3(nzb:nzt+1,nysg:nyng,nxlg:nxrg,ncomponents_mass*nbins_aerosol) ) 1022 1110 mconc_1 = 0.0_wp 1023 1111 mconc_2 = 0.0_wp 1024 1112 mconc_3 = 0.0_wp 1025 1026 DO i = 1, nc c_tot*nbins1113 1114 DO i = 1, ncomponents_mass*nbins_aerosol 1027 1115 aerosol_mass(i)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => mconc_1(:,:,:,i) 1028 1116 aerosol_mass(i)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => mconc_2(:,:,:,i) 1029 aerosol_mass(i)%tconc_m(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => mconc_3(:,:,:,i) 1030 ALLOCATE( aerosol_mass(i)%flux_s(nzb+1:nzt,0:threads_per_task-1), &1031 aerosol_mass(i)%diss_s(nzb+1:nzt,0:threads_per_task-1), &1032 aerosol_mass(i)%flux_l(nzb+1:nzt,nys:nyn,0:threads_per_task-1), &1033 aerosol_mass(i)%diss_l(nzb+1:nzt,nys:nyn,0:threads_per_task-1), &1034 aerosol_mass(i)%init(nzb:nzt+1), &1117 aerosol_mass(i)%tconc_m(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => mconc_3(:,:,:,i) 1118 ALLOCATE( aerosol_mass(i)%flux_s(nzb+1:nzt,0:threads_per_task-1), & 1119 aerosol_mass(i)%diss_s(nzb+1:nzt,0:threads_per_task-1), & 1120 aerosol_mass(i)%flux_l(nzb+1:nzt,nys:nyn,0:threads_per_task-1), & 1121 aerosol_mass(i)%diss_l(nzb+1:nzt,nys:nyn,0:threads_per_task-1), & 1122 aerosol_mass(i)%init(nzb:nzt+1), & 1035 1123 aerosol_mass(i)%sums_ws_l(nzb:nzt+1,0:threads_per_task-1) ) 1036 1124 ENDDO 1037 1038 ! 1039 !-- Surface fluxes: answs = aerosol number, amsws = aerosol mass 1125 1126 ! 1127 !-- Surface fluxes: answs = aerosol number, amsws = aerosol mass 1040 1128 ! 1041 1129 !-- Horizontal surfaces: default type 1042 1130 DO l = 0, 2 ! upward (l=0), downward (l=1) and model top (l=2) 1043 ALLOCATE( surf_def_h(l)%answs( 1:surf_def_h(l)%ns, nbins ) )1044 ALLOCATE( surf_def_h(l)%amsws( 1:surf_def_h(l)%ns, nbins *ncc_tot) )1131 ALLOCATE( surf_def_h(l)%answs( 1:surf_def_h(l)%ns, nbins_aerosol ) ) 1132 ALLOCATE( surf_def_h(l)%amsws( 1:surf_def_h(l)%ns, nbins_aerosol*ncomponents_mass ) ) 1045 1133 surf_def_h(l)%answs = 0.0_wp 1046 1134 surf_def_h(l)%amsws = 0.0_wp 1047 1135 ENDDO 1048 !-- Horizontal surfaces: natural type 1049 IF ( land_surface ) THEN 1050 ALLOCATE( surf_lsm_h%answs( 1:surf_lsm_h%ns, nbins ) ) 1051 ALLOCATE( surf_lsm_h%amsws( 1:surf_lsm_h%ns, nbins*ncc_tot ) ) 1052 surf_lsm_h%answs = 0.0_wp 1053 surf_lsm_h%amsws = 0.0_wp 1054 ENDIF 1055 !-- Horizontal surfaces: urban type 1056 IF ( urban_surface ) THEN 1057 ALLOCATE( surf_usm_h%answs( 1:surf_usm_h%ns, nbins ) ) 1058 ALLOCATE( surf_usm_h%amsws( 1:surf_usm_h%ns, nbins*ncc_tot ) ) 1059 surf_usm_h%answs = 0.0_wp 1060 surf_usm_h%amsws = 0.0_wp 1061 ENDIF 1062 ! 1063 !-- Vertical surfaces: northward (l=0), southward (l=1), eastward (l=2) and 1064 !-- westward (l=3) facing 1065 DO l = 0, 3 1066 ALLOCATE( surf_def_v(l)%answs( 1:surf_def_v(l)%ns, nbins ) ) 1136 ! 1137 !-- Horizontal surfaces: natural type 1138 ALLOCATE( surf_lsm_h%answs( 1:surf_lsm_h%ns, nbins_aerosol ) ) 1139 ALLOCATE( surf_lsm_h%amsws( 1:surf_lsm_h%ns, nbins_aerosol*ncomponents_mass ) ) 1140 surf_lsm_h%answs = 0.0_wp 1141 surf_lsm_h%amsws = 0.0_wp 1142 ! 1143 !-- Horizontal surfaces: urban type 1144 ALLOCATE( surf_usm_h%answs( 1:surf_usm_h%ns, nbins_aerosol ) ) 1145 ALLOCATE( surf_usm_h%amsws( 1:surf_usm_h%ns, nbins_aerosol*ncomponents_mass ) ) 1146 surf_usm_h%answs = 0.0_wp 1147 surf_usm_h%amsws = 0.0_wp 1148 1149 ! 1150 !-- Vertical surfaces: northward (l=0), southward (l=1), eastward (l=2) and westward (l=3) facing 1151 DO l = 0, 3 1152 ALLOCATE( surf_def_v(l)%answs( 1:surf_def_v(l)%ns, nbins_aerosol ) ) 1067 1153 surf_def_v(l)%answs = 0.0_wp 1068 ALLOCATE( surf_def_v(l)%amsws( 1:surf_def_v(l)%ns, nbins *ncc_tot) )1154 ALLOCATE( surf_def_v(l)%amsws( 1:surf_def_v(l)%ns, nbins_aerosol*ncomponents_mass ) ) 1069 1155 surf_def_v(l)%amsws = 0.0_wp 1070 1071 IF ( land_surface) THEN 1072 ALLOCATE( surf_lsm_v(l)%answs( 1:surf_lsm_v(l)%ns, nbins ) ) 1073 surf_lsm_v(l)%answs = 0.0_wp 1074 ALLOCATE( surf_lsm_v(l)%amsws( 1:surf_lsm_v(l)%ns, nbins*ncc_tot ) ) 1075 surf_lsm_v(l)%amsws = 0.0_wp 1076 ENDIF 1077 1078 IF ( urban_surface ) THEN 1079 ALLOCATE( surf_usm_v(l)%answs( 1:surf_usm_v(l)%ns, nbins ) ) 1080 surf_usm_v(l)%answs = 0.0_wp 1081 ALLOCATE( surf_usm_v(l)%amsws( 1:surf_usm_v(l)%ns, nbins*ncc_tot ) ) 1082 surf_usm_v(l)%amsws = 0.0_wp 1083 ENDIF 1084 ENDDO 1085 1156 1157 ALLOCATE( surf_lsm_v(l)%answs( 1:surf_lsm_v(l)%ns, nbins_aerosol ) ) 1158 surf_lsm_v(l)%answs = 0.0_wp 1159 ALLOCATE( surf_lsm_v(l)%amsws( 1:surf_lsm_v(l)%ns, nbins_aerosol*ncomponents_mass ) ) 1160 surf_lsm_v(l)%amsws = 0.0_wp 1161 1162 ALLOCATE( surf_usm_v(l)%answs( 1:surf_usm_v(l)%ns, nbins_aerosol ) ) 1163 surf_usm_v(l)%answs = 0.0_wp 1164 ALLOCATE( surf_usm_v(l)%amsws( 1:surf_usm_v(l)%ns, nbins_aerosol*ncomponents_mass ) ) 1165 surf_usm_v(l)%amsws = 0.0_wp 1166 1167 ENDDO 1168 1086 1169 ! 1087 1170 !-- Concentration of gaseous tracers (1. SO4, 2. HNO3, 3. NH3, 4. OCNV, 5. OCSV) … … 1091 1174 !-- allocate salsa_gas array. 1092 1175 1093 IF ( air_chemistry ) THEN 1176 IF ( air_chemistry ) THEN 1094 1177 DO lsp = 1, nvar 1095 IF ( TRIM( chem_species(lsp)%name ) == 'H2SO4' ) THEN 1096 gases_available = gases_available + 1 1097 gas_index_chem(1) = lsp 1098 ELSEIF ( TRIM( chem_species(lsp)%name ) == 'HNO3' ) THEN 1099 gases_available = gases_available + 1 1100 gas_index_chem(2) = lsp 1101 ELSEIF ( TRIM( chem_species(lsp)%name ) == 'NH3' ) THEN 1102 gases_available = gases_available + 1 1103 gas_index_chem(3) = lsp 1104 ELSEIF ( TRIM( chem_species(lsp)%name ) == 'OCNV' ) THEN 1105 gases_available = gases_available + 1 1106 gas_index_chem(4) = lsp 1107 ELSEIF ( TRIM( chem_species(lsp)%name ) == 'OCSV' ) THEN 1108 gases_available = gases_available + 1 1109 gas_index_chem(5) = lsp 1110 ENDIF 1178 SELECT CASE ( TRIM( chem_species(lsp)%name ) ) 1179 CASE ( 'H2SO4', 'h2so4' ) 1180 gases_available = gases_available + 1 1181 gas_index_chem(1) = lsp 1182 CASE ( 'HNO3', 'hno3' ) 1183 gases_available = gases_available + 1 1184 gas_index_chem(2) = lsp 1185 CASE ( 'NH3', 'nh3' ) 1186 gases_available = gases_available + 1 1187 gas_index_chem(3) = lsp 1188 CASE ( 'OCNV', 'ocnv' ) 1189 gases_available = gases_available + 1 1190 gas_index_chem(4) = lsp 1191 CASE ( 'OCSV', 'ocsv' ) 1192 gases_available = gases_available + 1 1193 gas_index_chem(5) = lsp 1194 END SELECT 1111 1195 ENDDO 1112 1196 1113 IF ( gases_available == ngas t) THEN1197 IF ( gases_available == ngases_salsa ) THEN 1114 1198 salsa_gases_from_chem = .TRUE. 1115 1199 ELSE 1116 WRITE( message_string, * ) 'SALSA is run together with chemistry '// & 1117 'but not all gaseous components are '// & 1118 'provided by kpp (H2SO4, HNO3, NH3, '// & 1119 'OCNV, OCSC)' 1120 CALL message( 'check_parameters', 'SA0024', 1, 2, 0, 6, 0 ) 1200 WRITE( message_string, * ) 'SALSA is run together with chemistry but not all gaseous '// & 1201 'components are provided by kpp (H2SO4, HNO3, NH3, OCNV, OCSV)' 1202 CALL message( 'check_parameters', 'PA0599', 1, 2, 0, 6, 0 ) 1121 1203 ENDIF 1122 1204 1123 1205 ELSE 1124 1206 1125 ALLOCATE( salsa_gas(ngas t) )1126 ALLOCATE( gconc_1(nzb:nzt+1,nysg:nyng,nxlg:nxrg,ngas t), &1127 gconc_2(nzb:nzt+1,nysg:nyng,nxlg:nxrg,ngas t), &1128 gconc_3(nzb:nzt+1,nysg:nyng,nxlg:nxrg,ngas t) )1207 ALLOCATE( salsa_gas(ngases_salsa) ) 1208 ALLOCATE( gconc_1(nzb:nzt+1,nysg:nyng,nxlg:nxrg,ngases_salsa), & 1209 gconc_2(nzb:nzt+1,nysg:nyng,nxlg:nxrg,ngases_salsa), & 1210 gconc_3(nzb:nzt+1,nysg:nyng,nxlg:nxrg,ngases_salsa) ) 1129 1211 gconc_1 = 0.0_wp 1130 1212 gconc_2 = 0.0_wp 1131 1213 gconc_3 = 0.0_wp 1132 1133 DO i = 1, ngas t1214 1215 DO i = 1, ngases_salsa 1134 1216 salsa_gas(i)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => gconc_1(:,:,:,i) 1135 1217 salsa_gas(i)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => gconc_2(:,:,:,i) … … 1141 1223 salsa_gas(i)%init(nzb:nzt+1), & 1142 1224 salsa_gas(i)%sums_ws_l(nzb:nzt+1,0:threads_per_task-1) ) 1143 ENDDO 1225 ENDDO 1144 1226 ! 1145 1227 !-- Surface fluxes: gtsws = gaseous tracer flux … … 1147 1229 !-- Horizontal surfaces: default type 1148 1230 DO l = 0, 2 ! upward (l=0), downward (l=1) and model top (l=2) 1149 ALLOCATE( surf_def_h(l)%gtsws( 1:surf_def_h(l)%ns, ngas t) )1231 ALLOCATE( surf_def_h(l)%gtsws( 1:surf_def_h(l)%ns, ngases_salsa ) ) 1150 1232 surf_def_h(l)%gtsws = 0.0_wp 1151 1233 ENDDO 1152 !-- Horizontal surfaces: natural type 1153 IF ( land_surface ) THEN 1154 ALLOCATE( surf_lsm_h%gtsws( 1:surf_lsm_h%ns, ngast ) ) 1155 surf_lsm_h%gtsws = 0.0_wp 1156 ENDIF 1157 !-- Horizontal surfaces: urban type 1158 IF ( urban_surface ) THEN 1159 ALLOCATE( surf_usm_h%gtsws( 1:surf_usm_h%ns, ngast ) ) 1160 surf_usm_h%gtsws = 0.0_wp 1161 ENDIF 1234 !-- Horizontal surfaces: natural type 1235 ALLOCATE( surf_lsm_h%gtsws( 1:surf_lsm_h%ns, ngases_salsa ) ) 1236 surf_lsm_h%gtsws = 0.0_wp 1237 !-- Horizontal surfaces: urban type 1238 ALLOCATE( surf_usm_h%gtsws( 1:surf_usm_h%ns, ngases_salsa ) ) 1239 surf_usm_h%gtsws = 0.0_wp 1162 1240 ! 1163 1241 !-- Vertical surfaces: northward (l=0), southward (l=1), eastward (l=2) and 1164 1242 !-- westward (l=3) facing 1165 DO l = 0, 3 1166 ALLOCATE( surf_def_v(l)%gtsws( 1:surf_def_v(l)%ns, ngas t) )1243 DO l = 0, 3 1244 ALLOCATE( surf_def_v(l)%gtsws( 1:surf_def_v(l)%ns, ngases_salsa ) ) 1167 1245 surf_def_v(l)%gtsws = 0.0_wp 1168 IF ( land_surface ) THEN 1169 ALLOCATE( surf_lsm_v(l)%gtsws( 1:surf_lsm_v(l)%ns, ngast ) ) 1170 surf_lsm_v(l)%gtsws = 0.0_wp 1171 ENDIF 1172 IF ( urban_surface ) THEN 1173 ALLOCATE( surf_usm_v(l)%gtsws( 1:surf_usm_v(l)%ns, ngast ) ) 1174 surf_usm_v(l)%gtsws = 0.0_wp 1175 ENDIF 1246 ALLOCATE( surf_lsm_v(l)%gtsws( 1:surf_lsm_v(l)%ns, ngases_salsa ) ) 1247 surf_lsm_v(l)%gtsws = 0.0_wp 1248 ALLOCATE( surf_usm_v(l)%gtsws( 1:surf_usm_v(l)%ns, ngases_salsa ) ) 1249 surf_usm_v(l)%gtsws = 0.0_wp 1176 1250 ENDDO 1177 1251 ENDIF 1178 1252 1179 1253 END SUBROUTINE salsa_init_arrays 1180 1254 … … 1182 1256 ! Description: 1183 1257 ! ------------ 1184 !> Initialization of SALSA. Based on salsa_initialize in UCLALES-SALSA. 1258 !> Initialization of SALSA. Based on salsa_initialize in UCLALES-SALSA. 1185 1259 !> Subroutines salsa_initialize, SALSAinit and DiagInitAero in UCLALES-SALSA are 1186 1260 !> also merged here. … … 1189 1263 1190 1264 IMPLICIT NONE 1191 1192 INTEGER(iwp) :: b 1193 INTEGER(iwp) :: c 1194 INTEGER(iwp) :: g 1195 INTEGER(iwp) :: i 1196 INTEGER(iwp) :: j 1197 1198 CALL location_message( 'initializing SALSA model', .TRUE. ) 1199 1265 1266 INTEGER(iwp) :: i !< 1267 INTEGER(iwp) :: ib !< loop index for aerosol number bins 1268 INTEGER(iwp) :: ic !< loop index for aerosol mass bins 1269 INTEGER(iwp) :: ig !< loop index for gases 1270 INTEGER(iwp) :: ii !< index for indexing 1271 INTEGER(iwp) :: j !< 1272 1273 CALL location_message( 'initializing salsa (sectional aerosol module )', .TRUE. ) 1274 1200 1275 bin_low_limits = 0.0_wp 1276 k_topo_top = 0 1201 1277 nsect = 0.0_wp 1202 massacc = 1.0_wp 1203 1278 massacc = 1.0_wp 1279 1204 1280 ! 1205 1281 !-- Indices for chemical components used (-1 = not used) 1206 i = 01282 ii = 0 1207 1283 IF ( is_used( prtcl, 'SO4' ) ) THEN 1208 i so4 = get_index( prtcl,'SO4' )1209 i =i + 11284 index_so4 = get_index( prtcl,'SO4' ) 1285 ii = ii + 1 1210 1286 ENDIF 1211 1287 IF ( is_used( prtcl,'OC' ) ) THEN 1212 i oc = get_index(prtcl, 'OC')1213 i =i + 11288 index_oc = get_index(prtcl, 'OC') 1289 ii = ii + 1 1214 1290 ENDIF 1215 1291 IF ( is_used( prtcl, 'BC' ) ) THEN 1216 i bc = get_index( prtcl, 'BC' )1217 i =i + 11292 index_bc = get_index( prtcl, 'BC' ) 1293 ii = ii + 1 1218 1294 ENDIF 1219 1295 IF ( is_used( prtcl, 'DU' ) ) THEN 1220 i du = get_index( prtcl, 'DU' )1221 i =i + 11296 index_du = get_index( prtcl, 'DU' ) 1297 ii = ii + 1 1222 1298 ENDIF 1223 1299 IF ( is_used( prtcl, 'SS' ) ) THEN 1224 i ss = get_index( prtcl, 'SS' )1225 i =i + 11300 index_ss = get_index( prtcl, 'SS' ) 1301 ii = ii + 1 1226 1302 ENDIF 1227 1303 IF ( is_used( prtcl, 'NO' ) ) THEN 1228 in o = get_index( prtcl, 'NO' )1229 i =i + 11304 index_no = get_index( prtcl, 'NO' ) 1305 ii = ii + 1 1230 1306 ENDIF 1231 1307 IF ( is_used( prtcl, 'NH' ) ) THEN 1232 in h = get_index( prtcl, 'NH' )1233 i =i + 11308 index_nh = get_index( prtcl, 'NH' ) 1309 ii = ii + 1 1234 1310 ENDIF 1235 ! 1311 ! 1236 1312 !-- All species must be known 1237 IF ( i /= ncc ) THEN 1238 message_string = 'Unknown aerosol species/component(s) given in the' // & 1239 ' initialization' 1240 CALL message( 'salsa_mod: salsa_init', 'SA0020', 1, 2, 0, 6, 0 ) 1313 IF ( ii /= ncc ) THEN 1314 message_string = 'Unknown aerosol species/component(s) given in the initialization' 1315 CALL message( 'salsa_mod: salsa_init', 'PA0600', 1, 2, 0, 6, 0 ) 1241 1316 ENDIF 1242 1317 ! 1318 !-- Partition and dissolutional growth by gaseous HNO3 and NH3 1319 IF ( index_no > 0 .AND. index_nh > 0 .AND. index_so4 > 0 ) lspartition = .TRUE. 1243 1320 ! 1244 1321 !-- Initialise … … 1249 1326 aero(:)%numc = nclim 1250 1327 aero(:)%core = 1.0E-10_wp 1251 DO c = 1, maxspec+1 ! 1:SO4, 2:OC, 3:BC, 4:DU, 5:SS, 6:NO, 7:NH, 8:H2O1252 aero(:)%volc( c) = 0.0_wp1328 DO ic = 1, maxspec+1 ! 1:SO4, 2:OC, 3:BC, 4:DU, 5:SS, 6:NO, 7:NH, 8:H2O 1329 aero(:)%volc(ic) = 0.0_wp 1253 1330 ENDDO 1254 1255 IF ( nldepo ) sedim_vd = 0.0_wp 1256 1257 DO b = 1, nbins1258 IF ( .NOT. read_restart_data_salsa ) aerosol_number( b)%conc = nclim1259 aerosol_number( b)%conc_p = 0.0_wp1260 aerosol_number( b)%tconc_m = 0.0_wp1261 aerosol_number( b)%flux_s = 0.0_wp1262 aerosol_number( b)%diss_s = 0.0_wp1263 aerosol_number( b)%flux_l = 0.0_wp1264 aerosol_number( b)%diss_l = 0.0_wp1265 aerosol_number( b)%init = nclim1266 aerosol_number( b)%sums_ws_l = 0.0_wp1331 1332 IF ( nldepo ) sedim_vd = 0.0_wp 1333 1334 DO ib = 1, nbins_aerosol 1335 IF ( .NOT. read_restart_data_salsa ) aerosol_number(ib)%conc = nclim 1336 aerosol_number(ib)%conc_p = 0.0_wp 1337 aerosol_number(ib)%tconc_m = 0.0_wp 1338 aerosol_number(ib)%flux_s = 0.0_wp 1339 aerosol_number(ib)%diss_s = 0.0_wp 1340 aerosol_number(ib)%flux_l = 0.0_wp 1341 aerosol_number(ib)%diss_l = 0.0_wp 1342 aerosol_number(ib)%init = nclim 1343 aerosol_number(ib)%sums_ws_l = 0.0_wp 1267 1344 ENDDO 1268 DO c = 1, ncc_tot*nbins1269 IF ( .NOT. read_restart_data_salsa ) aerosol_mass( c)%conc = mclim1270 aerosol_mass( c)%conc_p = 0.0_wp1271 aerosol_mass( c)%tconc_m = 0.0_wp1272 aerosol_mass( c)%flux_s = 0.0_wp1273 aerosol_mass( c)%diss_s = 0.0_wp1274 aerosol_mass( c)%flux_l = 0.0_wp1275 aerosol_mass( c)%diss_l = 0.0_wp1276 aerosol_mass( c)%init = mclim1277 aerosol_mass( c)%sums_ws_l = 0.0_wp1345 DO ic = 1, ncomponents_mass*nbins_aerosol 1346 IF ( .NOT. read_restart_data_salsa ) aerosol_mass(ic)%conc = mclim 1347 aerosol_mass(ic)%conc_p = 0.0_wp 1348 aerosol_mass(ic)%tconc_m = 0.0_wp 1349 aerosol_mass(ic)%flux_s = 0.0_wp 1350 aerosol_mass(ic)%diss_s = 0.0_wp 1351 aerosol_mass(ic)%flux_l = 0.0_wp 1352 aerosol_mass(ic)%diss_l = 0.0_wp 1353 aerosol_mass(ic)%init = mclim 1354 aerosol_mass(ic)%sums_ws_l = 0.0_wp 1278 1355 ENDDO 1279 1356 1280 1357 IF ( .NOT. salsa_gases_from_chem ) THEN 1281 DO g = 1, ngast1282 salsa_gas( g)%conc_p = 0.0_wp1283 salsa_gas( g)%tconc_m = 0.0_wp1284 salsa_gas( g)%flux_s = 0.0_wp1285 salsa_gas( g)%diss_s = 0.0_wp1286 salsa_gas( g)%flux_l = 0.0_wp1287 salsa_gas( g)%diss_l = 0.0_wp1288 salsa_gas( g)%sums_ws_l = 0.0_wp1358 DO ig = 1, ngases_salsa 1359 salsa_gas(ig)%conc_p = 0.0_wp 1360 salsa_gas(ig)%tconc_m = 0.0_wp 1361 salsa_gas(ig)%flux_s = 0.0_wp 1362 salsa_gas(ig)%diss_s = 0.0_wp 1363 salsa_gas(ig)%flux_l = 0.0_wp 1364 salsa_gas(ig)%diss_l = 0.0_wp 1365 salsa_gas(ig)%sums_ws_l = 0.0_wp 1289 1366 ENDDO 1290 1367 IF ( .NOT. read_restart_data_salsa ) THEN 1291 salsa_gas(1)%conc = H2SO4_init1292 salsa_gas(2)%conc = HNO3_init1293 salsa_gas(3)%conc = NH3_init1294 salsa_gas(4)%conc = OCNV_init1295 salsa_gas(5)%conc = OCSV_init1368 salsa_gas(1)%conc = h2so4_init 1369 salsa_gas(2)%conc = hno3_init 1370 salsa_gas(3)%conc = nh3_init 1371 salsa_gas(4)%conc = ocnv_init 1372 salsa_gas(5)%conc = ocsv_init 1296 1373 ENDIF 1297 1374 ! 1298 1375 !-- Set initial value for gas compound tracers and initial values 1299 salsa_gas(1)%init = H2SO4_init1300 salsa_gas(2)%init = HNO3_init1301 salsa_gas(3)%init = NH3_init1302 salsa_gas(4)%init = OCNV_init1303 salsa_gas(5)%init = OCSV_init1376 salsa_gas(1)%init = h2so4_init 1377 salsa_gas(2)%init = hno3_init 1378 salsa_gas(3)%init = nh3_init 1379 salsa_gas(4)%init = ocnv_init 1380 salsa_gas(5)%init = ocsv_init 1304 1381 ENDIF 1305 1382 ! 1306 1383 !-- Aerosol radius in each bin: dry and wet (m) 1307 Ra_dry = 1.0E-10_wp1308 ! 1309 !-- Initialise aerosol tracers 1384 ra_dry = 1.0E-10_wp 1385 ! 1386 !-- Initialise aerosol tracers 1310 1387 aero(:)%vhilim = 0.0_wp 1311 1388 aero(:)%vlolim = 0.0_wp … … 1315 1392 ! 1316 1393 !-- Initialise the sectional particle size distribution 1317 CALL set_sizebins() 1318 ! 1319 !-- Initialise location-dependent aerosol size distributions and 1320 !-- chemical compositions: 1321 CALL aerosol_init 1322 ! 1323 !-- Initalisation run of SALSA 1394 CALL set_sizebins 1395 ! 1396 !-- Initialise location-dependent aerosol size distributions and chemical compositions: 1397 CALL aerosol_init 1398 ! 1399 !-- Initalisation run of SALSA + calculate the vertical top index of the topography 1324 1400 DO i = nxl, nxr 1325 1401 DO j = nys, nyn 1402 1403 k_topo_top(j,i) = MAXLOC( MERGE( 1, 0, BTEST( wall_flags_0(:,j,i), 12 ) ), DIM = 1 ) - 1 1404 1326 1405 CALL salsa_driver( i, j, 1 ) 1327 1406 CALL salsa_diagnostics( i, j ) 1328 1407 ENDDO 1329 ENDDO 1330 ! 1331 !-- Set the aerosol and gas sources 1332 IF ( salsa_source_mode == 'read_from_file' ) THEN 1333 CALL salsa_set_source 1408 ENDDO 1409 ! 1410 !-- Initialise the deposition scheme and surface types 1411 IF ( nldepo ) CALL init_deposition 1412 1413 IF ( salsa_emission_mode /= 'no_emission' ) THEN 1414 ! 1415 !-- Read in and initialize emissions 1416 CALL salsa_emission_setup( .TRUE. ) 1417 IF ( .NOT. salsa_gases_from_chem .AND. salsa_emission_mode == 'read_from_file' ) THEN 1418 CALL salsa_gas_emission_setup( .TRUE. ) 1419 ENDIF 1334 1420 ENDIF 1335 1421 1336 1422 CALL location_message( 'finished', .TRUE. ) 1337 1423 1338 1424 END SUBROUTINE salsa_init 1339 1425 … … 1363 1449 !------------------------------------------------------------------------------! 1364 1450 SUBROUTINE set_sizebins 1365 1451 1366 1452 IMPLICIT NONE 1367 ! 1368 !-- Local variables 1369 INTEGER(iwp) :: cc1370 INTEGER(iwp) :: dd 1371 REAL(wp) :: ratio_d !< ratio of the upper and lower diameter of subranges1372 ! 1373 !-- vlolim&vhilim: min & max *dry* volumes [fxm] 1453 1454 INTEGER(iwp) :: cc !< running index 1455 INTEGER(iwp) :: dd !< running index 1456 1457 REAL(wp) :: ratio_d !< ratio of the upper and lower diameter of subranges 1458 ! 1459 !-- vlolim&vhilim: min & max *dry* volumes [fxm] 1374 1460 !-- dmid: bin mid *dry* diameter (m) 1375 1461 !-- vratiolo&vratiohi: volume ratio between the center and low/high limit … … 1377 1463 !-- 1) Size subrange 1: 1378 1464 ratio_d = reglim(2) / reglim(1) ! section spacing (m) 1379 DO cc = in1a,fn1a 1380 aero(cc)%vlolim = api6 * ( reglim(1) * ratio_d ** & 1381 ( REAL( cc-1 ) / nbin(1) ) ) ** 3.0_wp 1382 aero(cc)%vhilim = api6 * ( reglim(1) * ratio_d ** & 1383 ( REAL( cc ) / nbin(1) ) ) ** 3.0_wp 1384 aero(cc)%dmid = SQRT( ( aero(cc)%vhilim / api6 ) ** ( 1.0_wp / 3.0_wp ) & 1385 * ( aero(cc)%vlolim / api6 ) ** ( 1.0_wp / 3.0_wp ) ) 1386 aero(cc)%vratiohi = aero(cc)%vhilim / ( api6 * aero(cc)%dmid ** 3.0_wp ) 1387 aero(cc)%vratiolo = aero(cc)%vlolim / ( api6 * aero(cc)%dmid ** 3.0_wp ) 1465 DO cc = start_subrange_1a, end_subrange_1a 1466 aero(cc)%vlolim = api6 * ( reglim(1) * ratio_d**( REAL( cc-1 ) / nbin(1) ) )**3 1467 aero(cc)%vhilim = api6 * ( reglim(1) * ratio_d**( REAL( cc ) / nbin(1) ) )**3 1468 aero(cc)%dmid = SQRT( ( aero(cc)%vhilim / api6 )**0.33333333_wp * & 1469 ( aero(cc)%vlolim / api6 )**0.33333333_wp ) 1470 aero(cc)%vratiohi = aero(cc)%vhilim / ( api6 * aero(cc)%dmid**3 ) 1471 aero(cc)%vratiolo = aero(cc)%vlolim / ( api6 * aero(cc)%dmid**3 ) 1388 1472 ENDDO 1389 1473 ! 1390 !-- 2) Size subrange 2: 1474 !-- 2) Size subrange 2: 1391 1475 !-- 2.1) Sub-subrange 2a: high hygroscopicity 1392 1476 ratio_d = reglim(3) / reglim(2) ! section spacing 1393 DO dd = in2a, fn2a 1394 cc = dd - in2a 1395 aero(dd)%vlolim = api6 * ( reglim(2) * ratio_d ** & 1396 ( REAL( cc ) / nbin(2) ) ) ** 3.0_wp 1397 aero(dd)%vhilim = api6 * ( reglim(2) * ratio_d ** & 1398 ( REAL( cc+1 ) / nbin(2) ) ) ** 3.0_wp 1399 aero(dd)%dmid = SQRT( ( aero(dd)%vhilim / api6 ) ** ( 1.0_wp / 3.0_wp ) & 1400 * ( aero(dd)%vlolim / api6 ) ** ( 1.0_wp / 3.0_wp ) ) 1401 aero(dd)%vratiohi = aero(dd)%vhilim / ( api6 * aero(dd)%dmid ** 3.0_wp ) 1402 aero(dd)%vratiolo = aero(dd)%vlolim / ( api6 * aero(dd)%dmid ** 3.0_wp ) 1477 DO dd = start_subrange_2a, end_subrange_2a 1478 cc = dd - start_subrange_2a 1479 aero(dd)%vlolim = api6 * ( reglim(2) * ratio_d**( REAL( cc ) / nbin(2) ) )**3 1480 aero(dd)%vhilim = api6 * ( reglim(2) * ratio_d**( REAL( cc+1 ) / nbin(2) ) )**3 1481 aero(dd)%dmid = SQRT( ( aero(dd)%vhilim / api6 )**0.33333333_wp * & 1482 ( aero(dd)%vlolim / api6 )**0.33333333_wp ) 1483 aero(dd)%vratiohi = aero(dd)%vhilim / ( api6 * aero(dd)%dmid**3 ) 1484 aero(dd)%vratiolo = aero(dd)%vlolim / ( api6 * aero(dd)%dmid**3 ) 1403 1485 ENDDO 1404 ! 1486 ! 1405 1487 !-- 2.2) Sub-subrange 2b: low hygroscopicity 1406 1488 IF ( .NOT. no_insoluble ) THEN 1407 aero( in2b:fn2b)%vlolim = aero(in2a:fn2a)%vlolim1408 aero( in2b:fn2b)%vhilim = aero(in2a:fn2a)%vhilim1409 aero( in2b:fn2b)%dmid = aero(in2a:fn2a)%dmid1410 aero( in2b:fn2b)%vratiohi = aero(in2a:fn2a)%vratiohi1411 aero( in2b:fn2b)%vratiolo = aero(in2a:fn2a)%vratiolo1489 aero(start_subrange_2b:end_subrange_2b)%vlolim = aero(start_subrange_2a:end_subrange_2a)%vlolim 1490 aero(start_subrange_2b:end_subrange_2b)%vhilim = aero(start_subrange_2a:end_subrange_2a)%vhilim 1491 aero(start_subrange_2b:end_subrange_2b)%dmid = aero(start_subrange_2a:end_subrange_2a)%dmid 1492 aero(start_subrange_2b:end_subrange_2b)%vratiohi = aero(start_subrange_2a:end_subrange_2a)%vratiohi 1493 aero(start_subrange_2b:end_subrange_2b)%vratiolo = aero(start_subrange_2a:end_subrange_2a)%vratiolo 1412 1494 ENDIF 1413 ! 1414 !-- Initialize the wet diameter with the bin dry diameter to avoid numerical 1415 !-- problems later 1495 ! 1496 !-- Initialize the wet diameter with the bin dry diameter to avoid numerical problems later 1416 1497 aero(:)%dwet = aero(:)%dmid 1417 1498 ! 1418 !-- Save bin limits (lower diameter) to be delivered to the host modelif needed1419 DO cc = 1, nbins 1420 bin_low_limits(cc) = ( aero(cc)%vlolim / api6 )** ( 1.0_wp / 3.0_wp )1421 ENDDO 1422 1499 !-- Save bin limits (lower diameter) to be delivered to PALM if needed 1500 DO cc = 1, nbins_aerosol 1501 bin_low_limits(cc) = ( aero(cc)%vlolim / api6 )**0.33333333_wp 1502 ENDDO 1503 1423 1504 END SUBROUTINE set_sizebins 1424 1505 1425 1506 !------------------------------------------------------------------------------! 1426 1507 ! Description: … … 1434 1515 !------------------------------------------------------------------------------! 1435 1516 SUBROUTINE aerosol_init 1436 1437 USE arrays_3d, & 1438 ONLY: zu 1439 1440 ! USE NETCDF 1441 1442 USE netcdf_data_input_mod, & 1443 ONLY: get_attribute, get_variable, & 1444 netcdf_data_input_get_dimension_length, open_read_file 1445 1517 1518 USE netcdf_data_input_mod, & 1519 ONLY: get_attribute, get_variable, netcdf_data_input_get_dimension_length, open_read_file 1520 1446 1521 IMPLICIT NONE 1447 1448 INTEGER(iwp) :: b !< loop index: size bins 1449 INTEGER(iwp) :: c !< loop index: chemical components 1450 INTEGER(iwp) :: ee !< index: end 1451 INTEGER(iwp) :: g !< loop index: gases 1452 INTEGER(iwp) :: i !< loop index: x-direction 1453 INTEGER(iwp) :: id_faero !< NetCDF id of PIDS_SALSA 1454 INTEGER(iwp) :: id_fchem !< NetCDF id of PIDS_CHEM 1455 INTEGER(iwp) :: j !< loop index: y-direction 1456 INTEGER(iwp) :: k !< loop index: z-direction 1457 INTEGER(iwp) :: kk !< loop index: z-direction 1458 INTEGER(iwp) :: nz_file !< Number of grid-points in file (heights) 1459 INTEGER(iwp) :: prunmode 1460 INTEGER(iwp) :: ss !< index: start 1461 LOGICAL :: netcdf_extend = .FALSE. !< Flag indicating wether netcdf 1462 !< topography input file or not 1463 REAL(wp), DIMENSION(nbins) :: core !< size of the bin mid aerosol particle, 1464 REAL(wp) :: flag !< flag to mask topography grid points 1465 REAL(wp), DIMENSION(:,:), ALLOCATABLE :: pr_gas !< gas profiles 1466 REAL(wp), DIMENSION(:,:), ALLOCATABLE :: pr_mass_fracs_a !< mass fraction 1467 !< profiles: a 1468 REAL(wp), DIMENSION(:,:), ALLOCATABLE :: pr_mass_fracs_b !< and b 1469 REAL(wp), DIMENSION(:,:), ALLOCATABLE :: pr_nsect !< sectional size 1470 !< distribution profile 1471 REAL(wp), DIMENSION(nbins) :: nsect !< size distribution (#/m3) 1472 REAL(wp), DIMENSION(0:nz+1,nbins) :: pndist !< size dist as a function 1473 !< of height (#/m3) 1474 REAL(wp), DIMENSION(0:nz+1) :: pnf2a !< number fraction: bins 2a 1475 REAL(wp), DIMENSION(0:nz+1,maxspec) :: pvf2a !< mass distributions of 1476 !< aerosol species for a 1477 REAL(wp), DIMENSION(0:nz+1,maxspec) :: pvf2b !< and b-bins 1478 REAL(wp), DIMENSION(0:nz+1) :: pvfOC1a !< mass fraction between 1479 !< SO4 and OC in 1a 1480 REAL(wp), DIMENSION(:), ALLOCATABLE :: pr_z 1481 1522 1523 CHARACTER(LEN=25), DIMENSION(:), ALLOCATABLE :: cc_name !< chemical component name 1524 1525 INTEGER(iwp) :: ee !< index: end 1526 INTEGER(iwp) :: i !< loop index: x-direction 1527 INTEGER(iwp) :: ib !< loop index: size bins 1528 INTEGER(iwp) :: ic !< loop index: chemical components 1529 INTEGER(iwp) :: id_dyn !< NetCDF id of PIDS_DYNAMIC_SALSA 1530 INTEGER(iwp) :: ig !< loop index: gases 1531 INTEGER(iwp) :: j !< loop index: y-direction 1532 INTEGER(iwp) :: k !< loop index: z-direction 1533 INTEGER(iwp) :: lod_aero !< level of detail of inital aerosol concentrations 1534 INTEGER(iwp) :: pr_nbins !< Number of aerosol size bins in file 1535 INTEGER(iwp) :: pr_ncc !< Number of aerosol chemical components in file 1536 INTEGER(iwp) :: pr_nz !< Number of vertical grid-points in file 1537 INTEGER(iwp) :: prunmode !< running mode of SALSA 1538 INTEGER(iwp) :: ss !< index: start 1539 1540 INTEGER(iwp), DIMENSION(maxspec) :: cc_input_to_model 1541 1542 LOGICAL :: netcdf_extend = .FALSE. !< Flag: netcdf file exists 1543 1544 REAL(wp) :: flag !< flag to mask topography grid points 1545 1546 REAL(wp), DIMENSION(nbins_aerosol) :: core !< size of the bin mid aerosol particle 1547 REAL(wp), DIMENSION(nbins_aerosol) :: nsect !< size distribution (#/m3) 1548 1549 REAL(wp), DIMENSION(0:nz+1) :: pnf2a !< number fraction in 2a 1550 REAL(wp), DIMENSION(0:nz+1) :: pmfoc1a !< mass fraction of OC in 1a 1551 1552 REAL(wp), DIMENSION(0:nz+1,nbins_aerosol) :: pndist !< size dist as a function of height (#/m3) 1553 REAL(wp), DIMENSION(0:nz+1,maxspec) :: pmf2a !< mass distributions in subrange 2a 1554 REAL(wp), DIMENSION(0:nz+1,maxspec) :: pmf2b !< mass distributions in subrange 2b 1555 1556 REAL(wp), DIMENSION(:), ALLOCATABLE :: pr_dmid !< vertical profile of aerosol bin diameters 1557 REAL(wp), DIMENSION(:), ALLOCATABLE :: pr_z !< z levels of profiles 1558 1559 REAL(wp), DIMENSION(:,:), ALLOCATABLE :: pr_mass_fracs_a !< mass fraction: a 1560 REAL(wp), DIMENSION(:,:), ALLOCATABLE :: pr_mass_fracs_b !< and b 1561 1562 cc_input_to_model = 0 1482 1563 prunmode = 1 1483 1564 ! 1484 1565 !-- Bin mean aerosol particle volume (m3) 1485 1566 core(:) = 0.0_wp 1486 core(1:nbins ) = api6 * aero(1:nbins)%dmid ** 3.0_wp1487 ! 1488 !-- Set concentrations to zero 1567 core(1:nbins_aerosol) = api6 * aero(1:nbins_aerosol)%dmid**3 1568 ! 1569 !-- Set concentrations to zero 1489 1570 nsect(:) = 0.0_wp 1490 1571 pndist(:,:) = 0.0_wp 1491 pnf2a(:) = nf2a 1492 p vf2a(:,:) = 0.0_wp1493 p vf2b(:,:) = 0.0_wp1494 p vfOC1a(:) = 0.0_wp1572 pnf2a(:) = nf2a 1573 pmf2a(:,:) = 0.0_wp 1574 pmf2b(:,:) = 0.0_wp 1575 pmfoc1a(:) = 0.0_wp 1495 1576 1496 1577 IF ( isdtyp == 1 ) THEN 1497 1578 ! 1498 !-- Read input profiles from PIDS_ SALSA1579 !-- Read input profiles from PIDS_DYNAMIC_SALSA 1499 1580 #if defined( __netcdf ) 1500 ! 1501 !-- Location-dependent size distributions and compositions. 1502 INQUIRE( FILE ='PIDS_SALSA'// TRIM( coupling_char ), EXIST=netcdf_extend )1581 ! 1582 !-- Location-dependent size distributions and compositions. 1583 INQUIRE( FILE = TRIM( input_file_dynamic ) // TRIM( coupling_char ), EXIST = netcdf_extend ) 1503 1584 IF ( netcdf_extend ) THEN 1504 1585 ! 1505 !-- Open file in read-only mode 1506 CALL open_read_file( 'PIDS_SALSA' // TRIM( coupling_char ), id_faero ) 1507 ! 1508 !-- Input heights 1509 CALL netcdf_data_input_get_dimension_length( id_faero, nz_file, & 1510 "profile_z" ) 1511 1512 ALLOCATE( pr_z(nz_file), pr_mass_fracs_a(maxspec,nz_file), & 1513 pr_mass_fracs_b(maxspec,nz_file), pr_nsect(nbins,nz_file) ) 1514 CALL get_variable( id_faero, 'profile_z', pr_z ) 1515 ! 1516 !-- Mass fracs profile: 1: H2SO4 (sulphuric acid), 2: OC (organic carbon), 1517 !-- 3: BC (black carbon), 4: DU (dust), 1518 !-- 5: SS (sea salt), 6: HNO3 (nitric acid), 1519 !-- 7: NH3 (ammonia) 1520 CALL get_variable( id_faero, "profile_mass_fracs_a", pr_mass_fracs_a,& 1521 0, nz_file-1, 0, maxspec-1 ) 1522 CALL get_variable( id_faero, "profile_mass_fracs_b", pr_mass_fracs_b,& 1523 0, nz_file-1, 0, maxspec-1 ) 1524 CALL get_variable( id_faero, "profile_nsect", pr_nsect, 0, nz_file-1,& 1525 0, nbins-1 ) 1526 1527 kk = 1 1528 DO k = nzb, nz+1 1529 IF ( kk < nz_file ) THEN 1530 DO WHILE ( pr_z(kk+1) <= zu(k) ) 1531 kk = kk + 1 1532 IF ( kk == nz_file ) EXIT 1533 ENDDO 1586 !-- Open file in read-only mode 1587 CALL open_read_file( input_file_dynamic // TRIM( coupling_char ), id_dyn ) 1588 ! 1589 !-- Inquire dimensions: 1590 CALL netcdf_data_input_get_dimension_length( id_dyn, pr_nz, 'z' ) 1591 IF ( pr_nz /= nz ) THEN 1592 WRITE( message_string, * ) 'Number of inifor horizontal grid points does not match '//& 1593 'the number of numeric grid points.' 1594 CALL message( 'aerosol_init', 'PA0601', 1, 2, 0, 6, 0 ) 1595 ENDIF 1596 CALL netcdf_data_input_get_dimension_length( id_dyn, pr_ncc, 'composition_index' ) 1597 ! 1598 !-- Allocate memory 1599 ALLOCATE( pr_z(1:pr_nz), pr_mass_fracs_a(nzb:nzt+1,pr_ncc), & 1600 pr_mass_fracs_b(nzb:nzt+1,pr_ncc) ) 1601 pr_mass_fracs_a = 0.0_wp 1602 pr_mass_fracs_b = 0.0_wp 1603 ! 1604 !-- Read vertical levels 1605 CALL get_variable( id_dyn, 'z', pr_z ) 1606 ! 1607 !-- Read name and index of chemical components 1608 CALL get_variable( id_dyn, 'composition_name', cc_name, pr_ncc ) 1609 DO ic = 1, pr_ncc 1610 SELECT CASE ( TRIM( cc_name(ic) ) ) 1611 CASE ( 'H2SO4', 'SO4', 'h2so4', 'so4' ) 1612 cc_input_to_model(1) = ic 1613 CASE ( 'OC', 'oc' ) 1614 cc_input_to_model(2) = ic 1615 CASE ( 'BC', 'bc' ) 1616 cc_input_to_model(3) = ic 1617 CASE ( 'DU', 'du' ) 1618 cc_input_to_model(4) = ic 1619 CASE ( 'SS', 'ss' ) 1620 cc_input_to_model(5) = ic 1621 CASE ( 'HNO3', 'hno3', 'NO', 'no' ) 1622 cc_input_to_model(6) = ic 1623 CASE ( 'NH3', 'nh3', 'NH', 'nh' ) 1624 cc_input_to_model(7) = ic 1625 END SELECT 1626 ENDDO 1627 1628 IF ( SUM( cc_input_to_model ) == 0 ) THEN 1629 message_string = 'None of the aerosol chemical components in ' // TRIM( & 1630 input_file_dynamic ) // ' correspond to ones applied in SALSA.' 1631 CALL message( 'salsa_mod: aerosol_init', 'PA0602', 2, 2, 0, 6, 0 ) 1632 ENDIF 1633 ! 1634 !-- Vertical profiles of mass fractions of different chemical components: 1635 CALL get_variable( id_dyn, 'init_atmosphere_mass_fracs_a', pr_mass_fracs_a, & 1636 0, pr_ncc-1, 0, pr_nz-1 ) 1637 CALL get_variable( id_dyn, 'init_atmosphere_mass_fracs_b', pr_mass_fracs_b, & 1638 0, pr_ncc-1, 0, pr_nz-1 ) 1639 ! 1640 !-- Match the input data with the chemical composition applied in the model 1641 DO ic = 1, maxspec 1642 ss = cc_input_to_model(ic) 1643 IF ( ss == 0 ) CYCLE 1644 pmf2a(nzb+1:nzt+1,ic) = pr_mass_fracs_a(nzb:nzt,ss) 1645 pmf2b(nzb+1:nzt+1,ic) = pr_mass_fracs_b(nzb:nzt,ss) 1646 ENDDO 1647 ! 1648 !-- Aerosol concentrations: lod=1 (total PM) or lod=2 (sectional number size distribution) 1649 CALL get_attribute( id_dyn, 'lod', lod_aero, .FALSE., 'init_atmosphere_aerosol' ) 1650 IF ( lod_aero /= 2 ) THEN 1651 message_string = 'Currently only lod=2 accepted for init_atmosphere_aerosol' 1652 CALL message( 'salsa_mod: aerosol_init', 'PA0603', 2, 2, 0, 6, 0 ) 1653 ELSE 1654 ! 1655 !-- Bin mean diameters in the input file 1656 CALL netcdf_data_input_get_dimension_length( id_dyn, pr_nbins, 'Dmid') 1657 IF ( pr_nbins /= nbins_aerosol ) THEN 1658 message_string = 'Number of size bins in init_atmosphere_aerosol does not match ' & 1659 // 'with that applied in the model' 1660 CALL message( 'salsa_mod: aerosol_init', 'PA0604', 2, 2, 0, 6, 0 ) 1534 1661 ENDIF 1535 IF ( kk < nz_file ) THEN 1536 ! 1537 !-- Set initial value for gas compound tracers and initial values 1538 pvf2a(k,:) = pr_mass_fracs_a(:,kk) + ( zu(k) - pr_z(kk) ) / ( & 1539 pr_z(kk+1) - pr_z(kk) ) * ( pr_mass_fracs_a(:,kk+1)& 1540 - pr_mass_fracs_a(:,kk) ) 1541 pvf2b(k,:) = pr_mass_fracs_b(:,kk) + ( zu(k) - pr_z(kk) ) / ( & 1542 pr_z(kk+1) - pr_z(kk) ) * ( pr_mass_fracs_b(:,kk+1)& 1543 - pr_mass_fracs_b(:,kk) ) 1544 pndist(k,:) = pr_nsect(:,kk) + ( zu(k) - pr_z(kk) ) / ( & 1545 pr_z(kk+1) - pr_z(kk) ) * ( pr_nsect(:,kk+1) - & 1546 pr_nsect(:,kk) ) 1547 ELSE 1548 pvf2a(k,:) = pr_mass_fracs_a(:,kk) 1549 pvf2b(k,:) = pr_mass_fracs_b(:,kk) 1550 pndist(k,:) = pr_nsect(:,kk) 1662 1663 ALLOCATE( pr_dmid(pr_nbins) ) 1664 pr_dmid = 0.0_wp 1665 1666 CALL get_variable( id_dyn, 'Dmid', pr_dmid ) 1667 ! 1668 !-- Check whether the sectional representation conform to the one 1669 !-- applied in the model 1670 IF ( ANY( ABS( ( aero(1:nbins_aerosol)%dmid - pr_dmid ) / & 1671 aero(1:nbins_aerosol)%dmid ) > 0.1_wp ) ) THEN 1672 message_string = 'Mean diameters of the aerosol size bins ' // TRIM( & 1673 input_file_dynamic ) // ' in do not conform to the sectional '// & 1674 'representation of the model.' 1675 CALL message( 'salsa_mod: aerosol_init', 'PA0605', 2, 2, 0, 6, 0 ) 1551 1676 ENDIF 1552 IF ( iso4 < 0 ) THEN 1553 pvf2a(k,1) = 0.0_wp 1554 pvf2b(k,1) = 0.0_wp 1555 ENDIF 1556 IF ( ioc < 0 ) THEN 1557 pvf2a(k,2) = 0.0_wp 1558 pvf2b(k,2) = 0.0_wp 1559 ENDIF 1560 IF ( ibc < 0 ) THEN 1561 pvf2a(k,3) = 0.0_wp 1562 pvf2b(k,3) = 0.0_wp 1563 ENDIF 1564 IF ( idu < 0 ) THEN 1565 pvf2a(k,4) = 0.0_wp 1566 pvf2b(k,4) = 0.0_wp 1567 ENDIF 1568 IF ( iss < 0 ) THEN 1569 pvf2a(k,5) = 0.0_wp 1570 pvf2b(k,5) = 0.0_wp 1571 ENDIF 1572 IF ( ino < 0 ) THEN 1573 pvf2a(k,6) = 0.0_wp 1574 pvf2b(k,6) = 0.0_wp 1575 ENDIF 1576 IF ( inh < 0 ) THEN 1577 pvf2a(k,7) = 0.0_wp 1578 pvf2b(k,7) = 0.0_wp 1579 ENDIF 1580 ! 1581 !-- Then normalise the mass fraction so that SUM = 1 1582 pvf2a(k,:) = pvf2a(k,:) / SUM( pvf2a(k,:) ) 1583 IF ( SUM( pvf2b(k,:) ) > 0.0_wp ) pvf2b(k,:) = pvf2b(k,:) / & 1584 SUM( pvf2b(k,:) ) 1585 ENDDO 1586 DEALLOCATE( pr_z, pr_mass_fracs_a, pr_mass_fracs_b, pr_nsect ) 1677 ! 1678 !-- Inital aerosol concentrations 1679 CALL get_variable( id_dyn, 'init_atmosphere_aerosol', pndist(nzb+1:nzt,:), & 1680 0, pr_nbins-1, 0, pr_nz-1 ) 1681 ENDIF 1682 ! 1683 !-- Set bottom and top boundary condition (Neumann) 1684 pmf2a(nzb,:) = pmf2a(nzb+1,:) 1685 pmf2a(nzt+1,:) = pmf2a(nzt,:) 1686 pmf2b(nzb,:) = pmf2b(nzb+1,:) 1687 pmf2b(nzt+1,:) = pmf2b(nzt,:) 1688 pndist(nzb,:) = pndist(nzb+1,:) 1689 pndist(nzt+1,:) = pndist(nzt,:) 1690 1691 IF ( index_so4 < 0 ) THEN 1692 pmf2a(:,1) = 0.0_wp 1693 pmf2b(:,1) = 0.0_wp 1694 ENDIF 1695 IF ( index_oc < 0 ) THEN 1696 pmf2a(:,2) = 0.0_wp 1697 pmf2b(:,2) = 0.0_wp 1698 ENDIF 1699 IF ( index_bc < 0 ) THEN 1700 pmf2a(:,3) = 0.0_wp 1701 pmf2b(:,3) = 0.0_wp 1702 ENDIF 1703 IF ( index_du < 0 ) THEN 1704 pmf2a(:,4) = 0.0_wp 1705 pmf2b(:,4) = 0.0_wp 1706 ENDIF 1707 IF ( index_ss < 0 ) THEN 1708 pmf2a(:,5) = 0.0_wp 1709 pmf2b(:,5) = 0.0_wp 1710 ENDIF 1711 IF ( index_no < 0 ) THEN 1712 pmf2a(:,6) = 0.0_wp 1713 pmf2b(:,6) = 0.0_wp 1714 ENDIF 1715 IF ( index_nh < 0 ) THEN 1716 pmf2a(:,7) = 0.0_wp 1717 pmf2b(:,7) = 0.0_wp 1718 ENDIF 1719 1720 IF ( SUM( pmf2a ) < 0.00001_wp .AND. SUM( pmf2b ) < 0.00001_wp ) THEN 1721 message_string = 'Error in initialising mass fractions of chemical components. ' // & 1722 'Check that all chemical components are included in parameter file!' 1723 CALL message( 'salsa_mod: aerosol_init', 'PA0606', 2, 2, 0, 6, 0 ) 1724 ENDIF 1725 ! 1726 !-- Then normalise the mass fraction so that SUM = 1 1727 DO k = nzb, nzt+1 1728 pmf2a(k,:) = pmf2a(k,:) / SUM( pmf2a(k,:) ) 1729 IF ( SUM( pmf2b(k,:) ) > 0.0_wp ) pmf2b(k,:) = pmf2b(k,:) / SUM( pmf2b(k,:) ) 1730 ENDDO 1731 1732 DEALLOCATE( pr_z, pr_mass_fracs_a, pr_mass_fracs_b ) 1733 1587 1734 ELSE 1588 message_string = 'Input file '// TRIM( 'PIDS_SALSA' ) // & 1589 TRIM( coupling_char ) // ' for SALSA missing!' 1590 CALL message( 'salsa_mod: aerosol_init', 'SA0032', 1, 2, 0, 6, 0 ) 1591 ENDIF ! netcdf_extend 1735 message_string = 'Input file '// TRIM( input_file_dynamic ) // TRIM( coupling_char ) // & 1736 ' for SALSA missing!' 1737 CALL message( 'salsa_mod: aerosol_init', 'PA0607', 1, 2, 0, 6, 0 ) 1738 1739 ENDIF ! netcdf_extend 1740 1741 #else 1742 message_string = 'isdtyp = 1 but preprocessor directive __netcdf is not used in compiling!' 1743 CALL message( 'salsa_mod: aerosol_init', 'PA0608', 1, 2, 0, 6, 0 ) 1744 1592 1745 #endif 1593 1746 1594 1747 ELSEIF ( isdtyp == 0 ) THEN 1595 1748 ! 1596 1749 !-- Mass fractions for species in a and b-bins 1597 IF ( iso4 > 0 ) THEN 1598 pvf2a(:,1) = mass_fracs_a(iso4) 1599 pvf2b(:,1) = mass_fracs_b(iso4) 1600 ENDIF 1601 IF ( ioc > 0 ) THEN 1602 pvf2a(:,2) = mass_fracs_a(ioc) 1603 pvf2b(:,2) = mass_fracs_b(ioc) 1604 ENDIF 1605 IF ( ibc > 0 ) THEN 1606 pvf2a(:,3) = mass_fracs_a(ibc) 1607 pvf2b(:,3) = mass_fracs_b(ibc) 1608 ENDIF 1609 IF ( idu > 0 ) THEN 1610 pvf2a(:,4) = mass_fracs_a(idu) 1611 pvf2b(:,4) = mass_fracs_b(idu) 1612 ENDIF 1613 IF ( iss > 0 ) THEN 1614 pvf2a(:,5) = mass_fracs_a(iss) 1615 pvf2b(:,5) = mass_fracs_b(iss) 1616 ENDIF 1617 IF ( ino > 0 ) THEN 1618 pvf2a(:,6) = mass_fracs_a(ino) 1619 pvf2b(:,6) = mass_fracs_b(ino) 1620 ENDIF 1621 IF ( inh > 0 ) THEN 1622 pvf2a(:,7) = mass_fracs_a(inh) 1623 pvf2b(:,7) = mass_fracs_b(inh) 1624 ENDIF 1625 DO k = nzb, nz+1 1626 pvf2a(k,:) = pvf2a(k,:) / SUM( pvf2a(k,:) ) 1627 IF ( SUM( pvf2b(k,:) ) > 0.0_wp ) pvf2b(k,:) = pvf2b(k,:) / & 1628 SUM( pvf2b(k,:) ) 1750 IF ( index_so4 > 0 ) THEN 1751 pmf2a(:,1) = mass_fracs_a(index_so4) 1752 pmf2b(:,1) = mass_fracs_b(index_so4) 1753 ENDIF 1754 IF ( index_oc > 0 ) THEN 1755 pmf2a(:,2) = mass_fracs_a(index_oc) 1756 pmf2b(:,2) = mass_fracs_b(index_oc) 1757 ENDIF 1758 IF ( index_bc > 0 ) THEN 1759 pmf2a(:,3) = mass_fracs_a(index_bc) 1760 pmf2b(:,3) = mass_fracs_b(index_bc) 1761 ENDIF 1762 IF ( index_du > 0 ) THEN 1763 pmf2a(:,4) = mass_fracs_a(index_du) 1764 pmf2b(:,4) = mass_fracs_b(index_du) 1765 ENDIF 1766 IF ( index_ss > 0 ) THEN 1767 pmf2a(:,5) = mass_fracs_a(index_ss) 1768 pmf2b(:,5) = mass_fracs_b(index_ss) 1769 ENDIF 1770 IF ( index_no > 0 ) THEN 1771 pmf2a(:,6) = mass_fracs_a(index_no) 1772 pmf2b(:,6) = mass_fracs_b(index_no) 1773 ENDIF 1774 IF ( index_nh > 0 ) THEN 1775 pmf2a(:,7) = mass_fracs_a(index_nh) 1776 pmf2b(:,7) = mass_fracs_b(index_nh) 1777 ENDIF 1778 DO k = nzb, nzt+1 1779 pmf2a(k,:) = pmf2a(k,:) / SUM( pmf2a(k,:) ) 1780 IF ( SUM( pmf2b(k,:) ) > 0.0_wp ) pmf2b(k,:) = pmf2b(k,:) / SUM( pmf2b(k,:) ) 1629 1781 ENDDO 1630 1782 1631 1783 CALL size_distribution( n_lognorm, dpg, sigmag, nsect ) 1632 1784 ! 1633 1785 !-- Normalize by the given total number concentration 1634 nsect = nsect * SUM( n_lognorm ) * 1.0E+6_wp / SUM( nsect )1635 DO b = in1a, fn2b1636 pndist(:, b) = nsect(b)1786 nsect = nsect * SUM( n_lognorm ) / SUM( nsect ) 1787 DO ib = start_subrange_1a, end_subrange_2b 1788 pndist(:,ib) = nsect(ib) 1637 1789 ENDDO 1638 1790 ENDIF 1639 1791 1640 1792 IF ( igctyp == 1 ) THEN 1641 1793 ! 1642 !-- Read input profiles from PIDS_CHEM 1794 !-- Read input profiles from PIDS_CHEM 1643 1795 #if defined( __netcdf ) 1644 ! 1645 !-- Location-dependent size distributions and compositions. 1646 INQUIRE( FILE ='PIDS_CHEM' // TRIM( coupling_char ), EXIST=netcdf_extend )1796 ! 1797 !-- Location-dependent size distributions and compositions. 1798 INQUIRE( FILE = TRIM( input_file_dynamic ) // TRIM( coupling_char ), EXIST = netcdf_extend ) 1647 1799 IF ( netcdf_extend .AND. .NOT. salsa_gases_from_chem ) THEN 1648 1800 ! 1649 !-- Open file in read-only mode 1650 CALL open_read_file( 'PIDS_CHEM' // TRIM( coupling_char ), id_fchem ) 1651 ! 1652 !-- Input heights 1653 CALL netcdf_data_input_get_dimension_length( id_fchem, nz_file, & 1654 "profile_z" ) 1655 ALLOCATE( pr_z(nz_file), pr_gas(ngast,nz_file) ) 1656 CALL get_variable( id_fchem, 'profile_z', pr_z ) 1657 ! 1658 !-- Gases: 1659 CALL get_variable( id_fchem, "profile_H2SO4", pr_gas(1,:) ) 1660 CALL get_variable( id_fchem, "profile_HNO3", pr_gas(2,:) ) 1661 CALL get_variable( id_fchem, "profile_NH3", pr_gas(3,:) ) 1662 CALL get_variable( id_fchem, "profile_OCNV", pr_gas(4,:) ) 1663 CALL get_variable( id_fchem, "profile_OCSV", pr_gas(5,:) ) 1664 1665 kk = 1 1666 DO k = nzb, nz+1 1667 IF ( kk < nz_file ) THEN 1668 DO WHILE ( pr_z(kk+1) <= zu(k) ) 1669 kk = kk + 1 1670 IF ( kk == nz_file ) EXIT 1671 ENDDO 1672 ENDIF 1673 IF ( kk < nz_file ) THEN 1674 ! 1675 !-- Set initial value for gas compound tracers and initial values 1676 DO g = 1, ngast 1677 salsa_gas(g)%init(k) = pr_gas(g,kk) + ( zu(k) - pr_z(kk) ) & 1678 / ( pr_z(kk+1) - pr_z(kk) ) * & 1679 ( pr_gas(g,kk+1) - pr_gas(g,kk) ) 1680 salsa_gas(g)%conc(k,:,:) = salsa_gas(g)%init(k) 1681 ENDDO 1682 ELSE 1683 DO g = 1, ngast 1684 salsa_gas(g)%init(k) = pr_gas(g,kk) 1685 salsa_gas(g)%conc(k,:,:) = salsa_gas(g)%init(k) 1686 ENDDO 1687 ENDIF 1801 !-- Open file in read-only mode 1802 CALL open_read_file( input_file_dynamic // TRIM( coupling_char ), id_dyn ) 1803 ! 1804 !-- Inquire dimensions: 1805 CALL netcdf_data_input_get_dimension_length( id_dyn, pr_nz, 'z' ) 1806 IF ( pr_nz /= nz ) THEN 1807 WRITE( message_string, * ) 'Number of inifor horizontal grid points does not match '//& 1808 'the number of numeric grid points.' 1809 CALL message( 'aerosol_init', 'PA0609', 1, 2, 0, 6, 0 ) 1810 ENDIF 1811 ! 1812 !-- Read vertical profiles of gases: 1813 CALL get_variable( id_dyn, 'init_atmosphere_h2so4', salsa_gas(1)%init(nzb+1:nzt) ) 1814 CALL get_variable( id_dyn, 'init_atmosphere_hno3', salsa_gas(2)%init(nzb+1:nzt) ) 1815 CALL get_variable( id_dyn, 'init_atmosphere_nh3', salsa_gas(3)%init(nzb+1:nzt) ) 1816 CALL get_variable( id_dyn, 'init_atmosphere_ocnv', salsa_gas(4)%init(nzb+1:nzt) ) 1817 CALL get_variable( id_dyn, 'init_atmosphere_ocsv', salsa_gas(5)%init(nzb+1:nzt) ) 1818 ! 1819 !-- Set Neumann top and surface boundary condition for initial + initialise concentrations 1820 DO ig = 1, ngases_salsa 1821 salsa_gas(ig)%init(nzb) = salsa_gas(ig)%init(nzb+1) 1822 salsa_gas(ig)%init(nzt+1) = salsa_gas(ig)%init(nzt) 1823 DO k = nzb, nzt+1 1824 salsa_gas(ig)%conc(k,:,:) = salsa_gas(ig)%init(k) 1825 ENDDO 1688 1826 ENDDO 1689 1690 DEALLOCATE( pr_z, pr_gas ) 1827 1691 1828 ELSEIF ( .NOT. netcdf_extend .AND. .NOT. salsa_gases_from_chem ) THEN 1692 message_string = 'Input file '// TRIM( 'PIDS_CHEM' ) // & 1693 TRIM( coupling_char ) // ' for SALSA missing!' 1694 CALL message( 'salsa_mod: aerosol_init', 'SA0033', 1, 2, 0, 6, 0 ) 1695 ENDIF ! netcdf_extend 1829 message_string = 'Input file '// TRIM( input_file_dynamic ) // TRIM( coupling_char ) // & 1830 ' for SALSA missing!' 1831 CALL message( 'salsa_mod: aerosol_init', 'PA0610', 1, 2, 0, 6, 0 ) 1832 ENDIF ! netcdf_extend 1833 #else 1834 message_string = 'igctyp = 1 but preprocessor directive __netcdf is not used in compiling!' 1835 CALL message( 'salsa_mod: aerosol_init', 'PA0611', 1, 2, 0, 6, 0 ) 1836 1696 1837 #endif 1697 1838 1698 1839 ENDIF 1699 1700 IF ( ioc > 0 .AND. iso4 > 0 ) THEN 1701 !-- Both are there, so use the given "massDistrA" 1702 pvfOC1a(:) = pvf2a(:,2) / ( pvf2a(:,2) + pvf2a(:,1) ) ! Normalize 1703 ELSEIF ( ioc > 0 ) THEN 1704 !-- Pure organic carbon 1705 pvfOC1a(:) = 1.0_wp 1706 ELSEIF ( iso4 > 0 ) THEN 1707 !-- Pure SO4 1708 pvfOC1a(:) = 0.0_wp 1840 ! 1841 !-- Both SO4 and OC are included, so use the given mass fractions 1842 IF ( index_oc > 0 .AND. index_so4 > 0 ) THEN 1843 pmfoc1a(:) = pmf2a(:,2) / ( pmf2a(:,2) + pmf2a(:,1) ) ! Normalize 1844 ! 1845 !-- Pure organic carbon 1846 ELSEIF ( index_oc > 0 ) THEN 1847 pmfoc1a(:) = 1.0_wp 1848 ! 1849 !-- Pure SO4 1850 ELSEIF ( index_so4 > 0 ) THEN 1851 pmfoc1a(:) = 0.0_wp 1852 1709 1853 ELSE 1710 1854 message_string = 'Either OC or SO4 must be active for aerosol region 1a!' 1711 CALL message( 'salsa_mod: aerosol_init', ' SA0021', 1, 2, 0, 6, 0 )1712 ENDIF 1713 1855 CALL message( 'salsa_mod: aerosol_init', 'PA0612', 1, 2, 0, 6, 0 ) 1856 ENDIF 1857 1714 1858 ! 1715 1859 !-- Initialize concentrations 1716 DO i = nxlg, nxrg 1860 DO i = nxlg, nxrg 1717 1861 DO j = nysg, nyng 1718 1862 DO k = nzb, nzt+1 1719 1863 ! 1720 !-- Predetermine flag to mask topography 1864 !-- Predetermine flag to mask topography 1721 1865 flag = MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(k,j,i), 0 ) ) 1722 ! 1866 ! 1723 1867 !-- a) Number concentrations 1724 !-- 1725 DO b = in1a, fn1a1726 aerosol_number( b)%conc(k,j,i) = pndist(k,b) * flag1868 !-- Region 1: 1869 DO ib = start_subrange_1a, end_subrange_1a 1870 aerosol_number(ib)%conc(k,j,i) = pndist(k,ib) * flag 1727 1871 IF ( prunmode == 1 ) THEN 1728 aerosol_number( b)%init = pndist(:,b)1872 aerosol_number(ib)%init = pndist(:,ib) 1729 1873 ENDIF 1730 1874 ENDDO 1731 ! 1732 !-- 1875 ! 1876 !-- Region 2: 1733 1877 IF ( nreg > 1 ) THEN 1734 DO b = in2a, fn2a 1735 aerosol_number(b)%conc(k,j,i) = MAX( 0.0_wp, pnf2a(k) ) * & 1736 pndist(k,b) * flag 1878 DO ib = start_subrange_2a, end_subrange_2a 1879 aerosol_number(ib)%conc(k,j,i) = MAX( 0.0_wp, pnf2a(k) ) * pndist(k,ib) * flag 1737 1880 IF ( prunmode == 1 ) THEN 1738 aerosol_number( b)%init = MAX( 0.0_wp, nf2a ) * pndist(:,b)1881 aerosol_number(ib)%init = MAX( 0.0_wp, nf2a ) * pndist(:,ib) 1739 1882 ENDIF 1740 1883 ENDDO 1741 1884 IF ( .NOT. no_insoluble ) THEN 1742 DO b = in2b, fn2b1743 IF ( pnf2a(k) < 1.0_wp ) THEN 1744 aerosol_number( b)%conc(k,j,i) = MAX( 0.0_wp, 1.0_wp&1745 - pnf2a(k) ) * pndist(k,b) * flag1885 DO ib = start_subrange_2b, end_subrange_2b 1886 IF ( pnf2a(k) < 1.0_wp ) THEN 1887 aerosol_number(ib)%conc(k,j,i) = MAX( 0.0_wp, 1.0_wp - pnf2a(k) ) * & 1888 pndist(k,ib) * flag 1746 1889 IF ( prunmode == 1 ) THEN 1747 aerosol_number(b)%init = MAX( 0.0_wp, 1.0_wp - & 1748 nf2a ) * pndist(:,b) 1890 aerosol_number(ib)%init = MAX( 0.0_wp, 1.0_wp - nf2a ) * pndist(:,ib) 1749 1891 ENDIF 1750 1892 ENDIF … … 1755 1897 !-- b) Aerosol mass concentrations 1756 1898 !-- bin subrange 1: done here separately due to the SO4/OC convention 1899 ! 1757 1900 !-- SO4: 1758 IF ( iso4 > 0 ) THEN 1759 ss = ( iso4 - 1 ) * nbins + in1a !< start 1760 ee = ( iso4 - 1 ) * nbins + fn1a !< end 1761 b = in1a 1762 DO c = ss, ee 1763 aerosol_mass(c)%conc(k,j,i) = MAX( 0.0_wp, 1.0_wp - & 1764 pvfOC1a(k) ) * pndist(k,b) * & 1765 core(b) * arhoh2so4 * flag 1901 IF ( index_so4 > 0 ) THEN 1902 ss = ( index_so4 - 1 ) * nbins_aerosol + start_subrange_1a !< start 1903 ee = ( index_so4 - 1 ) * nbins_aerosol + end_subrange_1a !< end 1904 ib = start_subrange_1a 1905 DO ic = ss, ee 1906 aerosol_mass(ic)%conc(k,j,i) = MAX( 0.0_wp, 1.0_wp - pmfoc1a(k) ) * pndist(k,ib)& 1907 * core(ib) * arhoh2so4 * flag 1766 1908 IF ( prunmode == 1 ) THEN 1767 aerosol_mass(c)%init = MAX( 0.0_wp, 1.0_wp - MAXVAL( & 1768 pvfOC1a ) ) * pndist(:,b) * & 1769 core(b) * arhoh2so4 1909 aerosol_mass(ic)%init(k) = MAX( 0.0_wp, 1.0_wp - pmfoc1a(k) ) * pndist(k,ib) & 1910 * core(ib) * arhoh2so4 1770 1911 ENDIF 1771 b =b+11912 ib = ib+1 1772 1913 ENDDO 1773 1914 ENDIF 1915 ! 1774 1916 !-- OC: 1775 IF ( i oc > 0 ) THEN1776 ss = ( i oc - 1 ) * nbins + in1a !< start1777 ee = ( i oc - 1 ) * nbins + fn1a !< end1778 b = in1a1779 DO c = ss, ee1780 aerosol_mass( c)%conc(k,j,i) = MAX( 0.0_wp, pvfOC1a(k) ) *&1781 pndist(k,b) * core(b) * arhooc * flag1917 IF ( index_oc > 0 ) THEN 1918 ss = ( index_oc - 1 ) * nbins_aerosol + start_subrange_1a !< start 1919 ee = ( index_oc - 1 ) * nbins_aerosol + end_subrange_1a !< end 1920 ib = start_subrange_1a 1921 DO ic = ss, ee 1922 aerosol_mass(ic)%conc(k,j,i) = MAX( 0.0_wp, pmfoc1a(k) ) * pndist(k,ib) * & 1923 core(ib) * arhooc * flag 1782 1924 IF ( prunmode == 1 ) THEN 1783 aerosol_mass( c)%init = MAX( 0.0_wp, MAXVAL( pvfOC1a ) )&1784 * pndist(:,b) * core(b) * arhooc1925 aerosol_mass(ic)%init(k) = MAX( 0.0_wp, pmfoc1a(k) ) * pndist(k,ib) * & 1926 core(ib) * arhooc 1785 1927 ENDIF 1786 b =b+11928 ib = ib+1 1787 1929 ENDDO 1788 1930 ENDIF 1789 1790 prunmode = 3 ! Init only once1791 1792 1931 ENDDO !< k 1932 1933 prunmode = 3 ! Init only once 1934 1793 1935 ENDDO !< j 1794 1936 ENDDO !< i 1795 1937 1796 1938 ! 1797 1939 !-- c) Aerosol mass concentrations 1798 1940 !-- bin subrange 2: 1799 1941 IF ( nreg > 1 ) THEN 1800 1801 IF ( iso4 > 0 ) THEN 1802 CALL set_aero_mass( iso4, pvf2a(:,1), pvf2b(:,1), pnf2a, pndist, & 1803 core, arhoh2so4 ) 1804 ENDIF 1805 IF ( ioc > 0 ) THEN 1806 CALL set_aero_mass( ioc, pvf2a(:,2), pvf2b(:,2), pnf2a, pndist, core,& 1807 arhooc ) 1808 ENDIF 1809 IF ( ibc > 0 ) THEN 1810 CALL set_aero_mass( ibc, pvf2a(:,3), pvf2b(:,3), pnf2a, pndist, core,& 1811 arhobc ) 1812 ENDIF 1813 IF ( idu > 0 ) THEN 1814 CALL set_aero_mass( idu, pvf2a(:,4), pvf2b(:,4), pnf2a, pndist, core,& 1815 arhodu ) 1816 ENDIF 1817 IF ( iss > 0 ) THEN 1818 CALL set_aero_mass( iss, pvf2a(:,5), pvf2b(:,5), pnf2a, pndist, core,& 1819 arhoss ) 1820 ENDIF 1821 IF ( ino > 0 ) THEN 1822 CALL set_aero_mass( ino, pvf2a(:,6), pvf2b(:,6), pnf2a, pndist, core,& 1823 arhohno3 ) 1824 ENDIF 1825 IF ( inh > 0 ) THEN 1826 CALL set_aero_mass( inh, pvf2a(:,7), pvf2b(:,7), pnf2a, pndist, core,& 1827 arhonh3 ) 1942 1943 IF ( index_so4 > 0 ) THEN 1944 CALL set_aero_mass( index_so4, pmf2a(:,1), pmf2b(:,1), pnf2a, pndist, core, arhoh2so4 ) 1945 ENDIF 1946 IF ( index_oc > 0 ) THEN 1947 CALL set_aero_mass( index_oc, pmf2a(:,2), pmf2b(:,2), pnf2a, pndist, core, arhooc ) 1948 ENDIF 1949 IF ( index_bc > 0 ) THEN 1950 CALL set_aero_mass( index_bc, pmf2a(:,3), pmf2b(:,3), pnf2a, pndist, core, arhobc ) 1951 ENDIF 1952 IF ( index_du > 0 ) THEN 1953 CALL set_aero_mass( index_du, pmf2a(:,4), pmf2b(:,4), pnf2a, pndist, core, arhodu ) 1954 ENDIF 1955 IF ( index_ss > 0 ) THEN 1956 CALL set_aero_mass( index_ss, pmf2a(:,5), pmf2b(:,5), pnf2a, pndist, core, arhoss ) 1957 ENDIF 1958 IF ( index_no > 0 ) THEN 1959 CALL set_aero_mass( index_no, pmf2a(:,6), pmf2b(:,6), pnf2a, pndist, core, arhohno3 ) 1960 ENDIF 1961 IF ( index_nh > 0 ) THEN 1962 CALL set_aero_mass( index_nh, pmf2a(:,7), pmf2b(:,7), pnf2a, pndist, core, arhonh3 ) 1828 1963 ENDIF 1829 1964 1830 1965 ENDIF 1831 1966 1832 1967 END SUBROUTINE aerosol_init 1833 1968 1834 1969 !------------------------------------------------------------------------------! 1835 1970 ! Description: … … 1839 1974 !------------------------------------------------------------------------------! 1840 1975 SUBROUTINE size_distribution( in_ntot, in_dpg, in_sigma, psd_sect ) 1841 1976 1842 1977 IMPLICIT NONE 1843 1844 !-- Log-normal size distribution: modes 1845 REAL(wp), DIMENSION(:), INTENT(in) :: in_dpg !< geometric mean diameter 1846 !< (micrometres) 1847 REAL(wp), DIMENSION(:), INTENT(in) :: in_ntot !< number conc. (#/cm3) 1978 1979 INTEGER(iwp) :: ib !< running index: bin 1980 INTEGER(iwp) :: iteration !< running index: iteration 1981 1982 REAL(wp) :: d1 !< particle diameter (m, dummy) 1983 REAL(wp) :: d2 !< particle diameter (m, dummy) 1984 REAL(wp) :: delta_d !< (d2-d1)/10 1985 REAL(wp) :: deltadp !< bin width 1986 REAL(wp) :: dmidi !< ( d1 + d2 ) / 2 1987 1988 REAL(wp), DIMENSION(:), INTENT(in) :: in_dpg !< geometric mean diameter (m) 1989 REAL(wp), DIMENSION(:), INTENT(in) :: in_ntot !< number conc. (#/m3) 1848 1990 REAL(wp), DIMENSION(:), INTENT(in) :: in_sigma !< standard deviation 1849 REAL(wp), DIMENSION(:), INTENT(inout) :: psd_sect !< sectional size 1850 !< distribution 1851 INTEGER(iwp) :: b !< running index: bin 1852 INTEGER(iwp) :: ib !< running index: iteration 1853 REAL(wp) :: d1 !< particle diameter (m, dummy) 1854 REAL(wp) :: d2 !< particle diameter (m, dummy) 1855 REAL(wp) :: delta_d !< (d2-d1)/10 1856 REAL(wp) :: deltadp !< bin width 1857 REAL(wp) :: dmidi !< ( d1 + d2 ) / 2 1858 1859 DO b = in1a, fn2b !< aerosol size bins 1860 psd_sect(b) = 0.0_wp 1991 1992 REAL(wp), DIMENSION(:), INTENT(inout) :: psd_sect !< sectional size distribution 1993 1994 DO ib = start_subrange_1a, end_subrange_2b 1995 psd_sect(ib) = 0.0_wp 1996 ! 1861 1997 !-- Particle diameter at the low limit (largest in the bin) (m) 1862 d1 = ( aero(b)%vlolim / api6 ) ** ( 1.0_wp / 3.0_wp ) 1998 d1 = ( aero(ib)%vlolim / api6 )**0.33333333_wp 1999 ! 1863 2000 !-- Particle diameter at the high limit (smallest in the bin) (m) 1864 d2 = ( aero(b)%vhilim / api6 ) ** ( 1.0_wp / 3.0_wp ) 2001 d2 = ( aero(ib)%vhilim / api6 )**0.33333333_wp 2002 ! 1865 2003 !-- Span of particle diameter in a bin (m) 1866 delta_d = ( d2 - d1 ) / 10.0_wp1867 ! -- Iterate:1868 DO ib = 1, 10 1869 d1 = ( aero(b)%vlolim / api6 ) ** ( 1.0_wp / 3.0_wp ) + ( ib - 1) &1870 2004 delta_d = 0.1_wp * ( d2 - d1 ) 2005 ! 2006 !-- Iterate: 2007 DO iteration = 1, 10 2008 d1 = ( aero(ib)%vlolim / api6 )**0.33333333_wp + ( ib - 1) * delta_d 1871 2009 d2 = d1 + delta_d 1872 dmidi = ( d1 + d2 ) / 2.0_wp2010 dmidi = 0.5_wp * ( d1 + d2 ) 1873 2011 deltadp = LOG10( d2 / d1 ) 1874 2012 ! 1875 2013 !-- Size distribution 1876 2014 !-- in_ntot = total number, total area, or total volume concentration 1877 2015 !-- in_dpg = geometric-mean number, area, or volume diameter 1878 2016 !-- n(k) = number, area, or volume concentration in a bin 1879 !-- n_lognorm and dpg converted to units of #/m3 and m 1880 psd_sect(b) = psd_sect(b) + SUM( in_ntot * 1.0E+6_wp * deltadp / & 1881 ( SQRT( 2.0_wp * pi ) * LOG10( in_sigma ) ) * & 1882 EXP( -LOG10( dmidi / ( 1.0E-6_wp * in_dpg ) )**2.0_wp / & 1883 ( 2.0_wp * LOG10( in_sigma ) ** 2.0_wp ) ) ) 1884 2017 psd_sect(ib) = psd_sect(ib) + SUM( in_ntot * deltadp / ( SQRT( 2.0_wp * pi ) * & 2018 LOG10( in_sigma ) ) * EXP( -LOG10( dmidi / in_dpg )**2.0_wp / & 2019 ( 2.0_wp * LOG10( in_sigma ) ** 2.0_wp ) ) ) 2020 1885 2021 ENDDO 1886 2022 ENDDO 1887 2023 1888 2024 END SUBROUTINE size_distribution 1889 2025 … … 1895 2031 !> Tomi Raatikainen, FMI, 29.2.2016 1896 2032 !------------------------------------------------------------------------------! 1897 SUBROUTINE set_aero_mass( ispec, p pvf2a, ppvf2b, ppnf2a, ppndist, pcore, prho )1898 2033 SUBROUTINE set_aero_mass( ispec, pmf2a, pmf2b, pnf2a, pndist, pcore, prho ) 2034 1899 2035 IMPLICIT NONE 1900 2036 2037 INTEGER(iwp) :: ee !< index: end 2038 INTEGER(iwp) :: i !< loop index 2039 INTEGER(iwp) :: ib !< loop index 2040 INTEGER(iwp) :: ic !< loop index 2041 INTEGER(iwp) :: j !< loop index 2042 INTEGER(iwp) :: k !< loop index 2043 INTEGER(iwp) :: prunmode !< 1 = initialise 2044 INTEGER(iwp) :: ss !< index: start 2045 1901 2046 INTEGER(iwp), INTENT(in) :: ispec !< Aerosol species index 1902 REAL(wp), INTENT(in) :: pcore(nbins) !< Aerosol bin mid core volume 1903 REAL(wp), INTENT(in) :: ppndist(0:nz+1,nbins) !< Aerosol size distribution 1904 REAL(wp), INTENT(in) :: ppnf2a(0:nz+1) !< Number fraction for 2a 1905 REAL(wp), INTENT(in) :: ppvf2a(0:nz+1) !< Mass distributions for a 1906 REAL(wp), INTENT(in) :: ppvf2b(0:nz+1) !< and b bins 2047 2048 REAL(wp) :: flag !< flag to mask topography grid points 2049 1907 2050 REAL(wp), INTENT(in) :: prho !< Aerosol density 1908 INTEGER(iwp) :: b !< loop index 1909 INTEGER(iwp) :: c !< loop index 1910 INTEGER(iwp) :: ee !< index: end 1911 INTEGER(iwp) :: i !< loop index 1912 INTEGER(iwp) :: j !< loop index 1913 INTEGER(iwp) :: k !< loop index 1914 INTEGER(iwp) :: prunmode !< 1 = initialise 1915 INTEGER(iwp) :: ss !< index: start 1916 REAL(wp) :: flag !< flag to mask topography grid points 1917 2051 2052 REAL(wp), DIMENSION(nbins_aerosol), INTENT(in) :: pcore !< Aerosol bin mid core volume 2053 REAL(wp), DIMENSION(0:nz+1), INTENT(in) :: pnf2a !< Number fraction for 2a 2054 REAL(wp), DIMENSION(0:nz+1), INTENT(in) :: pmf2a !< Mass distributions for a 2055 REAL(wp), DIMENSION(0:nz+1), INTENT(in) :: pmf2b !< and b bins 2056 2057 REAL(wp), DIMENSION(0:nz+1,nbins_aerosol), INTENT(in) :: pndist !< Aerosol size distribution 2058 1918 2059 prunmode = 1 1919 1920 DO i = nxlg, nxrg 2060 2061 DO i = nxlg, nxrg 1921 2062 DO j = nysg, nyng 1922 DO k = nzb, nzt+1 2063 DO k = nzb, nzt+1 1923 2064 ! 1924 2065 !-- Predetermine flag to mask topography 1925 2066 flag = MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(k,j,i), 0 ) ) 1926 ! 2067 ! 1927 2068 !-- Regime 2a: 1928 ss = ( ispec - 1 ) * nbins + in2a1929 ee = ( ispec - 1 ) * nbins + fn2a1930 b = in2a1931 DO c = ss, ee1932 aerosol_mass( c)%conc(k,j,i) = MAX( 0.0_wp, ppvf2a(k) ) *&1933 ppnf2a(k) * ppndist(k,b) * pcore(b) * prho * flag2069 ss = ( ispec - 1 ) * nbins_aerosol + start_subrange_2a 2070 ee = ( ispec - 1 ) * nbins_aerosol + end_subrange_2a 2071 ib = start_subrange_2a 2072 DO ic = ss, ee 2073 aerosol_mass(ic)%conc(k,j,i) = MAX( 0.0_wp, pmf2a(k) ) * pnf2a(k) * pndist(k,ib) * & 2074 pcore(ib) * prho * flag 1934 2075 IF ( prunmode == 1 ) THEN 1935 aerosol_mass(c)%init = MAX( 0.0_wp, MAXVAL( ppvf2a(:) ) ) * & 1936 MAXVAL( ppnf2a ) * pcore(b) * prho * & 1937 MAXVAL( ppndist(:,b) ) 2076 aerosol_mass(ic)%init(k) = MAX( 0.0_wp, pmf2a(k) ) * pnf2a(k) * pndist(k,ib) * & 2077 pcore(ib) * prho 1938 2078 ENDIF 1939 b = b+12079 ib = ib + 1 1940 2080 ENDDO 2081 ! 1941 2082 !-- Regime 2b: 1942 2083 IF ( .NOT. no_insoluble ) THEN 1943 ss = ( ispec - 1 ) * nbins + in2b 1944 ee = ( ispec - 1 ) * nbins + fn2b 1945 b = in2a 1946 DO c = ss, ee 1947 aerosol_mass(c)%conc(k,j,i) = MAX( 0.0_wp, ppvf2b(k) ) * ( & 1948 1.0_wp - ppnf2a(k) ) * ppndist(k,b) * & 1949 pcore(b) * prho * flag 2084 ss = ( ispec - 1 ) * nbins_aerosol + start_subrange_2b 2085 ee = ( ispec - 1 ) * nbins_aerosol + end_subrange_2b 2086 ib = start_subrange_2a 2087 DO ic = ss, ee 2088 aerosol_mass(ic)%conc(k,j,i) = MAX( 0.0_wp, pmf2b(k) ) * ( 1.0_wp - pnf2a(k) ) *& 2089 pndist(k,ib) * pcore(ib) * prho * flag 1950 2090 IF ( prunmode == 1 ) THEN 1951 aerosol_mass(c)%init = MAX( 0.0_wp, MAXVAL( ppvf2b(:) ) )& 1952 * ( 1.0_wp - MAXVAL( ppnf2a ) ) * & 1953 MAXVAL( ppndist(:,b) ) * pcore(b) * prho 2091 aerosol_mass(ic)%init(k) = MAX( 0.0_wp, pmf2b(k) ) * ( 1.0_wp - pnf2a(k) ) * & 2092 pndist(k,ib) * pcore(ib) * prho 1954 2093 ENDIF 1955 b = b+1 1956 ENDDO 2094 ib = ib + 1 2095 ENDDO ! c 2096 1957 2097 ENDIF 1958 prunmode = 3 ! Init only once 1959 ENDDO 2098 ENDDO ! k 2099 2100 prunmode = 3 ! Init only once 2101 2102 ENDDO ! j 2103 ENDDO ! i 2104 2105 END SUBROUTINE set_aero_mass 2106 2107 !------------------------------------------------------------------------------! 2108 ! Description: 2109 ! ------------ 2110 !> Initialise the matching between surface types in LSM and deposition models. 2111 !> Do the matching based on Zhang et al. (2001). Atmos. Environ. 35, 549-560 2112 !> (here referred as Z01). 2113 !------------------------------------------------------------------------------! 2114 SUBROUTINE init_deposition 2115 2116 USE surface_mod, & 2117 ONLY: surf_lsm_h, surf_lsm_v 2118 2119 IMPLICIT NONE 2120 2121 INTEGER(iwp) :: l !< loop index for vertical surfaces 2122 2123 IF ( nldepo_surf .AND. land_surface ) THEN 2124 2125 ALLOCATE( lsm_to_depo_h%match(1:surf_lsm_h%ns) ) 2126 lsm_to_depo_h%match = 0 2127 CALL match_lsm_zhang( surf_lsm_h, lsm_to_depo_h%match ) 2128 2129 DO l = 0, 3 2130 ALLOCATE( lsm_to_depo_v(l)%match(1:surf_lsm_v(l)%ns) ) 2131 lsm_to_depo_v(l)%match = 0 2132 CALL match_lsm_zhang( surf_lsm_v(l), lsm_to_depo_v(l)%match ) 1960 2133 ENDDO 2134 ENDIF 2135 2136 IF ( nldepo_pcm ) THEN 2137 SELECT CASE ( depo_pcm_type ) 2138 CASE ( 'evergreen_needleleaf' ) 2139 depo_pcm_type_num = 1 2140 CASE ( 'evergreen_broadleaf' ) 2141 depo_pcm_type_num = 2 2142 CASE ( 'deciduous_needleleaf' ) 2143 depo_pcm_type_num = 3 2144 CASE ( 'deciduous_broadleaf' ) 2145 depo_pcm_type_num = 4 2146 CASE DEFAULT 2147 message_string = 'depo_pcm_type not set correctly.' 2148 CALL message( 'salsa_mod: init_deposition', 'PA0613', 1, 2, 0, 6, 0 ) 2149 END SELECT 2150 ENDIF 2151 2152 END SUBROUTINE init_deposition 2153 2154 !------------------------------------------------------------------------------! 2155 ! Description: 2156 ! ------------ 2157 !> Match the surface types in PALM and Zhang et al. 2001 deposition module 2158 !------------------------------------------------------------------------------! 2159 SUBROUTINE match_lsm_zhang( surf, match_array ) 2160 2161 USE surface_mod, & 2162 ONLY: ind_pav_green, ind_veg_wall, ind_wat_win, surf_type 2163 2164 IMPLICIT NONE 2165 2166 INTEGER(iwp) :: m !< index for surface elements 2167 INTEGER(iwp) :: pav_type_palm !< pavement type in PALM 2168 INTEGER(iwp) :: vege_type_palm !< vegetation type in PALM 2169 INTEGER(iwp) :: water_type_palm !< water type in PALM 2170 2171 INTEGER(iwp), DIMENSION(:), INTENT(inout) :: match_array !< array matching 2172 !< the surface types 2173 TYPE(surf_type), INTENT(in) :: surf !< respective surface type 2174 2175 DO m = 1, surf%ns 2176 2177 IF ( surf%frac(ind_veg_wall,m) > 0 ) THEN 2178 vege_type_palm = surf%vegetation_type(m) 2179 SELECT CASE ( vege_type_palm ) 2180 CASE ( 0 ) 2181 message_string = 'No vegetation type defined.' 2182 CALL message( 'salsa_mod: init_depo_surfaces', 'PA0614', 1, 2, 0, 6, 0 ) 2183 CASE ( 1 ) ! bare soil 2184 match_array(m) = 6 ! grass in Z01 2185 CASE ( 2 ) ! crops, mixed farming 2186 match_array(m) = 7 ! crops, mixed farming Z01 2187 CASE ( 3 ) ! short grass 2188 match_array(m) = 6 ! grass in Z01 2189 CASE ( 4 ) ! evergreen needleleaf trees 2190 match_array(m) = 1 ! evergreen needleleaf trees in Z01 2191 CASE ( 5 ) ! deciduous needleleaf trees 2192 match_array(m) = 3 ! deciduous needleleaf trees in Z01 2193 CASE ( 6 ) ! evergreen broadleaf trees 2194 match_array(m) = 2 ! evergreen broadleaf trees in Z01 2195 CASE ( 7 ) ! deciduous broadleaf trees 2196 match_array(m) = 4 ! deciduous broadleaf trees in Z01 2197 CASE ( 8 ) ! tall grass 2198 match_array(m) = 6 ! grass in Z01 2199 CASE ( 9 ) ! desert 2200 match_array(m) = 8 ! desert in Z01 2201 CASE ( 10 ) ! tundra 2202 match_array(m) = 9 ! tundra in Z01 2203 CASE ( 11 ) ! irrigated crops 2204 match_array(m) = 7 ! crops, mixed farming Z01 2205 CASE ( 12 ) ! semidesert 2206 match_array(m) = 8 ! desert in Z01 2207 CASE ( 13 ) ! ice caps and glaciers 2208 match_array(m) = 12 ! ice cap and glacier in Z01 2209 CASE ( 14 ) ! bogs and marshes 2210 match_array(m) = 11 ! wetland with plants in Z01 2211 CASE ( 15 ) ! evergreen shrubs 2212 match_array(m) = 10 ! shrubs and interrupted woodlands in Z01 2213 CASE ( 16 ) ! deciduous shrubs 2214 match_array(m) = 10 ! shrubs and interrupted woodlands in Z01 2215 CASE ( 17 ) ! mixed forest/woodland 2216 match_array(m) = 5 ! mixed broadleaf and needleleaf trees in Z01 2217 CASE ( 18 ) ! interrupted forest 2218 match_array(m) = 10 ! shrubs and interrupted woodlands in Z01 2219 END SELECT 2220 ENDIF 2221 2222 IF ( surf%frac(ind_pav_green,m) > 0 ) THEN 2223 pav_type_palm = surf%pavement_type(m) 2224 IF ( pav_type_palm == 0 ) THEN ! error 2225 message_string = 'No pavement type defined.' 2226 CALL message( 'salsa_mod: match_lsm_zhang', 'PA0615', 1, 2, 0, 6, 0 ) 2227 ELSEIF ( pav_type_palm > 0 .AND. pav_type_palm <= 15 ) THEN 2228 match_array(m) = 15 ! urban in Z01 2229 ENDIF 2230 ENDIF 2231 2232 IF ( surf%frac(ind_wat_win,m) > 0 ) THEN 2233 water_type_palm = surf%water_type(m) 2234 IF ( water_type_palm == 0 ) THEN ! error 2235 message_string = 'No water type defined.' 2236 CALL message( 'salsa_mod: match_lsm_zhang', 'PA0616', 1, 2, 0, 6, 0 ) 2237 ELSEIF ( water_type_palm == 3 ) THEN 2238 match_array(m) = 14 ! ocean in Z01 2239 ELSEIF ( water_type_palm == 1 .OR. water_type_palm == 2 .OR. water_type_palm == 4 & 2240 .OR. water_type_palm == 5 ) THEN 2241 match_array(m) = 13 ! inland water in Z01 2242 ENDIF 2243 ENDIF 2244 1961 2245 ENDDO 1962 END SUBROUTINE set_aero_mass 2246 2247 END SUBROUTINE match_lsm_zhang 1963 2248 1964 2249 !------------------------------------------------------------------------------! … … 1971 2256 IMPLICIT NONE 1972 2257 2258 INTEGER(iwp) :: ib !< 2259 INTEGER(iwp) :: ic !< 2260 INTEGER(iwp) :: icc !< 2261 INTEGER(iwp) :: ig !< 2262 1973 2263 INTEGER(iwp), INTENT(IN) :: mod_count !< 1974 INTEGER(iwp) :: b !< 1975 INTEGER(iwp) :: c !< 1976 INTEGER(iwp) :: cc !< 1977 INTEGER(iwp) :: g !< 1978 1979 IF ( simulated_time >= time_since_reference_point ) THEN 1980 1981 SELECT CASE ( mod_count ) 1982 1983 CASE ( 0 ) 1984 1985 DO b = 1, nbins 1986 aerosol_number(b)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => & 1987 nconc_1(:,:,:,b) 1988 aerosol_number(b)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => & 1989 nconc_2(:,:,:,b) 1990 DO c = 1, ncc_tot 1991 cc = ( c-1 ) * nbins + b ! required due to possible Intel18 bug 1992 aerosol_mass(cc)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => & 1993 mconc_1(:,:,:,cc) 1994 aerosol_mass(cc)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => & 1995 mconc_2(:,:,:,cc) 2264 2265 IF ( time_since_reference_point >= skip_time_do_salsa ) THEN 2266 2267 SELECT CASE ( mod_count ) 2268 2269 CASE ( 0 ) 2270 2271 DO ib = 1, nbins_aerosol 2272 aerosol_number(ib)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => nconc_1(:,:,:,ib) 2273 aerosol_number(ib)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => nconc_2(:,:,:,ib) 2274 2275 DO ic = 1, ncomponents_mass 2276 icc = ( ic-1 ) * nbins_aerosol + ib 2277 aerosol_mass(icc)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => mconc_1(:,:,:,icc) 2278 aerosol_mass(icc)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => mconc_2(:,:,:,icc) 2279 ENDDO 1996 2280 ENDDO 1997 ENDDO 1998 1999 IF ( .NOT. salsa_gases_from_chem ) THEN 2000 DO g = 1, ngast 2001 salsa_gas(g)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => & 2002 gconc_1(:,:,:,g) 2003 salsa_gas(g)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => & 2004 gconc_2(:,:,:,g) 2281 2282 IF ( .NOT. salsa_gases_from_chem ) THEN 2283 DO ig = 1, ngases_salsa 2284 salsa_gas(ig)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => gconc_1(:,:,:,ig) 2285 salsa_gas(ig)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => gconc_2(:,:,:,ig) 2286 ENDDO 2287 ENDIF 2288 2289 CASE ( 1 ) 2290 2291 DO ib = 1, nbins_aerosol 2292 aerosol_number(ib)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => nconc_2(:,:,:,ib) 2293 aerosol_number(ib)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => nconc_1(:,:,:,ib) 2294 DO ic = 1, ncomponents_mass 2295 icc = ( ic-1 ) * nbins_aerosol + ib 2296 aerosol_mass(icc)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => mconc_2(:,:,:,icc) 2297 aerosol_mass(icc)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => mconc_1(:,:,:,icc) 2298 ENDDO 2005 2299 ENDDO 2006 ENDIF 2007 2008 CASE ( 1 ) 2009 2010 DO b = 1, nbins 2011 aerosol_number(b)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => & 2012 nconc_2(:,:,:,b) 2013 aerosol_number(b)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => & 2014 nconc_1(:,:,:,b) 2015 DO c = 1, ncc_tot 2016 cc = ( c-1 ) * nbins + b ! required due to possible Intel18 bug 2017 aerosol_mass(cc)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => & 2018 mconc_2(:,:,:,cc) 2019 aerosol_mass(cc)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => & 2020 mconc_1(:,:,:,cc) 2021 ENDDO 2022 ENDDO 2023 2024 IF ( .NOT. salsa_gases_from_chem ) THEN 2025 DO g = 1, ngast 2026 salsa_gas(g)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => & 2027 gconc_2(:,:,:,g) 2028 salsa_gas(g)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => & 2029 gconc_1(:,:,:,g) 2030 ENDDO 2031 ENDIF 2032 2033 END SELECT 2300 2301 IF ( .NOT. salsa_gases_from_chem ) THEN 2302 DO ig = 1, ngases_salsa 2303 salsa_gas(ig)%conc(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => gconc_2(:,:,:,ig) 2304 salsa_gas(ig)%conc_p(nzb:nzt+1,nysg:nyng,nxlg:nxrg) => gconc_1(:,:,:,ig) 2305 ENDDO 2306 ENDIF 2307 2308 END SELECT 2034 2309 2035 2310 ENDIF … … 2043 2318 !> This routine reads the respective restart data. 2044 2319 !------------------------------------------------------------------------------! 2045 SUBROUTINE salsa_rrd_local( k, nxlf, nxlc, nxl_on_file, nxrf, nxrc, & 2046 nxr_on_file, nynf, nync, nyn_on_file, nysf, & 2047 nysc, nys_on_file, tmp_3d, found ) 2048 2049 2320 SUBROUTINE salsa_rrd_local( k, nxlf, nxlc, nxl_on_file, nxrf, nxrc, nxr_on_file, nynf, nync, & 2321 nyn_on_file, nysf, nysc, nys_on_file, tmp_3d, found ) 2322 2050 2323 IMPLICIT NONE 2051 2052 INTEGER(iwp) :: b !<2053 INTEGER(iwp) :: c!<2054 INTEGER(iwp) :: g!<2055 INTEGER(iwp) :: k !<2324 2325 INTEGER(iwp) :: ib !< 2326 INTEGER(iwp) :: ic !< 2327 INTEGER(iwp) :: ig !< 2328 INTEGER(iwp) :: k !< 2056 2329 INTEGER(iwp) :: nxlc !< 2057 2330 INTEGER(iwp) :: nxlf !< … … 2067 2340 INTEGER(iwp) :: nys_on_file !< 2068 2341 2069 LOGICAL, INTENT(OUT) :: found 2342 LOGICAL, INTENT(OUT) :: found !< 2070 2343 2071 2344 REAL(wp), & 2072 2345 DIMENSION(nzb:nzt+1,nys_on_file-nbgp:nyn_on_file+nbgp,nxl_on_file-nbgp:nxr_on_file+nbgp) :: tmp_3d !< 2073 2346 2074 2347 found = .FALSE. 2075 2348 2076 2349 IF ( read_restart_data_salsa ) THEN 2077 2350 2078 2351 SELECT CASE ( restart_string(1:length) ) 2079 2352 2080 2353 CASE ( 'aerosol_number' ) 2081 DO b = 1, nbins2354 DO ib = 1, nbins_aerosol 2082 2355 IF ( k == 1 ) READ ( 13 ) tmp_3d 2083 aerosol_number( b)%conc(:,nysc-nbgp:nync+nbgp,nxlc-nbgp:nxrc+nbgp) = &2084 tmp_3d(:,nysf-nbgp:nynf+nbgp,nxlf-nbgp:nxrf+nbgp)2356 aerosol_number(ib)%conc(:,nysc-nbgp:nync+nbgp,nxlc-nbgp:nxrc+nbgp) = & 2357 tmp_3d(:,nysf-nbgp:nynf+nbgp,nxlf-nbgp:nxrf+nbgp) 2085 2358 found = .TRUE. 2086 2359 ENDDO 2087 2360 2088 2361 CASE ( 'aerosol_mass' ) 2089 DO c = 1, ncc_tot * nbins2362 DO ic = 1, ncomponents_mass * nbins_aerosol 2090 2363 IF ( k == 1 ) READ ( 13 ) tmp_3d 2091 aerosol_mass( c)%conc(:,nysc-nbgp:nync+nbgp,nxlc-nbgp:nxrc+nbgp) = &2092 tmp_3d(:,nysf-nbgp:nynf+nbgp,nxlf-nbgp:nxrf+nbgp)2364 aerosol_mass(ic)%conc(:,nysc-nbgp:nync+nbgp,nxlc-nbgp:nxrc+nbgp) = & 2365 tmp_3d(:,nysf-nbgp:nynf+nbgp,nxlf-nbgp:nxrf+nbgp) 2093 2366 found = .TRUE. 2094 2367 ENDDO 2095 2368 2096 2369 CASE ( 'salsa_gas' ) 2097 DO g = 1, ngast2370 DO ig = 1, ngases_salsa 2098 2371 IF ( k == 1 ) READ ( 13 ) tmp_3d 2099 salsa_gas( g)%conc(:,nysc-nbgp:nync+nbgp,nxlc-nbgp:nxrc+nbgp) = &2100 tmp_3d(:,nysf-nbgp:nynf+nbgp,nxlf-nbgp:nxrf+nbgp)2372 salsa_gas(ig)%conc(:,nysc-nbgp:nync+nbgp,nxlc-nbgp:nxrc+nbgp) = & 2373 tmp_3d(:,nysf-nbgp:nynf+nbgp,nxlf-nbgp:nxrf+nbgp) 2101 2374 found = .TRUE. 2102 2375 ENDDO 2103 2376 2104 2377 CASE DEFAULT 2105 2378 found = .FALSE. 2106 2379 2107 2380 END SELECT 2108 2381 ENDIF 2109 2382 2110 2383 END SUBROUTINE salsa_rrd_local 2111 2112 2384 2113 2385 !------------------------------------------------------------------------------! … … 2122 2394 2123 2395 IMPLICIT NONE 2124 2125 INTEGER(iwp) :: b !<2126 INTEGER(iwp) :: c!<2127 INTEGER(iwp) :: g !<2128 2396 2397 INTEGER(iwp) :: ib !< 2398 INTEGER(iwp) :: ic !< 2399 INTEGER(iwp) :: ig !< 2400 2129 2401 IF ( write_binary .AND. write_binary_salsa ) THEN 2130 2402 2131 2403 CALL wrd_write_string( 'aerosol_number' ) 2132 DO b = 1, nbins2133 WRITE ( 14 ) aerosol_number( b)%conc2404 DO ib = 1, nbins_aerosol 2405 WRITE ( 14 ) aerosol_number(ib)%conc 2134 2406 ENDDO 2135 2407 2136 2408 CALL wrd_write_string( 'aerosol_mass' ) 2137 DO c = 1, nbins*ncc_tot2138 WRITE ( 14 ) aerosol_mass( c)%conc2409 DO ic = 1, nbins_aerosol * ncomponents_mass 2410 WRITE ( 14 ) aerosol_mass(ic)%conc 2139 2411 ENDDO 2140 2412 2141 2413 CALL wrd_write_string( 'salsa_gas' ) 2142 DO g = 1, ngast2143 WRITE ( 14 ) salsa_gas( g)%conc2414 DO ig = 1, ngases_salsa 2415 WRITE ( 14 ) salsa_gas(ig)%conc 2144 2416 ENDDO 2145 2417 2146 2418 ENDIF 2147 2148 END SUBROUTINE salsa_wrd_local 2149 2419 2420 END SUBROUTINE salsa_wrd_local 2150 2421 2151 2422 !------------------------------------------------------------------------------! … … 2165 2436 SUBROUTINE salsa_driver( i, j, prunmode ) 2166 2437 2167 USE arrays_3d, &2168 ONLY: pt_p, q_p, rho_air_zw,u, v, w2169 2170 USE plant_canopy_model_mod, &2438 USE arrays_3d, & 2439 ONLY: pt_p, q_p, u, v, w 2440 2441 USE plant_canopy_model_mod, & 2171 2442 ONLY: lad_s 2172 2173 USE surface_mod, & 2174 ONLY: surf_def_h, surf_def_v, surf_lsm_h, surf_lsm_v, surf_usm_h, & 2175 surf_usm_v 2176 2443 2444 USE surface_mod, & 2445 ONLY: surf_def_h, surf_def_v, surf_lsm_h, surf_lsm_v, surf_usm_h, surf_usm_v 2446 2177 2447 IMPLICIT NONE 2178 2179 INTEGER(iwp), INTENT(in) :: i !< loop index 2180 INTEGER(iwp), INTENT(in) :: j !< loop index 2181 INTEGER(iwp), INTENT(in) :: prunmode !< 1: Initialization call 2182 !< 2: Spinup period call 2183 !< 3: Regular runtime call 2184 !-- Local variables 2185 TYPE(t_section), DIMENSION(fn2b) :: aero_old !< helper array 2186 INTEGER(iwp) :: bb !< loop index 2187 INTEGER(iwp) :: cc !< loop index 2188 INTEGER(iwp) :: endi !< end index 2189 INTEGER(iwp) :: k_wall !< vertical index of topography top 2190 INTEGER(iwp) :: k !< loop index 2191 INTEGER(iwp) :: l !< loop index 2192 INTEGER(iwp) :: nc_h2o !< index of H2O in the prtcl index table 2193 INTEGER(iwp) :: ss !< loop index 2194 INTEGER(iwp) :: str !< start index 2195 INTEGER(iwp) :: vc !< default index in prtcl 2196 REAL(wp) :: cw_old !< previous H2O mixing ratio 2197 REAL(wp) :: flag !< flag to mask topography grid points 2198 REAL(wp), DIMENSION(nzb:nzt+1) :: in_adn !< air density (kg/m3) 2199 REAL(wp), DIMENSION(nzb:nzt+1) :: in_cs !< H2O sat. vapour conc. 2200 REAL(wp), DIMENSION(nzb:nzt+1) :: in_cw !< H2O vapour concentration 2201 REAL(wp) :: in_lad !< leaf area density (m2/m3) 2202 REAL(wp), DIMENSION(nzb:nzt+1) :: in_p !< pressure (Pa) 2203 REAL(wp) :: in_rh !< relative humidity 2204 REAL(wp), DIMENSION(nzb:nzt+1) :: in_t !< temperature (K) 2205 REAL(wp), DIMENSION(nzb:nzt+1) :: in_u !< wind magnitude (m/s) 2206 REAL(wp), DIMENSION(nzb:nzt+1) :: kvis !< kinematic viscosity of air(m2/s) 2207 REAL(wp), DIMENSION(nzb:nzt+1,fn2b) :: Sc !< particle Schmidt number 2208 REAL(wp), DIMENSION(nzb:nzt+1,fn2b) :: vd !< particle fall seed (m/s, 2209 !< sedimentation velocity) 2210 REAL(wp), DIMENSION(nzb:nzt+1) :: ppm_to_nconc !< Conversion factor 2211 !< from ppm to #/m3 2212 REAL(wp) :: zgso4 !< SO4 2213 REAL(wp) :: zghno3 !< HNO3 2214 REAL(wp) :: zgnh3 !< NH3 2215 REAL(wp) :: zgocnv !< non-volatile OC 2216 REAL(wp) :: zgocsv !< semi-volatile OC 2217 2448 2449 INTEGER(iwp) :: endi !< end index 2450 INTEGER(iwp) :: ib !< loop index 2451 INTEGER(iwp) :: ic !< loop index 2452 INTEGER(iwp) :: ig !< loop index 2453 INTEGER(iwp) :: k_wall !< vertical index of topography top 2454 INTEGER(iwp) :: k !< loop index 2455 INTEGER(iwp) :: l !< loop index 2456 INTEGER(iwp) :: nc_h2o !< index of H2O in the prtcl index table 2457 INTEGER(iwp) :: ss !< loop index 2458 INTEGER(iwp) :: str !< start index 2459 INTEGER(iwp) :: vc !< default index in prtcl 2460 2461 INTEGER(iwp), INTENT(in) :: i !< loop index 2462 INTEGER(iwp), INTENT(in) :: j !< loop index 2463 INTEGER(iwp), INTENT(in) :: prunmode !< 1: Initialization, 2: Spinup, 3: Regular runtime 2464 2465 REAL(wp) :: cw_old !< previous H2O mixing ratio 2466 REAL(wp) :: flag !< flag to mask topography grid points 2467 REAL(wp) :: in_lad !< leaf area density (m2/m3) 2468 REAL(wp) :: in_rh !< relative humidity 2469 REAL(wp) :: zgso4 !< SO4 2470 REAL(wp) :: zghno3 !< HNO3 2471 REAL(wp) :: zgnh3 !< NH3 2472 REAL(wp) :: zgocnv !< non-volatile OC 2473 REAL(wp) :: zgocsv !< semi-volatile OC 2474 2475 REAL(wp), DIMENSION(nzb:nzt+1) :: in_adn !< air density (kg/m3) 2476 REAL(wp), DIMENSION(nzb:nzt+1) :: in_cs !< H2O sat. vapour conc. 2477 REAL(wp), DIMENSION(nzb:nzt+1) :: in_cw !< H2O vapour concentration 2478 REAL(wp), DIMENSION(nzb:nzt+1) :: in_p !< pressure (Pa) 2479 REAL(wp), DIMENSION(nzb:nzt+1) :: in_t !< temperature (K) 2480 REAL(wp), DIMENSION(nzb:nzt+1) :: in_u !< wind magnitude (m/s) 2481 REAL(wp), DIMENSION(nzb:nzt+1) :: kvis !< kinematic viscosity of air(m2/s) 2482 REAL(wp), DIMENSION(nzb:nzt+1) :: ppm_to_nconc !< Conversion factor from ppm to #/m3 2483 2484 REAL(wp), DIMENSION(nzb:nzt+1,nbins_aerosol) :: schmidt_num !< particle Schmidt number 2485 REAL(wp), DIMENSION(nzb:nzt+1,nbins_aerosol) :: vd !< particle fall seed (m/s) 2486 2487 TYPE(t_section), DIMENSION(nbins_aerosol) :: aero_old !< helper array 2488 2218 2489 aero_old(:)%numc = 0.0_wp 2219 in_adn = 0.0_wp2220 in_cs = 0.0_wp2221 in_cw = 0.0_wp2222 2490 in_lad = 0.0_wp 2223 in_rh = 0.0_wp2224 in_p = 0.0_wp2225 in_t = 0.0_wp2226 2491 in_u = 0.0_wp 2227 2492 kvis = 0.0_wp 2228 Sc= 0.0_wp2493 schmidt_num = 0.0_wp 2229 2494 vd = 0.0_wp 2230 ppm_to_nconc = 1.0_wp2231 2495 zgso4 = nclim 2232 2496 zghno3 = nclim … … 2234 2498 zgocnv = nclim 2235 2499 zgocsv = nclim 2236 2237 ! 2500 ! 2238 2501 !-- Aerosol number is always set, but mass can be uninitialized 2239 DO cc = 1, nbins2240 aero( cc)%volc= 0.0_wp2241 aero_old( cc)%volc= 0.0_wp2242 ENDDO 2243 ! 2502 DO ib = 1, nbins_aerosol 2503 aero(ib)%volc(:) = 0.0_wp 2504 aero_old(ib)%volc(:) = 0.0_wp 2505 ENDDO 2506 ! 2244 2507 !-- Set the salsa runtime config (How to make this more efficient?) 2245 2508 CALL set_salsa_runtime( prunmode ) 2246 ! 2509 ! 2247 2510 !-- Calculate thermodynamic quantities needed in SALSA 2248 CALL salsa_thrm_ij( i, j, p_ij=in_p, temp_ij=in_t, cw_ij=in_cw, & 2249 cs_ij=in_cs, adn_ij=in_adn ) 2511 CALL salsa_thrm_ij( i, j, p_ij=in_p, temp_ij=in_t, cw_ij=in_cw, cs_ij=in_cs, adn_ij=in_adn ) 2250 2512 ! 2251 2513 !-- Magnitude of wind: needed for deposition 2252 2514 IF ( lsdepo ) THEN 2253 in_u(nzb+1:nzt) = SQRT( & 2254 ( 0.5_wp * ( u(nzb+1:nzt,j,i) + u(nzb+1:nzt,j,i+1) ) )**2 + & 2255 ( 0.5_wp * ( v(nzb+1:nzt,j,i) + v(nzb+1:nzt,j+1,i) ) )**2 + & 2256 ( 0.5_wp * ( w(nzb:nzt-1,j,i) + w(nzb+1:nzt,j, i) ) )**2 ) 2515 in_u(nzb+1:nzt) = SQRT( ( 0.5_wp * ( u(nzb+1:nzt,j,i) + u(nzb+1:nzt,j,i+1) ) )**2 + & 2516 ( 0.5_wp * ( v(nzb+1:nzt,j,i) + v(nzb+1:nzt,j+1,i) ) )**2 + & 2517 ( 0.5_wp * ( w(nzb:nzt-1,j,i) + w(nzb+1:nzt,j, i) ) )**2 ) 2257 2518 ENDIF 2258 2519 ! 2259 2520 !-- Calculate conversion factors for gas concentrations 2260 ppm_to_nconc = for_ppm_to_nconc * in_p / in_t2521 ppm_to_nconc(:) = for_ppm_to_nconc * in_p(:) / in_t(:) 2261 2522 ! 2262 2523 !-- Determine topography-top index on scalar grid 2263 k_wall = MAXLOC( MERGE( 1, 0, BTEST( wall_flags_0(:,j,i), 12 ) ), & 2264 DIM = 1 ) - 1 2265 2524 k_wall = k_topo_top(j,i) 2525 2266 2526 DO k = nzb+1, nzt 2267 2527 ! 2268 2528 !-- Predetermine flag to mask topography 2269 2529 flag = MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(k,j,i), 0 ) ) 2270 ! 2271 !-- Do not run inside buildings 2272 IF ( flag == 0.0_wp ) CYCLE 2273 ! 2274 !-- Wind velocity for dry depositon on vegetation 2275 IF ( lsdepo_vege .AND. plant_canopy ) THEN 2276 in_lad = lad_s(k-k_wall,j,i) 2277 ENDIF 2530 ! 2531 !-- Wind velocity for dry depositon on vegetation 2532 IF ( lsdepo_pcm .AND. plant_canopy ) THEN 2533 in_lad = lad_s( MAX( k-k_wall,0 ),j,i) 2534 ENDIF 2278 2535 ! 2279 2536 !-- For initialization and spinup, limit the RH with the parameter rhlim … … 2284 2541 ENDIF 2285 2542 cw_old = in_cw(k) !* in_adn(k) 2286 ! 2543 ! 2287 2544 !-- Set volume concentrations: 2288 2545 !-- Sulphate (SO4) or sulphuric acid H2SO4 2289 IF ( i so4 > 0 ) THEN2546 IF ( index_so4 > 0 ) THEN 2290 2547 vc = 1 2291 str = ( i so4-1 ) * nbins+ 1 ! start index2292 endi = i so4 * nbins! end index2293 cc = 12548 str = ( index_so4-1 ) * nbins_aerosol + 1 ! start index 2549 endi = index_so4 * nbins_aerosol ! end index 2550 ic = 1 2294 2551 DO ss = str, endi 2295 aero( cc)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhoh2so42296 cc = cc+12552 aero(ic)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhoh2so4 2553 ic = ic+1 2297 2554 ENDDO 2298 aero_old(1:nbins )%volc(vc) = aero(1:nbins)%volc(vc)2299 ENDIF 2300 2555 aero_old(1:nbins_aerosol)%volc(vc) = aero(1:nbins_aerosol)%volc(vc) 2556 ENDIF 2557 ! 2301 2558 !-- Organic carbon (OC) compounds 2302 IF ( i oc > 0 ) THEN2559 IF ( index_oc > 0 ) THEN 2303 2560 vc = 2 2304 str = ( i oc-1 ) * nbins+ 12305 endi = i oc * nbins2306 cc = 12561 str = ( index_oc-1 ) * nbins_aerosol + 1 2562 endi = index_oc * nbins_aerosol 2563 ic = 1 2307 2564 DO ss = str, endi 2308 aero( cc)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhooc2309 cc = cc+12565 aero(ic)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhooc 2566 ic = ic+1 2310 2567 ENDDO 2311 aero_old(1:nbins )%volc(vc) = aero(1:nbins)%volc(vc)2312 ENDIF 2313 2568 aero_old(1:nbins_aerosol)%volc(vc) = aero(1:nbins_aerosol)%volc(vc) 2569 ENDIF 2570 ! 2314 2571 !-- Black carbon (BC) 2315 IF ( i bc > 0 ) THEN2572 IF ( index_bc > 0 ) THEN 2316 2573 vc = 3 2317 str = ( i bc-1 ) * nbins + 1 + fn1a2318 endi = i bc * nbins2319 cc = 1 + fn1a2574 str = ( index_bc-1 ) * nbins_aerosol + 1 + end_subrange_1a 2575 endi = index_bc * nbins_aerosol 2576 ic = 1 + end_subrange_1a 2320 2577 DO ss = str, endi 2321 aero( cc)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhobc2322 cc = cc+12323 ENDDO 2324 aero_old(1:nbins )%volc(vc) = aero(1:nbins)%volc(vc)2325 ENDIF 2326 2578 aero(ic)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhobc 2579 ic = ic+1 2580 ENDDO 2581 aero_old(1:nbins_aerosol)%volc(vc) = aero(1:nbins_aerosol)%volc(vc) 2582 ENDIF 2583 ! 2327 2584 !-- Dust (DU) 2328 IF ( i du > 0 ) THEN2585 IF ( index_du > 0 ) THEN 2329 2586 vc = 4 2330 str = ( i du-1 ) * nbins + 1 + fn1a2331 endi = i du * nbins2332 cc = 1 + fn1a2587 str = ( index_du-1 ) * nbins_aerosol + 1 + end_subrange_1a 2588 endi = index_du * nbins_aerosol 2589 ic = 1 + end_subrange_1a 2333 2590 DO ss = str, endi 2334 aero( cc)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhodu2335 cc = cc+12591 aero(ic)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhodu 2592 ic = ic+1 2336 2593 ENDDO 2337 aero_old(1:nbins )%volc(vc) = aero(1:nbins)%volc(vc)2338 ENDIF 2339 2594 aero_old(1:nbins_aerosol)%volc(vc) = aero(1:nbins_aerosol)%volc(vc) 2595 ENDIF 2596 ! 2340 2597 !-- Sea salt (SS) 2341 IF ( i ss > 0 ) THEN2598 IF ( index_ss > 0 ) THEN 2342 2599 vc = 5 2343 str = ( i ss-1 ) * nbins + 1 + fn1a2344 endi = i ss * nbins2345 cc = 1 + fn1a2600 str = ( index_ss-1 ) * nbins_aerosol + 1 + end_subrange_1a 2601 endi = index_ss * nbins_aerosol 2602 ic = 1 + end_subrange_1a 2346 2603 DO ss = str, endi 2347 aero( cc)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhoss2348 cc = cc+12604 aero(ic)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhoss 2605 ic = ic+1 2349 2606 ENDDO 2350 aero_old(1:nbins )%volc(vc) = aero(1:nbins)%volc(vc)2351 ENDIF 2352 2607 aero_old(1:nbins_aerosol)%volc(vc) = aero(1:nbins_aerosol)%volc(vc) 2608 ENDIF 2609 ! 2353 2610 !-- Nitrate (NO(3-)) or nitric acid HNO3 2354 IF ( in o > 0 ) THEN2611 IF ( index_no > 0 ) THEN 2355 2612 vc = 6 2356 str = ( in o-1 ) * nbins+ 12357 endi = in o * nbins2358 cc = 12613 str = ( index_no-1 ) * nbins_aerosol + 1 2614 endi = index_no * nbins_aerosol 2615 ic = 1 2359 2616 DO ss = str, endi 2360 aero( cc)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhohno32361 cc = cc+12617 aero(ic)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhohno3 2618 ic = ic+1 2362 2619 ENDDO 2363 aero_old(1:nbins )%volc(vc) = aero(1:nbins)%volc(vc)2364 ENDIF 2365 2620 aero_old(1:nbins_aerosol)%volc(vc) = aero(1:nbins_aerosol)%volc(vc) 2621 ENDIF 2622 ! 2366 2623 !-- Ammonium (NH(4+)) or ammonia NH3 2367 IF ( in h > 0 ) THEN2624 IF ( index_nh > 0 ) THEN 2368 2625 vc = 7 2369 str = ( in h-1 ) * nbins+ 12370 endi = in h * nbins2371 cc = 12626 str = ( index_nh-1 ) * nbins_aerosol + 1 2627 endi = index_nh * nbins_aerosol 2628 ic = 1 2372 2629 DO ss = str, endi 2373 aero( cc)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhonh32374 cc = cc+12630 aero(ic)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhonh3 2631 ic = ic+1 2375 2632 ENDDO 2376 aero_old(1:nbins )%volc(vc) = aero(1:nbins)%volc(vc)2377 ENDIF 2378 2633 aero_old(1:nbins_aerosol)%volc(vc) = aero(1:nbins_aerosol)%volc(vc) 2634 ENDIF 2635 ! 2379 2636 !-- Water (always used) 2380 2637 nc_h2o = get_index( prtcl,'H2O' ) 2381 2638 vc = 8 2382 str = ( nc_h2o-1 ) * nbins + 12383 endi = nc_h2o * nbins 2384 cc = 12639 str = ( nc_h2o-1 ) * nbins_aerosol + 1 2640 endi = nc_h2o * nbins_aerosol 2641 ic = 1 2385 2642 IF ( advect_particle_water ) THEN 2386 2643 DO ss = str, endi 2387 aero( cc)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhoh2o2388 cc = cc+12644 aero(ic)%volc(vc) = aerosol_mass(ss)%conc(k,j,i) / arhoh2o 2645 ic = ic+1 2389 2646 ENDDO 2390 2647 ELSE 2391 aero(1:nbins )%volc(vc) = mclim2392 ENDIF 2393 aero_old(1:nbins )%volc(vc) = aero(1:nbins)%volc(vc)2648 aero(1:nbins_aerosol)%volc(vc) = mclim 2649 ENDIF 2650 aero_old(1:nbins_aerosol)%volc(vc) = aero(1:nbins_aerosol)%volc(vc) 2394 2651 ! 2395 2652 !-- Number concentrations (numc) and particle sizes 2396 2653 !-- (dwet = wet diameter, core = dry volume) 2397 DO bb = 1, nbins 2398 aero(bb)%numc = aerosol_number(bb)%conc(k,j,i) 2399 aero_old(bb)%numc = aero(bb)%numc 2400 IF ( aero(bb)%numc > nclim ) THEN 2401 aero(bb)%dwet = ( SUM( aero(bb)%volc(:) ) / aero(bb)%numc / api6 )& 2402 **( 1.0_wp / 3.0_wp ) 2403 aero(bb)%core = SUM( aero(bb)%volc(1:7) ) / aero(bb)%numc 2654 DO ib = 1, nbins_aerosol 2655 aero(ib)%numc = aerosol_number(ib)%conc(k,j,i) 2656 aero_old(ib)%numc = aero(ib)%numc 2657 IF ( aero(ib)%numc > nclim ) THEN 2658 aero(ib)%dwet = ( SUM( aero(ib)%volc(:) ) / aero(ib)%numc / api6 )**0.33333333_wp 2659 aero(ib)%core = SUM( aero(ib)%volc(1:7) ) / aero(ib)%numc 2404 2660 ELSE 2405 aero( bb)%dwet = aero(bb)%dmid2406 aero( bb)%core = api6 * ( aero(bb)%dwet ) ** 3.0_wp2661 aero(ib)%dwet = aero(ib)%dmid 2662 aero(ib)%core = api6 * ( aero(ib)%dwet )**3 2407 2663 ENDIF 2408 2664 ENDDO 2409 ! 2665 ! 2410 2666 !-- On EACH call of salsa_driver, calculate the ambient sizes of 2411 2667 !-- particles by equilibrating soluble fraction of particles with water … … 2417 2673 ! 2418 2674 !-- Gaseous tracer concentrations in #/m3 2419 IF ( salsa_gases_from_chem ) THEN 2420 ! 2675 IF ( salsa_gases_from_chem ) THEN 2676 ! 2421 2677 !-- Convert concentrations in ppm to #/m3 2422 2678 zgso4 = chem_species(gas_index_chem(1))%conc(k,j,i) * ppm_to_nconc(k) 2423 2679 zghno3 = chem_species(gas_index_chem(2))%conc(k,j,i) * ppm_to_nconc(k) 2424 2680 zgnh3 = chem_species(gas_index_chem(3))%conc(k,j,i) * ppm_to_nconc(k) 2425 zgocnv = chem_species(gas_index_chem(4))%conc(k,j,i) * ppm_to_nconc(k) 2426 zgocsv = chem_species(gas_index_chem(5))%conc(k,j,i) * ppm_to_nconc(k) 2681 zgocnv = chem_species(gas_index_chem(4))%conc(k,j,i) * ppm_to_nconc(k) 2682 zgocsv = chem_species(gas_index_chem(5))%conc(k,j,i) * ppm_to_nconc(k) 2427 2683 ELSE 2428 zgso4 = salsa_gas(1)%conc(k,j,i) 2429 zghno3 = salsa_gas(2)%conc(k,j,i) 2430 zgnh3 = salsa_gas(3)%conc(k,j,i) 2431 zgocnv = salsa_gas(4)%conc(k,j,i) 2684 zgso4 = salsa_gas(1)%conc(k,j,i) 2685 zghno3 = salsa_gas(2)%conc(k,j,i) 2686 zgnh3 = salsa_gas(3)%conc(k,j,i) 2687 zgocnv = salsa_gas(4)%conc(k,j,i) 2432 2688 zgocsv = salsa_gas(5)%conc(k,j,i) 2433 ENDIF 2434 ! 2435 !-- ***************************************! 2436 !-- Run SALSA ! 2437 !-- ***************************************! 2438 CALL run_salsa( in_p(k), in_cw(k), in_cs(k), in_t(k), in_u(k), & 2439 in_adn(k), in_lad, zgso4, zgocnv, zgocsv, zghno3, zgnh3,& 2440 aero, prtcl, kvis(k), Sc(k,:), vd(k,:), dt_salsa ) 2441 !-- ***************************************! 2689 ENDIF 2690 ! 2691 !-- Calculate aerosol processes: 2692 !-- ********************************************************************************************* 2693 ! 2694 !-- Coagulation 2695 IF ( lscoag ) THEN 2696 CALL coagulation( aero, dt_salsa, in_t(k), in_p(k) ) 2697 ENDIF 2698 ! 2699 !-- Condensation 2700 IF ( lscnd ) THEN 2701 CALL condensation( aero, zgso4, zgocnv, zgocsv, zghno3, zgnh3, in_cw(k), in_cs(k), & 2702 in_t(k), in_p(k), dt_salsa, prtcl ) 2703 ENDIF 2704 ! 2705 !-- Deposition 2706 IF ( lsdepo ) THEN 2707 CALL deposition( aero, in_t(k), in_adn(k), in_u(k), in_lad, kvis(k), schmidt_num(k,:), & 2708 vd(k,:) ) 2709 ENDIF 2710 ! 2711 !-- Size distribution bin update 2712 IF ( lsdistupdate ) THEN 2713 CALL distr_update( aero ) 2714 ENDIF 2715 !-- ********************************************************************************************* 2716 2442 2717 IF ( lsdepo ) sedim_vd(k,j,i,:) = vd(k,:) 2443 ! 2718 ! 2444 2719 !-- Calculate changes in concentrations 2445 DO bb = 1, nbins2446 aerosol_number( bb)%conc(k,j,i) = aerosol_number(bb)%conc(k,j,i)&2447 + ( aero(bb)%numc - aero_old(bb)%numc ) * flag2720 DO ib = 1, nbins_aerosol 2721 aerosol_number(ib)%conc(k,j,i) = aerosol_number(ib)%conc(k,j,i) + ( aero(ib)%numc - & 2722 aero_old(ib)%numc ) * flag 2448 2723 ENDDO 2449 2450 IF ( i so4 > 0 ) THEN2724 2725 IF ( index_so4 > 0 ) THEN 2451 2726 vc = 1 2452 str = ( i so4-1 ) * nbins+ 12453 endi = i so4 * nbins2454 cc = 12727 str = ( index_so4-1 ) * nbins_aerosol + 1 2728 endi = index_so4 * nbins_aerosol 2729 ic = 1 2455 2730 DO ss = str, endi 2456 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) & 2457 + ( aero(cc)%volc(vc) - aero_old(cc)%volc(vc) ) & 2458 * arhoh2so4 * flag 2459 cc = cc+1 2731 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) + ( aero(ic)%volc(vc) - & 2732 aero_old(ic)%volc(vc) ) * arhoh2so4 * flag 2733 ic = ic+1 2460 2734 ENDDO 2461 2735 ENDIF 2462 2463 IF ( i oc > 0 ) THEN2736 2737 IF ( index_oc > 0 ) THEN 2464 2738 vc = 2 2465 str = ( i oc-1 ) * nbins+ 12466 endi = i oc * nbins2467 cc = 12739 str = ( index_oc-1 ) * nbins_aerosol + 1 2740 endi = index_oc * nbins_aerosol 2741 ic = 1 2468 2742 DO ss = str, endi 2469 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) & 2470 + ( aero(cc)%volc(vc) - aero_old(cc)%volc(vc) ) & 2471 * arhooc * flag 2472 cc = cc+1 2743 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) + ( aero(ic)%volc(vc) - & 2744 aero_old(ic)%volc(vc) ) * arhooc * flag 2745 ic = ic+1 2473 2746 ENDDO 2474 2747 ENDIF 2475 2476 IF ( i bc > 0 ) THEN2748 2749 IF ( index_bc > 0 ) THEN 2477 2750 vc = 3 2478 str = ( i bc-1 ) * nbins + 1 + fn1a2479 endi = i bc * nbins2480 cc = 1 + fn1a2751 str = ( index_bc-1 ) * nbins_aerosol + 1 + end_subrange_1a 2752 endi = index_bc * nbins_aerosol 2753 ic = 1 + end_subrange_1a 2481 2754 DO ss = str, endi 2482 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) & 2483 + ( aero(cc)%volc(vc) - aero_old(cc)%volc(vc) ) & 2484 * arhobc * flag 2485 cc = cc+1 2755 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) + ( aero(ic)%volc(vc) - & 2756 aero_old(ic)%volc(vc) ) * arhobc * flag 2757 ic = ic+1 2486 2758 ENDDO 2487 2759 ENDIF 2488 2489 IF ( i du > 0 ) THEN2760 2761 IF ( index_du > 0 ) THEN 2490 2762 vc = 4 2491 str = ( i du-1 ) * nbins + 1 + fn1a2492 endi = i du * nbins2493 cc = 1 + fn1a2763 str = ( index_du-1 ) * nbins_aerosol + 1 + end_subrange_1a 2764 endi = index_du * nbins_aerosol 2765 ic = 1 + end_subrange_1a 2494 2766 DO ss = str, endi 2495 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) & 2496 + ( aero(cc)%volc(vc) - aero_old(cc)%volc(vc) ) & 2497 * arhodu * flag 2498 cc = cc+1 2767 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) + ( aero(ic)%volc(vc) - & 2768 aero_old(ic)%volc(vc) ) * arhodu * flag 2769 ic = ic+1 2499 2770 ENDDO 2500 2771 ENDIF 2501 2502 IF ( i ss > 0 ) THEN2772 2773 IF ( index_ss > 0 ) THEN 2503 2774 vc = 5 2504 str = ( i ss-1 ) * nbins + 1 + fn1a2505 endi = i ss * nbins2506 cc = 1 + fn1a2775 str = ( index_ss-1 ) * nbins_aerosol + 1 + end_subrange_1a 2776 endi = index_ss * nbins_aerosol 2777 ic = 1 + end_subrange_1a 2507 2778 DO ss = str, endi 2508 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) & 2509 + ( aero(cc)%volc(vc) - aero_old(cc)%volc(vc) ) & 2510 * arhoss * flag 2511 cc = cc+1 2779 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) + ( aero(ic)%volc(vc) - & 2780 aero_old(ic)%volc(vc) ) * arhoss * flag 2781 ic = ic+1 2512 2782 ENDDO 2513 2783 ENDIF 2514 2515 IF ( in o > 0 ) THEN2784 2785 IF ( index_no > 0 ) THEN 2516 2786 vc = 6 2517 str = ( in o-1 ) * nbins+ 12518 endi = in o * nbins2519 cc = 12787 str = ( index_no-1 ) * nbins_aerosol + 1 2788 endi = index_no * nbins_aerosol 2789 ic = 1 2520 2790 DO ss = str, endi 2521 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) & 2522 + ( aero(cc)%volc(vc) - aero_old(cc)%volc(vc) ) & 2523 * arhohno3 * flag 2524 cc = cc+1 2791 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) + ( aero(ic)%volc(vc) - & 2792 aero_old(ic)%volc(vc) ) * arhohno3 * flag 2793 ic = ic+1 2525 2794 ENDDO 2526 2795 ENDIF 2527 2528 IF ( in h > 0 ) THEN2796 2797 IF ( index_nh > 0 ) THEN 2529 2798 vc = 7 2530 str = ( in o-1 ) * nbins+ 12531 endi = in o * nbins2532 cc = 12799 str = ( index_nh-1 ) * nbins_aerosol + 1 2800 endi = index_nh * nbins_aerosol 2801 ic = 1 2533 2802 DO ss = str, endi 2534 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) & 2535 + ( aero(cc)%volc(vc) - aero_old(cc)%volc(vc) ) & 2536 * arhonh3 * flag 2537 cc = cc+1 2803 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) + ( aero(ic)%volc(vc) - & 2804 aero_old(ic)%volc(vc) ) * arhonh3 * flag 2805 ic = ic+1 2538 2806 ENDDO 2539 2807 ENDIF 2540 2808 2541 2809 IF ( advect_particle_water ) THEN 2542 2810 nc_h2o = get_index( prtcl,'H2O' ) 2543 2811 vc = 8 2544 str = ( nc_h2o-1 ) * nbins + 12545 endi = nc_h2o * nbins 2546 cc = 12812 str = ( nc_h2o-1 ) * nbins_aerosol + 1 2813 endi = nc_h2o * nbins_aerosol 2814 ic = 1 2547 2815 DO ss = str, endi 2548 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) & 2549 + ( aero(cc)%volc(vc) - aero_old(cc)%volc(vc) ) & 2550 * arhoh2o * flag 2816 aerosol_mass(ss)%conc(k,j,i) = aerosol_mass(ss)%conc(k,j,i) + ( aero(ic)%volc(vc) - & 2817 aero_old(ic)%volc(vc) ) * arhoh2o * flag 2551 2818 IF ( prunmode == 1 ) THEN 2552 aerosol_mass(ss)%init(k) = MAX( aerosol_mass(ss)%init(k), & 2553 aerosol_mass(ss)%conc(k,j,i) ) 2819 aerosol_mass(ss)%init(k) = MAX( aerosol_mass(ss)%init(k), & 2820 aerosol_mass(ss)%conc(k,j,i) ) 2821 IF ( k == nzb+1 ) THEN 2822 aerosol_mass(ss)%init(k-1) = 0.0_wp 2823 ELSEIF ( k == nzt ) THEN 2824 aerosol_mass(ss)%init(k+1) = aerosol_mass(ss)%init(k) 2825 ENDIF 2554 2826 ENDIF 2555 cc = cc+12827 ic = ic+1 2556 2828 ENDDO 2557 2829 ENDIF 2558 2830 ! 2559 2831 !-- Condensation of precursor gases 2560 2832 IF ( lscndgas ) THEN 2561 IF ( salsa_gases_from_chem ) THEN 2562 ! 2833 IF ( salsa_gases_from_chem ) THEN 2834 ! 2563 2835 !-- SO4 (or H2SO4) 2564 chem_species( gas_index_chem(1) )%conc(k,j,i) = & 2565 chem_species( gas_index_chem(1) )%conc(k,j,i) + & 2566 ( zgso4 / ppm_to_nconc(k) - & 2567 chem_species( gas_index_chem(1) )%conc(k,j,i) ) * flag 2568 ! 2836 ig = gas_index_chem(1) 2837 chem_species(ig)%conc(k,j,i) = chem_species(ig)%conc(k,j,i) + ( zgso4 / & 2838 ppm_to_nconc(k) - chem_species(ig)%conc(k,j,i) ) * flag 2839 ! 2569 2840 !-- HNO3 2570 chem_species( gas_index_chem(2) )%conc(k,j,i) = & 2571 chem_species( gas_index_chem(2) )%conc(k,j,i) + & 2572 ( zghno3 / ppm_to_nconc(k) - & 2573 chem_species( gas_index_chem(2) )%conc(k,j,i) ) * flag 2574 ! 2841 ig = gas_index_chem(2) 2842 chem_species(ig)%conc(k,j,i) = chem_species(ig)%conc(k,j,i) + ( zghno3 / & 2843 ppm_to_nconc(k) - chem_species(ig)%conc(k,j,i) ) * flag 2844 ! 2575 2845 !-- NH3 2576 chem_species( gas_index_chem(3) )%conc(k,j,i) = & 2577 chem_species( gas_index_chem(3) )%conc(k,j,i) + & 2578 ( zgnh3 / ppm_to_nconc(k) - & 2579 chem_species( gas_index_chem(3) )%conc(k,j,i) ) * flag 2580 ! 2846 ig = gas_index_chem(3) 2847 chem_species(ig)%conc(k,j,i) = chem_species(ig)%conc(k,j,i) + ( zgnh3 / & 2848 ppm_to_nconc(k) - chem_species(ig)%conc(k,j,i) ) * flag 2849 ! 2581 2850 !-- non-volatile OC 2582 chem_species( gas_index_chem(4) )%conc(k,j,i) = & 2583 chem_species( gas_index_chem(4) )%conc(k,j,i) + & 2584 ( zgocnv / ppm_to_nconc(k) - & 2585 chem_species( gas_index_chem(4) )%conc(k,j,i) ) * flag 2586 ! 2851 ig = gas_index_chem(4) 2852 chem_species(ig)%conc(k,j,i) = chem_species(ig)%conc(k,j,i) + ( zgocnv / & 2853 ppm_to_nconc(k) - chem_species(ig)%conc(k,j,i) ) * flag 2854 ! 2587 2855 !-- semi-volatile OC 2588 chem_species( gas_index_chem(5) )%conc(k,j,i) = & 2589 chem_species( gas_index_chem(5) )%conc(k,j,i) + & 2590 ( zgocsv / ppm_to_nconc(k) - & 2591 chem_species( gas_index_chem(5) )%conc(k,j,i) ) * flag 2592 2856 ig = gas_index_chem(5) 2857 chem_species(ig)%conc(k,j,i) = chem_species(ig)%conc(k,j,i) + ( zgocsv / & 2858 ppm_to_nconc(k) - chem_species(ig)%conc(k,j,i) ) * flag 2859 2593 2860 ELSE 2594 ! 2861 ! 2595 2862 !-- SO4 (or H2SO4) 2596 salsa_gas(1)%conc(k,j,i) = salsa_gas(1)%conc(k,j,i) + ( zgso4 - &2597 2598 ! 2863 salsa_gas(1)%conc(k,j,i) = salsa_gas(1)%conc(k,j,i) + ( zgso4 - & 2864 salsa_gas(1)%conc(k,j,i) ) * flag 2865 ! 2599 2866 !-- HNO3 2600 salsa_gas(2)%conc(k,j,i) = salsa_gas(2)%conc(k,j,i) + ( zghno3 - &2601 2602 ! 2867 salsa_gas(2)%conc(k,j,i) = salsa_gas(2)%conc(k,j,i) + ( zghno3 - & 2868 salsa_gas(2)%conc(k,j,i) ) * flag 2869 ! 2603 2870 !-- NH3 2604 salsa_gas(3)%conc(k,j,i) = salsa_gas(3)%conc(k,j,i) + ( zgnh3 - &2605 2606 ! 2871 salsa_gas(3)%conc(k,j,i) = salsa_gas(3)%conc(k,j,i) + ( zgnh3 - & 2872 salsa_gas(3)%conc(k,j,i) ) * flag 2873 ! 2607 2874 !-- non-volatile OC 2608 salsa_gas(4)%conc(k,j,i) = salsa_gas(4)%conc(k,j,i) + ( zgocnv - &2609 2610 ! 2875 salsa_gas(4)%conc(k,j,i) = salsa_gas(4)%conc(k,j,i) + ( zgocnv - & 2876 salsa_gas(4)%conc(k,j,i) ) * flag 2877 ! 2611 2878 !-- semi-volatile OC 2612 salsa_gas(5)%conc(k,j,i) = salsa_gas(5)%conc(k,j,i) + ( zgocsv - &2613 2879 salsa_gas(5)%conc(k,j,i) = salsa_gas(5)%conc(k,j,i) + ( zgocsv - & 2880 salsa_gas(5)%conc(k,j,i) ) * flag 2614 2881 ENDIF 2615 2882 ENDIF 2616 ! 2883 ! 2617 2884 !-- Tendency of water vapour mixing ratio is obtained from the 2618 2885 !-- change in RH during SALSA run. This releases heat and changes pt. … … 2621 2888 ! 2622 2889 IF ( feedback_to_palm ) THEN 2623 q_p(k,j,i) = q_p(k,j,i) + 1.0_wp / ( in_cw(k) * in_adn(k) + 1.0_wp ) & 2624 ** 2.0_wp * ( in_cw(k) - cw_old ) * in_adn(k) 2625 pt_p(k,j,i) = pt_p(k,j,i) + alv / c_p * ( in_cw(k) - cw_old ) * & 2626 in_adn(k) / ( in_cw(k) / in_adn(k) + 1.0_wp ) ** 2.0_wp& 2627 * pt_p(k,j,i) / in_t(k) 2628 ENDIF 2629 2890 q_p(k,j,i) = q_p(k,j,i) + 1.0_wp / ( in_cw(k) * in_adn(k) + 1.0_wp )**2 * & 2891 ( in_cw(k) - cw_old ) * in_adn(k) * flag 2892 pt_p(k,j,i) = pt_p(k,j,i) + alv / c_p * ( in_cw(k) - cw_old ) * in_adn(k) / ( in_cw(k) / & 2893 in_adn(k) + 1.0_wp )**2 * pt_p(k,j,i) / in_t(k) * flag 2894 ENDIF 2895 2630 2896 ENDDO ! k 2631 ! 2632 !-- Set surfaces and wall fluxes due to deposition 2633 IF ( lsdepo _topo.AND. prunmode == 3 ) THEN2897 ! 2898 !-- Set surfaces and wall fluxes due to deposition 2899 IF ( lsdepo .AND. lsdepo_surf .AND. prunmode == 3 ) THEN 2634 2900 IF ( .NOT. land_surface .AND. .NOT. urban_surface ) THEN 2635 CALL depo_ topo( i, j, surf_def_h(0), vd, Sc, kvis, in_u, rho_air_zw)2901 CALL depo_surf( i, j, surf_def_h(0), vd, schmidt_num, kvis, in_u, .TRUE. ) 2636 2902 DO l = 0, 3 2637 CALL depo_topo( i, j, surf_def_v(l), vd, Sc, kvis, in_u, & 2638 rho_air_zw**0.0_wp ) 2903 CALL depo_surf( i, j, surf_def_v(l), vd, schmidt_num, kvis, in_u, .FALSE., l ) 2639 2904 ENDDO 2640 2905 ELSE 2641 CALL depo_ topo( i, j, surf_usm_h, vd, Sc, kvis, in_u, rho_air_zw)2906 CALL depo_surf( i, j, surf_usm_h, vd, schmidt_num, kvis, in_u, .TRUE. ) 2642 2907 DO l = 0, 3 2643 CALL depo_topo( i, j, surf_usm_v(l), vd, Sc, kvis, in_u, & 2644 rho_air_zw**0.0_wp ) 2908 CALL depo_surf( i, j, surf_usm_v(l), vd, schmidt_num, kvis, in_u, .FALSE., l ) 2645 2909 ENDDO 2646 CALL depo_ topo( i, j, surf_lsm_h, vd, Sc, kvis, in_u, rho_air_zw)2910 CALL depo_surf( i, j, surf_lsm_h, vd, schmidt_num, kvis, in_u, .TRUE. ) 2647 2911 DO l = 0, 3 2648 CALL depo_topo( i, j, surf_lsm_v(l), vd, Sc, kvis, in_u, & 2649 rho_air_zw**0.0_wp ) 2912 CALL depo_surf( i, j, surf_lsm_v(l), vd, schmidt_num, kvis, in_u, .FALSE., l ) 2650 2913 ENDDO 2651 2914 ENDIF 2652 2915 ENDIF 2653 2916 2654 2917 END SUBROUTINE salsa_driver 2655 2918 2656 !------------------------------------------------------------------------------!2657 ! Description:2658 ! ------------2659 !> The SALSA subroutine2660 !> Modified for the new aerosol datatype,2661 !> Juha Tonttila, FMI, 2014.2662 !> Only aerosol processes included, Mona Kurppa, UHel, 20172663 !------------------------------------------------------------------------------!2664 SUBROUTINE run_salsa( ppres, pcw, pcs, ptemp, mag_u, adn, lad, pc_h2so4, &2665 pc_ocnv, pc_ocsv, pc_hno3, pc_nh3, paero, prtcl, kvis, &2666 Sc, vc, ptstep )2667 2668 IMPLICIT NONE2669 !2670 !-- Input parameters and variables2671 REAL(wp), INTENT(in) :: adn !< air density (kg/m3)2672 REAL(wp), INTENT(in) :: lad !< leaf area density (m2/m3)2673 REAL(wp), INTENT(in) :: mag_u !< magnitude of wind (m/s)2674 REAL(wp), INTENT(in) :: ppres !< atmospheric pressure at each grid2675 !< point (Pa)2676 REAL(wp), INTENT(in) :: ptemp !< temperature at each grid point (K)2677 REAL(wp), INTENT(in) :: ptstep !< time step of salsa processes (s)2678 TYPE(component_index), INTENT(in) :: prtcl !< part. component index table2679 !2680 !-- Input variables that are changed within:2681 REAL(wp), INTENT(inout) :: kvis !< kinematic viscosity of air (m2/s)2682 REAL(wp), INTENT(inout) :: Sc(:) !< particle Schmidt number2683 REAL(wp), INTENT(inout) :: vc(:) !< particle fall speed (m/s,2684 !< sedimentation velocity)2685 !-- Gas phase concentrations at each grid point (#/m3)2686 REAL(wp), INTENT(inout) :: pc_h2so4 !< sulphuric acid2687 REAL(wp), INTENT(inout) :: pc_hno3 !< nitric acid2688 REAL(wp), INTENT(inout) :: pc_nh3 !< ammonia2689 REAL(wp), INTENT(inout) :: pc_ocnv !< nonvolatile OC2690 REAL(wp), INTENT(inout) :: pc_ocsv !< semivolatile OC2691 REAL(wp), INTENT(inout) :: pcs !< Saturation concentration of water2692 !< vapour (kg/m3)2693 REAL(wp), INTENT(inout) :: pcw !< Water vapour concentration (kg/m3)2694 TYPE(t_section), INTENT(inout) :: paero(fn2b)2695 !2696 !-- Coagulation2697 IF ( lscoag ) THEN2698 CALL coagulation( paero, ptstep, ptemp, ppres )2699 ENDIF2700 !2701 !-- Condensation2702 IF ( lscnd ) THEN2703 CALL condensation( paero, pc_h2so4, pc_ocnv, pc_ocsv, pc_hno3, pc_nh3, &2704 pcw, pcs, ptemp, ppres, ptstep, prtcl )2705 ENDIF2706 !2707 !-- Deposition2708 IF ( lsdepo ) THEN2709 CALL deposition( paero, ptemp, adn, mag_u, lad, kvis, Sc, vc )2710 ENDIF2711 !2712 !-- Size distribution bin update2713 !-- Mona: why done 3 times in SALSA-standalone?2714 IF ( lsdistupdate ) THEN2715 CALL distr_update( paero )2716 ENDIF2717 2718 END SUBROUTINE run_salsa2719 2720 2919 !------------------------------------------------------------------------------! 2721 2920 ! Description: … … 2727 2926 !------------------------------------------------------------------------------! 2728 2927 SUBROUTINE set_salsa_runtime( prunmode ) 2729 2928 2730 2929 IMPLICIT NONE 2731 2930 2732 2931 INTEGER(iwp), INTENT(in) :: prunmode 2733 2932 2734 2933 SELECT CASE(prunmode) 2735 2934 … … 2740 2939 lscndh2oae = .FALSE. 2741 2940 lsdepo = .FALSE. 2742 lsdepo_ vege= .FALSE.2743 lsdepo_ topo= .FALSE.2941 lsdepo_pcm = .FALSE. 2942 lsdepo_surf = .FALSE. 2744 2943 lsdistupdate = .TRUE. 2944 lspartition = .FALSE. 2745 2945 2746 2946 CASE(2) !< Spinup period … … 2756 2956 lscndh2oae = nlcndh2oae 2757 2957 lsdepo = nldepo 2758 lsdepo_ vege = nldepo_vege2759 lsdepo_ topo = nldepo_topo2958 lsdepo_pcm = nldepo_pcm 2959 lsdepo_surf = nldepo_surf 2760 2960 lsdistupdate = nldistupdate 2761 2762 2961 END SELECT 2763 2962 2764 2963 2765 END SUBROUTINE set_salsa_runtime 2964 END SUBROUTINE set_salsa_runtime 2766 2965 2767 2966 !------------------------------------------------------------------------------! … … 2770 2969 !> Calculates the absolute temperature (using hydrostatic pressure), saturation 2771 2970 !> vapour pressure and mixing ratio over water, relative humidity and air 2772 !> density needed in the SALSA model. 2971 !> density needed in the SALSA model. 2773 2972 !> NOTE, no saturation adjustment takes place -> the resulting water vapour 2774 2973 !> mixing ratio can be supersaturated, allowing the microphysical calculations … … 2779 2978 !------------------------------------------------------------------------------! 2780 2979 SUBROUTINE salsa_thrm_ij( i, j, p_ij, temp_ij, cw_ij, cs_ij, adn_ij ) 2781 2782 USE arrays_3d, &2783 ONLY: p , pt, q, zu2784 2785 USE basic_constants_and_equations_mod, &2980 2981 USE arrays_3d, & 2982 ONLY: pt, q, zu 2983 2984 USE basic_constants_and_equations_mod, & 2786 2985 ONLY: barometric_formula, exner_function, ideal_gas_law_rho, magnus 2787 2788 USE control_parameters, &2986 2987 USE control_parameters, & 2789 2988 ONLY: pt_surface, surface_pressure 2790 2989 2791 2990 IMPLICIT NONE 2792 2793 INTEGER(iwp), INTENT(in) :: i 2794 INTEGER(iwp), INTENT(in) :: j 2795 REAL(wp), DIMENSION(:), INTENT(inout) :: adn_ij 2796 REAL(wp), DIMENSION(:), INTENT(inout) :: p_ij 2797 REAL(wp), DIMENSION(:), INTENT(inout) :: temp_ij 2798 REAL(wp), DIMENSION(:), INTENT(inout), OPTIONAL :: cw_ij 2799 REAL(wp), DIMENSION(:), INTENT(inout), OPTIONAL :: cs_ij 2800 REAL(wp), DIMENSION(nzb:nzt+1) :: e_s !< saturation vapour pressure 2801 !< over water (Pa) 2802 REAL(wp) :: t_surface !< absolute surface temperature (K) 2803 ! 2804 !-- Pressure p_ijk (Pa) = hydrostatic pressure + perturbation pressure (p) 2991 2992 INTEGER(iwp), INTENT(in) :: i !< 2993 INTEGER(iwp), INTENT(in) :: j !< 2994 2995 REAL(wp) :: t_surface !< absolute surface temperature (K) 2996 2997 REAL(wp), DIMENSION(nzb:nzt+1) :: e_s !< saturation vapour pressure over water (Pa) 2998 2999 REAL(wp), DIMENSION(:), INTENT(inout) :: adn_ij !< air density (kg/m3) 3000 REAL(wp), DIMENSION(:), INTENT(inout) :: p_ij !< air pressure (Pa) 3001 REAL(wp), DIMENSION(:), INTENT(inout) :: temp_ij !< air temperature (K) 3002 3003 REAL(wp), DIMENSION(:), INTENT(inout), OPTIONAL :: cw_ij !< water vapour concentration (kg/m3) 3004 REAL(wp), DIMENSION(:), INTENT(inout), OPTIONAL :: cs_ij !< saturation water vap. conc.(kg/m3) 3005 ! 3006 !-- Pressure p_ijk (Pa) = hydrostatic pressure 2805 3007 t_surface = pt_surface * exner_function( surface_pressure * 100.0_wp ) 2806 p_ij(:) = barometric_formula( zu, t_surface, surface_pressure * 100.0_wp ) & 2807 + p(:,j,i) 2808 ! 3008 p_ij(:) = barometric_formula( zu, t_surface, surface_pressure * 100.0_wp ) 3009 ! 2809 3010 !-- Absolute ambient temperature (K) 2810 temp_ij(:) = pt(:,j,i) * exner_function( p_ij(:) ) 3011 temp_ij(:) = pt(:,j,i) * exner_function( p_ij(:) ) 2811 3012 ! 2812 3013 !-- Air density … … 2815 3016 !-- Water vapour concentration r_v (kg/m3) 2816 3017 IF ( PRESENT( cw_ij ) ) THEN 2817 cw_ij(:) = ( q(:,j,i) / ( 1.0_wp - q(:,j,i) ) ) * adn_ij(:) 3018 cw_ij(:) = ( q(:,j,i) / ( 1.0_wp - q(:,j,i) ) ) * adn_ij(:) 2818 3019 ENDIF 2819 3020 ! … … 2822 3023 e_s(:) = 611.0_wp * EXP( alv_d_rv * ( 3.6609E-3_wp - 1.0_wp / & 2823 3024 temp_ij(:) ) )! magnus( temp_ij(:) ) 2824 cs_ij(:) = ( 0.622_wp * e_s / ( p_ij(:) - e_s(:) ) ) * adn_ij(:) 3025 cs_ij(:) = ( 0.622_wp * e_s / ( p_ij(:) - e_s(:) ) ) * adn_ij(:) 2825 3026 ENDIF 2826 3027 2827 END SUBROUTINE salsa_thrm_ij 3028 END SUBROUTINE salsa_thrm_ij 2828 3029 2829 3030 !------------------------------------------------------------------------------! … … 2862 3063 !> fxm: crashes if no sulphate or sea salt 2863 3064 !> fxm: do we really need to consider Kelvin effect for subrange 2 2864 !------------------------------------------------------------------------------! 3065 !------------------------------------------------------------------------------! 2865 3066 SUBROUTINE equilibration( prh, ptemp, paero, init ) 2866 3067 2867 3068 IMPLICIT NONE 2868 ! 2869 !-- Input variables 2870 LOGICAL, INTENT(in) :: init !< TRUE: Initialization call 2871 !< FALSE: Normal runtime: update water 2872 !< content only for 1a 2873 REAL(wp), INTENT(in) :: prh !< relative humidity [0-1] 2874 REAL(wp), INTENT(in) :: ptemp !< temperature (K) 2875 ! 2876 !-- Output variables 2877 TYPE(t_section), INTENT(inout) :: paero(fn2b) 2878 ! 2879 !-- Local 2880 INTEGER(iwp) :: b !< loop index 3069 3070 INTEGER(iwp) :: ib !< loop index 2881 3071 INTEGER(iwp) :: counti !< loop index 2882 REAL(wp) :: zaw !< water activity [0-1] 2883 REAL(wp) :: zbinmol(7) !< binary molality of each components (mol/kg) 2884 REAL(wp) :: zcore !< Volume of dry particle 2885 REAL(wp) :: zdold !< Old diameter 2886 REAL(wp) :: zdwet !< Wet diameter or mean droplet diameter 2887 REAL(wp) :: zke !< Kelvin term in the Köhler equation 2888 REAL(wp) :: zlwc !< liquid water content [kg/m3-air] 2889 REAL(wp) :: zrh !< Relative humidity 2890 REAL(wp) :: zvpart(7) !< volume of chem. compounds in one particle 2891 3072 3073 LOGICAL, INTENT(in) :: init !< TRUE: Initialization, FALSE: Normal runtime: update water 3074 !< content only for 1a 3075 3076 REAL(wp) :: zaw !< water activity [0-1] 3077 REAL(wp) :: zcore !< Volume of dry particle 3078 REAL(wp) :: zdold !< Old diameter 3079 REAL(wp) :: zdwet !< Wet diameter or mean droplet diameter 3080 REAL(wp) :: zke !< Kelvin term in the Köhler equation 3081 REAL(wp) :: zlwc !< liquid water content [kg/m3-air] 3082 REAL(wp) :: zrh !< Relative humidity 3083 3084 REAL(wp), DIMENSION(maxspec) :: zbinmol !< binary molality of each components (mol/kg) 3085 REAL(wp), DIMENSION(maxspec) :: zvpart !< volume of chem. compounds in one particle 3086 3087 REAL(wp), INTENT(in) :: prh !< relative humidity [0-1] 3088 REAL(wp), INTENT(in) :: ptemp !< temperature (K) 3089 3090 TYPE(t_section), DIMENSION(nbins_aerosol), INTENT(inout) :: paero !< aerosol properties 3091 2892 3092 zaw = 0.0_wp 2893 zbinmol = 0.0_wp2894 zcore = 0.0_wp2895 zdold = 0.0_wp2896 zdwet = 0.0_wp2897 3093 zlwc = 0.0_wp 2898 zrh = 0.0_wp 2899 2900 ! 3094 ! 2901 3095 !-- Relative humidity: 2902 3096 zrh = prh 2903 3097 zrh = MAX( zrh, 0.05_wp ) 2904 zrh = MIN( zrh, 0.98_wp) 3098 zrh = MIN( zrh, 0.98_wp) 2905 3099 ! 2906 3100 !-- 1) Regime 1: sulphate and partly water-soluble OC. Done for every CALL 2907 DO b = in1a, fn1a ! size bin2908 3101 DO ib = start_subrange_1a, end_subrange_1a ! size bin 3102 2909 3103 zbinmol = 0.0_wp 2910 zdold = 1.0_wp 3104 zdold = 1.0_wp 2911 3105 zke = 1.02_wp 2912 2913 IF ( paero( b)%numc > nclim ) THEN3106 3107 IF ( paero(ib)%numc > nclim ) THEN 2914 3108 ! 2915 3109 !-- Volume in one particle 2916 3110 zvpart = 0.0_wp 2917 zvpart(1:2) = paero( b)%volc(1:2) / paero(b)%numc2918 zvpart(6:7) = paero( b)%volc(6:7) / paero(b)%numc2919 ! 3111 zvpart(1:2) = paero(ib)%volc(1:2) / paero(ib)%numc 3112 zvpart(6:7) = paero(ib)%volc(6:7) / paero(ib)%numc 3113 ! 2920 3114 !-- Total volume and wet diameter of one dry particle 2921 3115 zcore = SUM( zvpart(1:2) ) 2922 zdwet = paero( b)%dwet2923 3116 zdwet = paero(ib)%dwet 3117 2924 3118 counti = 0 2925 DO WHILE ( ABS( zdwet / zdold - 1.0_wp ) > 1.0E-2_wp ) 2926 3119 DO WHILE ( ABS( zdwet / zdold - 1.0_wp ) > 1.0E-2_wp ) 3120 2927 3121 zdold = MAX( zdwet, 1.0E-20_wp ) 2928 3122 zaw = MAX( 1.0E-3_wp, zrh / zke ) ! To avoid underflow 2929 ! 3123 ! 2930 3124 !-- Binary molalities (mol/kg): 2931 3125 !-- Sulphate 2932 zbinmol(1) = 1.1065495E+2_wp - 3.6759197E+2_wp * zaw & 2933 + 5.0462934E+2_wp * zaw**2.0_wp & 2934 - 3.1543839E+2_wp * zaw**3.0_wp & 2935 + 6.770824E+1_wp * zaw**4.0_wp 2936 !-- Organic carbon 2937 zbinmol(2) = 1.0_wp / ( zaw * amh2o ) - 1.0_wp / amh2o 2938 !-- Nitric acid 2939 zbinmol(6) = 2.306844303E+1_wp - 3.563608869E+1_wp * zaw & 2940 - 6.210577919E+1_wp * zaw**2.0_wp & 2941 + 5.510176187E+2_wp * zaw**3.0_wp & 2942 - 1.460055286E+3_wp * zaw**4.0_wp & 2943 + 1.894467542E+3_wp * zaw**5.0_wp & 2944 - 1.220611402E+3_wp * zaw**6.0_wp & 2945 + 3.098597737E+2_wp * zaw**7.0_wp 2946 ! 2947 !-- Calculate the liquid water content (kg/m3-air) using ZSR (see e.g. 2948 !-- Eq. 10.98 in Seinfeld and Pandis (2006)) 2949 zlwc = ( paero(b)%volc(1) * ( arhoh2so4 / amh2so4 ) ) / & 2950 zbinmol(1) + epsoc * paero(b)%volc(2) * ( arhooc / amoc ) & 2951 / zbinmol(2) + ( paero(b)%volc(6) * ( arhohno3/amhno3 ) ) & 2952 / zbinmol(6) 2953 ! 2954 !-- Particle wet diameter (m) 2955 zdwet = ( zlwc / paero(b)%numc / arhoh2o / api6 + & 2956 ( SUM( zvpart(6:7) ) / api6 ) + & 2957 zcore / api6 )**( 1.0_wp / 3.0_wp ) 2958 ! 3126 zbinmol(1) = 1.1065495E+2_wp - 3.6759197E+2_wp * zaw + 5.0462934E+2_wp * zaw**2 - & 3127 3.1543839E+2_wp * zaw**3 + 6.770824E+1_wp * zaw**4 3128 !-- Organic carbon 3129 zbinmol(2) = 1.0_wp / ( zaw * amh2o ) - 1.0_wp / amh2o 3130 !-- Nitric acid 3131 zbinmol(6) = 2.306844303E+1_wp - 3.563608869E+1_wp * zaw - 6.210577919E+1_wp * zaw**2 & 3132 + 5.510176187E+2_wp * zaw**3 - 1.460055286E+3_wp * zaw**4 & 3133 + 1.894467542E+3_wp * zaw**5 - 1.220611402E+3_wp * zaw**6 & 3134 + 3.098597737E+2_wp * zaw**7 3135 ! 3136 !-- Calculate the liquid water content (kg/m3-air) using ZSR (see e.g. Eq. 10.98 in 3137 !-- Seinfeld and Pandis (2006)) 3138 zlwc = ( paero(ib)%volc(1) * ( arhoh2so4 / amh2so4 ) ) / zbinmol(1) + & 3139 epsoc * paero(ib)%volc(2) * ( arhooc / amoc ) / zbinmol(2) + & 3140 ( paero(ib)%volc(6) * ( arhohno3/amhno3 ) ) / zbinmol(6) 3141 ! 3142 !-- Particle wet diameter (m) 3143 zdwet = ( zlwc / paero(ib)%numc / arhoh2o / api6 + ( SUM( zvpart(6:7) ) / api6 ) + & 3144 zcore / api6 )**0.33333333_wp 3145 ! 2959 3146 !-- Kelvin effect (Eq. 10.85 in in Seinfeld and Pandis (2006)). Avoid 2960 3147 !-- overflow. 2961 zke = EXP( MIN( 50.0_wp, & 2962 4.0_wp * surfw0 * amvh2so4 / ( abo * ptemp * zdwet ) ) ) 2963 3148 zke = EXP( MIN( 50.0_wp, 4.0_wp * surfw0 * amvh2so4 / ( abo * ptemp * zdwet ) ) ) 3149 2964 3150 counti = counti + 1 2965 3151 IF ( counti > 1000 ) THEN 2966 3152 message_string = 'Subrange 1: no convergence!' 2967 CALL message( 'salsa_mod: equilibration', 'SA0042', & 2968 1, 2, 0, 6, 0 ) 3153 CALL message( 'salsa_mod: equilibration', 'PA0617', 1, 2, 0, 6, 0 ) 2969 3154 ENDIF 2970 3155 ENDDO 2971 ! 3156 ! 2972 3157 !-- Instead of lwc, use the volume concentration of water from now on 2973 3158 !-- (easy to convert...) 2974 paero( b)%volc(8) = zlwc / arhoh2o2975 ! 3159 paero(ib)%volc(8) = zlwc / arhoh2o 3160 ! 2976 3161 !-- If this is initialization, update the core and wet diameter 2977 3162 IF ( init ) THEN 2978 paero( b)%dwet = zdwet2979 paero( b)%core = zcore3163 paero(ib)%dwet = zdwet 3164 paero(ib)%core = zcore 2980 3165 ENDIF 2981 3166 2982 3167 ELSE 2983 3168 !-- If initialization 2984 !-- 1.2) empty bins given bin average values 3169 !-- 1.2) empty bins given bin average values 2985 3170 IF ( init ) THEN 2986 paero( b)%dwet = paero(b)%dmid2987 paero( b)%core = api6 * paero(b)%dmid ** 3.0_wp3171 paero(ib)%dwet = paero(ib)%dmid 3172 paero(ib)%core = api6 * paero(ib)%dmid**3 2988 3173 ENDIF 2989 2990 ENDIF 2991 2992 ENDDO !<b3174 3175 ENDIF 3176 3177 ENDDO ! ib 2993 3178 ! 2994 3179 !-- 2) Regime 2a: sulphate, OC, BC and sea salt … … 2996 3181 !-- are computed via condensation 2997 3182 IF ( init ) THEN 2998 DO b = in2a, fn2b2999 3183 DO ib = start_subrange_2a, end_subrange_2b 3184 ! 3000 3185 !-- Initialize 3001 3186 zke = 1.02_wp 3002 3187 zbinmol = 0.0_wp 3003 3188 zdold = 1.0_wp 3004 ! 3189 ! 3005 3190 !-- 1) Particle properties calculated for non-empty bins 3006 IF ( paero( b)%numc > nclim ) THEN3007 ! 3191 IF ( paero(ib)%numc > nclim ) THEN 3192 ! 3008 3193 !-- Volume in one particle [fxm] 3009 3194 zvpart = 0.0_wp 3010 zvpart(1:7) = paero( b)%volc(1:7) / paero(b)%numc3011 ! 3012 !-- Total volume and wet diameter of one dry particle [fxm] 3195 zvpart(1:7) = paero(ib)%volc(1:7) / paero(ib)%numc 3196 ! 3197 !-- Total volume and wet diameter of one dry particle [fxm] 3013 3198 zcore = SUM( zvpart(1:5) ) 3014 zdwet = paero( b)%dwet3199 zdwet = paero(ib)%dwet 3015 3200 3016 3201 counti = 0 3017 3202 DO WHILE ( ABS( zdwet / zdold - 1.0_wp ) > 1.0E-12_wp ) 3018 3203 3019 3204 zdold = MAX( zdwet, 1.0E-20_wp ) 3020 3205 zaw = zrh / zke 3021 ! 3206 ! 3022 3207 !-- Binary molalities (mol/kg): 3023 3208 !-- Sulphate 3024 zbinmol(1) = 1.1065495E+2_wp - 3.6759197E+2_wp * zaw & 3025 + 5.0462934E+2_wp * zaw**2 - 3.1543839E+2_wp * zaw**3 & 3026 + 6.770824E+1_wp * zaw**4 3027 !-- Organic carbon 3028 zbinmol(2) = 1.0_wp / ( zaw * amh2o ) - 1.0_wp / amh2o 3209 zbinmol(1) = 1.1065495E+2_wp - 3.6759197E+2_wp * zaw + 5.0462934E+2_wp * zaw**2 - & 3210 3.1543839E+2_wp * zaw**3 + 6.770824E+1_wp * zaw**4 3211 !-- Organic carbon 3212 zbinmol(2) = 1.0_wp / ( zaw * amh2o ) - 1.0_wp / amh2o 3029 3213 !-- Nitric acid 3030 zbinmol(6) = 2.306844303E+1_wp - 3.563608869E+1_wp * zaw & 3031 - 6.210577919E+1_wp * zaw**2 + 5.510176187E+2_wp * zaw**3 & 3032 - 1.460055286E+3_wp * zaw**4 + 1.894467542E+3_wp * zaw**5 & 3033 - 1.220611402E+3_wp * zaw**6 + 3.098597737E+2_wp * zaw**7 3034 !-- Sea salt (natrium chloride) 3035 zbinmol(5) = 5.875248E+1_wp - 1.8781997E+2_wp * zaw & 3036 + 2.7211377E+2_wp * zaw**2 - 1.8458287E+2_wp * zaw**3 & 3037 + 4.153689E+1_wp * zaw**4 3038 ! 3214 zbinmol(6) = 2.306844303E+1_wp - 3.563608869E+1_wp * zaw - & 3215 6.210577919E+1_wp * zaw**2 + 5.510176187E+2_wp * zaw**3 - & 3216 1.460055286E+3_wp * zaw**4 + 1.894467542E+3_wp * zaw**5 - & 3217 1.220611402E+3_wp * zaw**6 + 3.098597737E+2_wp * zaw**7 3218 !-- Sea salt (natrium chloride) 3219 zbinmol(5) = 5.875248E+1_wp - 1.8781997E+2_wp * zaw + 2.7211377E+2_wp * zaw**2 - & 3220 1.8458287E+2_wp * zaw**3 + 4.153689E+1_wp * zaw**4 3221 ! 3039 3222 !-- Calculate the liquid water content (kg/m3-air) 3040 zlwc = ( paero(b)%volc(1) * ( arhoh2so4 / amh2so4 ) ) / & 3041 zbinmol(1) + epsoc * ( paero(b)%volc(2) * ( arhooc / & 3042 amoc ) ) / zbinmol(2) + ( paero(b)%volc(6) * ( arhohno3 & 3043 / amhno3 ) ) / zbinmol(6) + ( paero(b)%volc(5) * & 3044 ( arhoss / amss ) ) / zbinmol(5) 3045 3046 !-- Particle wet radius (m) 3047 zdwet = ( zlwc / paero(b)%numc / arhoh2o / api6 + & 3048 ( SUM( zvpart(6:7) ) / api6 ) + & 3049 zcore / api6 ) ** ( 1.0_wp / 3.0_wp ) 3050 ! 3223 zlwc = ( paero(ib)%volc(1) * ( arhoh2so4 / amh2so4 ) ) / zbinmol(1) + & 3224 epsoc * ( paero(ib)%volc(2) * ( arhooc / amoc ) ) / zbinmol(2) + & 3225 ( paero(ib)%volc(6) * ( arhohno3 / amhno3 ) ) / zbinmol(6) + & 3226 ( paero(ib)%volc(5) * ( arhoss / amss ) ) / zbinmol(5) 3227 3228 !-- Particle wet radius (m) 3229 zdwet = ( zlwc / paero(ib)%numc / arhoh2o / api6 + ( SUM( zvpart(6:7) ) / api6 ) + & 3230 zcore / api6 )**0.33333333_wp 3231 ! 3051 3232 !-- Kelvin effect (Eq. 10.85 in Seinfeld and Pandis (2006)) 3052 zke = EXP( MIN( 50.0_wp, & 3053 4.0_wp * surfw0 * amvh2so4 / ( abo * zdwet * ptemp ) ) ) 3054 3233 zke = EXP( MIN( 50.0_wp, 4.0_wp * surfw0 * amvh2so4 / ( abo * zdwet * ptemp ) ) ) 3234 3055 3235 counti = counti + 1 3056 3236 IF ( counti > 1000 ) THEN 3057 3237 message_string = 'Subrange 2: no convergence!' 3058 CALL message( 'salsa_mod: equilibration', 'SA0043', & 3059 1, 2, 0, 6, 0 ) 3238 CALL message( 'salsa_mod: equilibration', 'PA0618', 1, 2, 0, 6, 0 ) 3060 3239 ENDIF 3061 3240 ENDDO 3062 ! 3241 ! 3063 3242 !-- Liquid water content; instead of LWC use the volume concentration 3064 paero( b)%volc(8) = zlwc / arhoh2o3065 paero( b)%dwet = zdwet3066 paero( b)%core = zcore3067 3243 paero(ib)%volc(8) = zlwc / arhoh2o 3244 paero(ib)%dwet = zdwet 3245 paero(ib)%core = zcore 3246 3068 3247 ELSE 3069 !-- 2.2) empty bins given bin average values 3070 paero( b)%dwet = paero(b)%dmid3071 paero( b)%core = api6 * paero(b)%dmid ** 3.0_wp3248 !-- 2.2) empty bins given bin average values 3249 paero(ib)%dwet = paero(ib)%dmid 3250 paero(ib)%core = api6 * paero(ib)%dmid**3 3072 3251 ENDIF 3073 3074 ENDDO ! b3252 3253 ENDDO ! ib 3075 3254 ENDIF 3076 3255 3077 END SUBROUTINE equilibration 3078 3256 END SUBROUTINE equilibration 3257 3079 3258 !------------------------------------------------------------------------------! 3080 3259 !> Description: 3081 3260 !> ------------ 3082 3261 !> Calculation of the settling velocity vc (m/s) per aerosol size bin and 3083 !> deposition on plant canopy (lsdepo_ vege).3084 ! 3085 !> Deposition is based on either the scheme presented in: 3086 !> Zhang et al. (2001), Atmos. Environ. 35, 549-560 (includes collection due to 3087 !> Brownian diffusion, impaction, interception and sedimentation )3262 !> deposition on plant canopy (lsdepo_pcm). 3263 ! 3264 !> Deposition is based on either the scheme presented in: 3265 !> Zhang et al. (2001), Atmos. Environ. 35, 549-560 (includes collection due to 3266 !> Brownian diffusion, impaction, interception and sedimentation; hereafter ZO1) 3088 3267 !> OR 3089 !> Petroff & Zhang (2010), Geosci. Model Dev. 3, 753-769 (includes also 3090 !> collection due to turbulent impaction )3091 ! 3092 !> Equation numbers refer to equation in Jacobson (2005): Fundamentals of 3093 !> Atmospheric Modeling, 2nd Edition. 3094 ! 3095 !> Subroutine follows closely sedim_SALSA in UCLALES-SALSA written by Juha 3268 !> Petroff & Zhang (2010), Geosci. Model Dev. 3, 753-769 (includes also 3269 !> collection due to turbulent impaction, hereafter P10) 3270 ! 3271 !> Equation numbers refer to equation in Jacobson (2005): Fundamentals of 3272 !> Atmospheric Modeling, 2nd Edition. 3273 ! 3274 !> Subroutine follows closely sedim_SALSA in UCLALES-SALSA written by Juha 3096 3275 !> Tonttila (KIT/FMI) and Zubair Maalick (UEF). 3097 !> Rewritten to PALM by Mona Kurppa (UH), 2017. 3276 !> Rewritten to PALM by Mona Kurppa (UH), 2017. 3098 3277 ! 3099 3278 !> Call for grid point i,j,k 3100 3279 !------------------------------------------------------------------------------! 3101 3280 3102 SUBROUTINE deposition( paero, tk, adn, mag_u, lad, kvis, Sc, vc )3103 3281 SUBROUTINE deposition( paero, tk, adn, mag_u, lad, kvis, schmidt_num, vc ) 3282 3104 3283 USE plant_canopy_model_mod, & 3105 3284 ONLY: cdc 3106 3285 3107 3286 IMPLICIT NONE 3108 3109 REAL(wp), INTENT(in) :: adn !< air density (kg/m3) 3110 REAL(wp), INTENT(out) :: kvis !< kinematic viscosity of air (m2/s) 3111 REAL(wp), INTENT(in) :: lad !< leaf area density (m2/m3) 3112 REAL(wp), INTENT(in) :: mag_u !< wind velocity (m/s) 3113 REAL(wp), INTENT(out) :: Sc(:) !< particle Schmidt number 3114 REAL(wp), INTENT(in) :: tk !< abs.temperature (K) 3115 REAL(wp), INTENT(out) :: vc(:) !< critical fall speed i.e. settling 3116 !< velocity of an aerosol particle (m/s) 3117 TYPE(t_section), INTENT(inout) :: paero(fn2b) 3118 3119 INTEGER(iwp) :: b !< loop index 3287 3288 INTEGER(iwp) :: ib !< loop index 3289 3120 3290 REAL(wp) :: avis !< molecular viscocity of air (kg/(m*s)) 3121 REAL(wp), PARAMETER :: c_A = 1.249_wp !< Constants A, B and C for 3122 REAL(wp), PARAMETER :: c_B = 0.42_wp !< calculating the Cunningham 3123 REAL(wp), PARAMETER :: c_C = 0.87_wp !< slip-flow correction (Cc) 3124 !< according to Jacobson (2005), 3125 !< Eq. 15.30 3126 REAL(wp) :: Cc !< Cunningham slip-flow correction factor 3127 REAL(wp) :: Kn !< Knudsen number 3291 REAL(wp) :: Cc !< Cunningham slip-flow correction factor 3292 REAL(wp) :: Kn !< Knudsen number 3128 3293 REAL(wp) :: lambda !< molecular mean free path (m) 3129 REAL(wp) :: mdiff !< particle diffusivity coefficient 3130 REAL(wp) :: pdn !< particle density (kg/m3) 3131 REAL(wp) :: ustar !< friction velocity (m/s) 3294 REAL(wp) :: mdiff !< particle diffusivity coefficient 3295 REAL(wp) :: pdn !< particle density (kg/m3) 3296 REAL(wp) :: ustar !< friction velocity (m/s) 3132 3297 REAL(wp) :: va !< thermal speed of an air molecule (m/s) 3133 REAL(wp) :: zdwet !< wet diameter (m) 3134 ! 3135 !-- Initialise 3136 Cc = 0.0_wp 3137 Kn = 0.0_wp 3138 mdiff = 0.0_wp 3139 pdn = 1500.0_wp ! default value 3140 ustar = 0.0_wp 3298 REAL(wp) :: zdwet !< wet diameter (m) 3299 3300 REAL(wp), INTENT(in) :: adn !< air density (kg/m3) 3301 REAL(wp), INTENT(in) :: lad !< leaf area density (m2/m3) 3302 REAL(wp), INTENT(in) :: mag_u !< wind velocity (m/s) 3303 REAL(wp), INTENT(in) :: tk !< abs.temperature (K) 3304 3305 REAL(wp), INTENT(inout) :: kvis !< kinematic viscosity of air (m2/s) 3306 3307 REAL(wp), DIMENSION(:), INTENT(inout) :: schmidt_num !< particle Schmidt number 3308 REAL(wp), DIMENSION(:), INTENT(inout) :: vc !< critical fall speed i.e. settling velocity of 3309 !< an aerosol particle (m/s) 3310 3311 TYPE(t_section), DIMENSION(nbins_aerosol), INTENT(inout) :: paero !< aerosol properties 3312 ! 3313 !-- Initialise 3314 pdn = 1500.0_wp ! default value 3315 ustar = 0.0_wp 3141 3316 ! 3142 3317 !-- Molecular viscosity of air (Eq. 4.54) 3143 avis = 1.8325E-5_wp * ( 416.16_wp / ( tk + 120.0_wp ) ) * ( tk / & 3144 296.16_wp )**1.5_wp 3145 ! 3318 avis = 1.8325E-5_wp * ( 416.16_wp / ( tk + 120.0_wp ) ) * ( tk / 296.16_wp )**1.5_wp 3319 ! 3146 3320 !-- Kinematic viscosity (Eq. 4.55) 3147 3321 kvis = avis / adn 3148 ! 3322 ! 3149 3323 !-- Thermal velocity of an air molecule (Eq. 15.32) 3150 va = SQRT( 8.0_wp * abo * tk / ( pi * am_airmol ) ) 3324 va = SQRT( 8.0_wp * abo * tk / ( pi * am_airmol ) ) 3151 3325 ! 3152 3326 !-- Mean free path (m) (Eq. 15.24) 3153 3327 lambda = 2.0_wp * avis / ( adn * va ) 3154 3155 DO b = 1, nbins3156 3157 IF ( paero( b)%numc < nclim ) CYCLE3158 zdwet = paero( b)%dwet3328 3329 DO ib = 1, nbins_aerosol 3330 3331 IF ( paero(ib)%numc < nclim ) CYCLE 3332 zdwet = paero(ib)%dwet 3159 3333 ! 3160 3334 !-- Knudsen number (Eq. 15.23) … … 3162 3336 ! 3163 3337 !-- Cunningham slip-flow correction (Eq. 15.30) 3164 Cc = 1.0_wp + Kn * ( c_A + c_B * EXP( -c_C/ Kn ) )3338 Cc = 1.0_wp + Kn * ( 1.249_wp + 0.42_wp * EXP( -0.87_wp / Kn ) ) 3165 3339 3166 3340 !-- Particle diffusivity coefficient (Eq. 15.29) 3167 3341 mdiff = ( abo * tk * Cc ) / ( 3.0_wp * pi * avis * zdwet ) 3168 ! 3342 ! 3169 3343 !-- Particle Schmidt number (Eq. 15.36) 3170 Sc(b) = kvis / mdiff 3171 ! 3172 !-- Critical fall speed i.e. settling velocity (Eq. 20.4) 3173 vc(b) = MIN( 1.0_wp, terminal_vel( 0.5_wp * zdwet, pdn, adn, avis, Cc) ) 3174 3175 IF ( lsdepo_vege .AND. plant_canopy .AND. lad > 0.0_wp ) THEN 3176 ! 3177 !-- Friction velocity calculated following Prandtl (1925): 3344 schmidt_num(ib) = kvis / mdiff 3345 ! 3346 !-- Critical fall speed i.e. settling velocity (Eq. 20.4) 3347 vc(ib) = MIN( 1.0_wp, terminal_vel( 0.5_wp * zdwet, pdn, adn, avis, Cc) ) 3348 ! 3349 !-- Friction velocity for deposition on vegetation. Calculated following Prandtl (1925): 3350 IF ( lsdepo_pcm .AND. plant_canopy .AND. lad > 0.0_wp ) THEN 3178 3351 ustar = SQRT( cdc ) * mag_u 3179 CALL depo_ vege( paero, b, vc(b), mag_u, ustar, kvis, Sc(b), lad )3180 ENDIF 3352 CALL depo_pcm( paero, ib, vc(ib), mag_u, ustar, kvis, schmidt_num(ib), lad ) 3353 ENDIF 3181 3354 ENDDO 3182 3183 END SUBROUTINE deposition 3184 3355 3356 END SUBROUTINE deposition 3357 3185 3358 !------------------------------------------------------------------------------! 3186 3359 ! Description: 3187 ! ------------ 3188 !> Calculate change in number and volume concentrations due to deposition on 3360 ! ------------ 3361 !> Calculate change in number and volume concentrations due to deposition on 3189 3362 !> plant canopy. 3190 3363 !------------------------------------------------------------------------------! 3191 SUBROUTINE depo_ vege( paero, b, vc, mag_u, ustar, kvis_a, Sc, lad )3192 3193 IMPLICIT NONE 3194 3195 INTEGER(iwp) , INTENT(in) :: b!< loop index3196 REAL(wp), INTENT(in) :: kvis_a !< kinematic viscosity of air (m2/s) 3197 REAL(wp), INTENT(in) :: lad !< leaf area density (m2/m3)3198 REAL(wp), INTENT(in) :: mag_u !< wind velocity (m/s) 3199 REAL(wp) , INTENT(in) :: Sc !< particle Schmidt number3200 REAL(wp) , INTENT(in) :: ustar !< friction velocity (m/s)3201 REAL(wp) , INTENT(in) :: vc !< terminal velocity (m/s)3202 TYPE(t_section), INTENT(inout) :: paero(fn2b)3203 3204 INTEGER(iwp) :: c !< loop index3205 3206 REAL(wp) :: alpha !< parameter, Table 3 in Zhang et al. (2001)3207 REAL(wp) :: depo !< deposition efficiency3208 REAL(wp) :: C_Br !< coefficient for Brownian diffusion3209 REAL(wp) :: C_IM !< coefficient for inertial impaction3210 REAL(wp) :: C_IN !< coefficient for interception3211 REAL(wp) :: C_IT !< coefficient for turbulent impaction3212 REAL(wp) :: gamma !< parameter, Table 3 in Zhang et al. (2001)3213 REAL(wp) :: par_A !< parameter A for the characteristic radius of3214 !< collectors, Table 3 in Zhang et al. (2001)3215 REAL(wp) :: rt !< the overall quasi-laminar resistance for3216 !< particles3217 REAL(wp) :: St !< Stokes number for smooth surfaces or bluff 3218 !< surface elements3219 REAL(wp) :: tau_plus !< dimensionless particle relaxation time3220 REAL(wp) :: v_bd !< deposition velocity due to Brownian diffusion3221 REAL(wp) :: v_im !< deposition velocity due to impaction3222 REAL(wp) :: v_in !< deposition velocity due to interception3223 REAL(wp) :: v_it !< deposition velocity due to turbulent impaction3224 ! 3225 !-- Initialise 3226 depo = 0.0_wp 3227 rt = 0.0_wp 3228 St= 0.0_wp3364 SUBROUTINE depo_pcm( paero, ib, vc, mag_u, ustar, kvis_a, schmidt_num, lad ) 3365 3366 IMPLICIT NONE 3367 3368 INTEGER(iwp) :: ic !< loop index 3369 3370 INTEGER(iwp), INTENT(in) :: ib !< loop index 3371 3372 REAL(wp) :: alpha !< parameter, Table 3 in Z01 3373 REAL(wp) :: beta_im !< parameter for turbulent impaction 3374 REAL(wp) :: depo !< deposition efficiency 3375 REAL(wp) :: c_brownian_diff !< coefficient for Brownian diffusion 3376 REAL(wp) :: c_impaction !< coefficient for inertial impaction 3377 REAL(wp) :: c_interception !< coefficient for interception 3378 REAL(wp) :: c_turb_impaction !< coefficient for turbulent impaction 3379 REAL(wp) :: gamma !< parameter, Table 3 in Z01 3380 REAL(wp) :: par_a !< parameter A for the characteristic radius of collectors, 3381 !< Table 3 in Z01 3382 REAL(wp) :: par_l !< obstacle characteristic dimension in P10 3383 REAL(wp) :: rs !< overall quasi-laminar resistance for particles 3384 REAL(wp) :: stokes_num !< Stokes number for smooth or bluff surfaces 3385 REAL(wp) :: tau_plus !< dimensionless particle relaxation time 3386 REAL(wp) :: v_bd !< deposition velocity due to Brownian diffusion 3387 REAL(wp) :: v_im !< deposition velocity due to impaction 3388 REAL(wp) :: v_in !< deposition velocity due to interception 3389 REAL(wp) :: v_it !< deposition velocity due to turbulent impaction 3390 3391 REAL(wp), INTENT(in) :: kvis_a !< kinematic viscosity of air (m2/s) 3392 REAL(wp), INTENT(in) :: lad !< leaf area density (m2/m3) 3393 REAL(wp), INTENT(in) :: mag_u !< wind velocity (m/s) 3394 REAL(wp), INTENT(in) :: schmidt_num !< particle Schmidt number 3395 REAL(wp), INTENT(in) :: ustar !< friction velocity (m/s) 3396 REAL(wp), INTENT(in) :: vc !< terminal velocity (m/s) 3397 3398 TYPE(t_section), DIMENSION(nbins_aerosol), INTENT(inout) :: paero !< aerosol properties 3399 ! 3400 !-- Initialise 3401 rs = 0.0_wp 3229 3402 tau_plus = 0.0_wp 3230 v_bd = 0.0_wp 3231 v_im = 0.0_wp 3232 v_in = 0.0_wp 3233 v_it = 0.0_wp 3234 3235 IF ( depo_vege_type == 'zhang2001' ) THEN 3236 ! 3237 !-- Parameters for the land use category 'deciduous broadleaf trees'(Table 3) 3238 par_A = 5.0E-3_wp 3239 alpha = 0.8_wp 3240 gamma = 0.56_wp 3241 ! 3242 !-- Stokes number for vegetated surfaces (Seinfeld & Pandis (2006): Eq.19.24) 3243 St = vc * ustar / ( g * par_A ) 3244 ! 3245 !-- The overall quasi-laminar resistance for particles (Zhang et al., Eq. 5) 3246 rt = MAX( EPSILON( 1.0_wp ), ( 3.0_wp * ustar * EXP( -St**0.5_wp ) * & 3247 ( Sc**( -gamma ) + ( St / ( alpha + St ) )**2.0_wp + & 3248 0.5_wp * ( paero(b)%dwet / par_A )**2.0_wp ) ) ) 3249 depo = ( rt + vc ) * lad 3250 paero(b)%numc = paero(b)%numc - depo * paero(b)%numc * dt_salsa 3251 DO c = 1, maxspec+1 3252 paero(b)%volc(c) = paero(b)%volc(c) - depo * paero(b)%volc(c) * & 3253 dt_salsa 3254 ENDDO 3255 3256 ELSEIF ( depo_vege_type == 'petroff2010' ) THEN 3257 ! 3258 !-- vd = v_BD + v_IN + v_IM + v_IT + vc 3403 v_bd = 0.0_wp 3404 v_im = 0.0_wp 3405 v_in = 0.0_wp 3406 v_it = 0.0_wp 3407 3408 IF ( depo_pcm_par == 'zhang2001' ) THEN 3409 ! 3410 !-- Parameters for the land use category 'deciduous broadleaf trees'(Table 3) 3411 alpha = alpha_z01(depo_pcm_type_num) 3412 gamma = gamma_z01(depo_pcm_type_num) 3413 par_a = A_z01(depo_pcm_type_num, season) * 1.0E-3_wp 3414 ! 3415 !-- Stokes number for vegetated surfaces (Seinfeld & Pandis (2006): Eq.19.24) 3416 stokes_num = vc * ustar / ( g * par_a ) 3417 ! 3418 !-- The overall quasi-laminar resistance for particles (Zhang et al., Eq. 5) 3419 rs = MAX( EPSILON( 1.0_wp ), ( 3.0_wp * ustar * EXP( -stokes_num**0.5_wp ) * & 3420 ( schmidt_num**( -gamma ) + ( stokes_num / ( alpha + stokes_num ) )**2 + & 3421 0.5_wp * ( paero(ib)%dwet / par_a )**2 ) ) ) 3422 3423 depo = ( rs + vc ) * lad 3424 3425 ELSEIF ( depo_pcm_par == 'petroff2010' ) THEN 3426 ! 3427 !-- vd = v_BD + v_IN + v_IM + v_IT + vc 3259 3428 !-- Deposition efficiencies from Table 1. Constants from Table 2. 3260 C_Br = 1.262_wp 3261 C_IM = 0.130_wp 3262 C_IN = 0.216_wp 3263 C_IT = 0.056_wp 3264 par_A = 0.03_wp ! Here: leaf width (m) 3265 ! 3266 !-- Stokes number for vegetated surfaces (Seinfeld & Pandis (2006): Eq.19.24) 3267 St = vc * ustar / ( g * par_A ) 3429 par_l = l_p10(depo_pcm_type_num) * 0.01_wp 3430 c_brownian_diff = c_b_p10(depo_pcm_type_num) 3431 c_interception = c_in_p10(depo_pcm_type_num) 3432 c_impaction = c_im_p10(depo_pcm_type_num) 3433 beta_im = beta_im_p10(depo_pcm_type_num) 3434 c_turb_impaction = c_it_p10(depo_pcm_type_num) 3435 ! 3436 !-- Stokes number for vegetated surfaces (Seinfeld & Pandis (2006): Eq.19.24) 3437 stokes_num = vc * ustar / ( g * par_l ) 3268 3438 ! 3269 3439 !-- Non-dimensional relexation time of the particle on top of canopy 3270 tau_plus = vc * ustar**2 .0_wp / ( kvis_a * g )3440 tau_plus = vc * ustar**2 / ( kvis_a * g ) 3271 3441 ! 3272 3442 !-- Brownian diffusion 3273 v_bd = mag_u * C_Br * Sc**( -2.0_wp / 3.0_wp ) *&3274 ( mag_u * par_ A/ kvis_a )**( -0.5_wp )3443 v_bd = mag_u * c_brownian_diff * schmidt_num**( -0.66666666_wp ) * & 3444 ( mag_u * par_l / kvis_a )**( -0.5_wp ) 3275 3445 ! 3276 3446 !-- Interception 3277 v_in = mag_u * C_IN * paero(b)%dwet / par_A * ( 2.0_wp + LOG( 2.0_wp *&3278 pa r_A / paero(b)%dwet ) )3447 v_in = mag_u * c_interception * paero(ib)%dwet / par_l * ( 2.0_wp + LOG( 2.0_wp * par_l / & 3448 paero(ib)%dwet ) ) 3279 3449 ! 3280 3450 !-- Impaction: Petroff (2009) Eq. 18 3281 v_im = mag_u * C_IM * ( St / ( St + 0.47_wp ) )**2.0_wp 3282 3451 v_im = mag_u * c_impaction * ( stokes_num / ( stokes_num + beta_im ) )**2 3452 ! 3453 !-- Turbulent impaction 3283 3454 IF ( tau_plus < 20.0_wp ) THEN 3284 v_it = 2.5E-3_wp * C_IT * tau_plus**2.0_wp3455 v_it = 2.5E-3_wp * c_turb_impaction * tau_plus**2 3285 3456 ELSE 3286 v_it = C_IT 3287 ENDIF 3288 depo = ( v_bd + v_in + v_im + v_it + vc ) * lad 3289 paero(b)%numc = paero(b)%numc - depo * paero(b)%numc * dt_salsa 3290 DO c = 1, maxspec+1 3291 paero(b)%volc(c) = paero(b)%volc(c) - depo * paero(b)%volc(c) * & 3292 dt_salsa 3293 ENDDO 3294 ENDIF 3295 3296 END SUBROUTINE depo_vege 3297 3457 v_it = c_turb_impaction 3458 ENDIF 3459 3460 depo = ( v_bd + v_in + v_im + v_it + vc ) * lad 3461 3462 ENDIF 3463 ! 3464 !-- Calculate the change in concentrations 3465 paero(ib)%numc = paero(ib)%numc - depo * paero(ib)%numc * dt_salsa 3466 DO ic = 1, maxspec+1 3467 paero(ib)%volc(ic) = paero(ib)%volc(ic) - depo * paero(ib)%volc(ic) * dt_salsa 3468 ENDDO 3469 3470 END SUBROUTINE depo_pcm 3471 3298 3472 !------------------------------------------------------------------------------! 3299 3473 ! Description: 3300 ! ------------ 3301 !> Calculate deposition on horizontal and vertical surfaces. Implement as 3302 !> surface flux. 3303 !------------------------------------------------------------------------------! 3304 3305 SUBROUTINE depo_topo( i, j, surf, vc, Sc, kvis, mag_u, norm ) 3306 3474 ! ------------ 3475 !> Calculate the dry deposition on horizontal and vertical surfaces. Implement 3476 !> as a surface flux. 3477 !> @todo aerodynamic resistance ignored for now (not important for 3478 ! high-resolution simulations) 3479 !------------------------------------------------------------------------------! 3480 SUBROUTINE depo_surf( i, j, surf, vc, schmidt_num, kvis, mag_u, norm, l ) 3481 3482 USE arrays_3d, & 3483 ONLY: rho_air_zw 3484 3307 3485 USE surface_mod, & 3308 3486 ONLY: surf_type 3309 3487 3310 3488 IMPLICIT NONE 3311 3489 3490 INTEGER(iwp) :: ib !< loop index 3491 INTEGER(iwp) :: ic !< loop index 3492 INTEGER(iwp) :: icc !< additional loop index 3493 INTEGER(iwp) :: k !< loop index 3494 INTEGER(iwp) :: m !< loop index 3495 INTEGER(iwp) :: surf_e !< End index of surface elements at (j,i)-gridpoint 3496 INTEGER(iwp) :: surf_s !< Start index of surface elements at (j,i)-gridpoint 3497 3312 3498 INTEGER(iwp), INTENT(in) :: i !< loop index 3313 3499 INTEGER(iwp), INTENT(in) :: j !< loop index 3314 REAL(wp), INTENT(in) :: kvis(:) !< kinematic viscosity of air (m2/s) 3315 REAL(wp), INTENT(in) :: mag_u(:) !< wind velocity (m/s) 3316 REAL(wp), INTENT(in) :: norm(:) !< normalisation (usually air density) 3317 REAL(wp), INTENT(in) :: Sc(:,:) !< particle Schmidt number 3318 REAL(wp), INTENT(in) :: vc(:,:) !< terminal velocity (m/s) 3319 TYPE(surf_type), INTENT(inout) :: surf !< respective surface type 3320 INTEGER(iwp) :: b !< loop index 3321 INTEGER(iwp) :: c !< loop index 3322 INTEGER(iwp) :: k !< loop index 3323 INTEGER(iwp) :: m !< loop index 3324 INTEGER(iwp) :: surf_e !< End index of surface elements at (j,i)-gridpoint 3325 INTEGER(iwp) :: surf_s !< Start index of surface elements at (j,i)-gridpoint 3326 REAL(wp) :: alpha !< parameter, Table 3 in Zhang et al. (2001) 3327 REAL(wp) :: C_Br !< coefficient for Brownian diffusion 3328 REAL(wp) :: C_IM !< coefficient for inertial impaction 3329 REAL(wp) :: C_IN !< coefficient for interception 3330 REAL(wp) :: C_IT !< coefficient for turbulent impaction 3331 REAL(wp) :: depo !< deposition efficiency 3332 REAL(wp) :: gamma !< parameter, Table 3 in Zhang et al. (2001) 3333 REAL(wp) :: par_A !< parameter A for the characteristic radius of 3334 !< collectors, Table 3 in Zhang et al. (2001) 3335 REAL(wp) :: rt !< the overall quasi-laminar resistance for 3336 !< particles 3337 REAL(wp) :: St !< Stokes number for bluff surface elements 3338 REAL(wp) :: tau_plus !< dimensionless particle relaxation time 3339 REAL(wp) :: v_bd !< deposition velocity due to Brownian diffusion 3340 REAL(wp) :: v_im !< deposition velocity due to impaction 3341 REAL(wp) :: v_in !< deposition velocity due to interception 3342 REAL(wp) :: v_it !< deposition velocity due to turbulent impaction 3343 ! 3344 !-- Initialise 3345 rt = 0.0_wp 3346 St = 0.0_wp 3500 3501 INTEGER(iwp), INTENT(in), OPTIONAL :: l !< index variable for surface facing 3502 3503 LOGICAL, INTENT(in) :: norm !< to normalise or not 3504 3505 REAL(wp) :: alpha !< parameter, Table 3 in Z01 3506 REAL(wp) :: beta_im !< parameter for turbulent impaction 3507 REAL(wp) :: c_brownian_diff !< coefficient for Brownian diffusion 3508 REAL(wp) :: c_impaction !< coefficient for inertial impaction 3509 REAL(wp) :: c_interception !< coefficient for interception 3510 REAL(wp) :: c_turb_impaction !< coefficient for turbulent impaction 3511 REAL(wp) :: depo !< deposition efficiency 3512 REAL(wp) :: gamma !< parameter, Table 3 in Z01 3513 REAL(wp) :: norm_fac !< normalisation factor (usually air density) 3514 REAL(wp) :: par_a !< parameter A for the characteristic radius of collectors, 3515 !< Table 3 in Z01 3516 REAL(wp) :: par_l !< obstacle characteristic dimension in P10 3517 REAL(wp) :: rs !< the overall quasi-laminar resistance for particles 3518 REAL(wp) :: stokes_num !< Stokes number for bluff surface elements 3519 REAL(wp) :: tau_plus !< dimensionless particle relaxation time 3520 REAL(wp) :: v_bd !< deposition velocity due to Brownian diffusion 3521 REAL(wp) :: v_im !< deposition velocity due to impaction 3522 REAL(wp) :: v_in !< deposition velocity due to interception 3523 REAL(wp) :: v_it !< deposition velocity due to turbulent impaction 3524 3525 REAL(wp), DIMENSION(:), INTENT(in) :: kvis !< kinematic viscosity of air (m2/s) 3526 REAL(wp), DIMENSION(:), INTENT(in) :: mag_u !< wind velocity (m/s) 3527 3528 REAL(wp), DIMENSION(:,:), INTENT(in) :: schmidt_num !< particle Schmidt number 3529 REAL(wp), DIMENSION(:,:), INTENT(in) :: vc !< terminal velocity (m/s) 3530 3531 TYPE(surf_type), INTENT(inout) :: surf !< respective surface type 3532 ! 3533 !-- Initialise 3534 rs = 0.0_wp 3535 surf_s = surf%start_index(j,i) 3536 surf_e = surf%end_index(j,i) 3347 3537 tau_plus = 0.0_wp 3348 v_bd = 0.0_wp 3349 v_im = 0.0_wp 3350 v_in = 0.0_wp 3351 v_it = 0.0_wp 3352 surf_s = surf%start_index(j,i) 3353 surf_e = surf%end_index(j,i) 3354 3355 DO m = surf_s, surf_e 3356 k = surf%k(m) 3357 DO b = 1, nbins 3358 IF ( aerosol_number(b)%conc(k,j,i) <= nclim .OR. & 3359 Sc(k+1,b) < 1.0_wp ) CYCLE 3360 3361 IF ( depo_topo_type == 'zhang2001' ) THEN 3362 ! 3363 !-- Parameters for the land use category 'urban' in Table 3 3364 alpha = 1.5_wp 3365 gamma = 0.56_wp 3366 par_A = 10.0E-3_wp 3367 ! 3538 v_bd = 0.0_wp 3539 v_im = 0.0_wp 3540 v_in = 0.0_wp 3541 v_it = 0.0_wp 3542 ! 3543 !-- Model parameters for the land use category. If LSM is applied, import 3544 !-- characteristics. Otherwise, apply surface type "urban". 3545 alpha = alpha_z01(luc_urban) 3546 gamma = gamma_z01(luc_urban) 3547 par_a = A_z01(luc_urban, season) * 1.0E-3_wp 3548 3549 par_l = l_p10(luc_urban) * 0.01_wp 3550 c_brownian_diff = c_b_p10(luc_urban) 3551 c_interception = c_in_p10(luc_urban) 3552 c_impaction = c_im_p10(luc_urban) 3553 beta_im = beta_im_p10(luc_urban) 3554 c_turb_impaction = c_it_p10(luc_urban) 3555 3556 DO m = surf_s, surf_e 3557 k = surf%k(m) 3558 3559 IF ( norm ) THEN 3560 norm_fac = rho_air_zw(k) 3561 IF ( land_surface ) THEN 3562 alpha = alpha_z01( lsm_to_depo_h%match(m) ) 3563 beta_im = beta_im_p10( lsm_to_depo_h%match(m) ) 3564 c_brownian_diff = c_b_p10( lsm_to_depo_h%match(m) ) 3565 c_impaction = c_im_p10( lsm_to_depo_h%match(m) ) 3566 c_interception = c_in_p10( lsm_to_depo_h%match(m) ) 3567 c_turb_impaction = c_it_p10( lsm_to_depo_h%match(m) ) 3568 gamma = gamma_z01( lsm_to_depo_h%match(m) ) 3569 par_a = A_z01( lsm_to_depo_h%match(m), season ) * 1.0E-3_wp 3570 par_l = l_p10( lsm_to_depo_h%match(m) ) * 0.01_wp 3571 ENDIF 3572 ELSE 3573 norm_fac = 0.0_wp 3574 IF ( land_surface ) THEN 3575 alpha = alpha_z01( lsm_to_depo_v(l)%match(m) ) 3576 beta_im = beta_im_p10( lsm_to_depo_v(l)%match(m) ) 3577 c_brownian_diff = c_b_p10( lsm_to_depo_v(l)%match(m) ) 3578 c_impaction = c_im_p10( lsm_to_depo_v(l)%match(m) ) 3579 c_interception = c_in_p10( lsm_to_depo_v(l)%match(m) ) 3580 c_turb_impaction = c_it_p10( lsm_to_depo_v(l)%match(m) ) 3581 gamma = gamma_z01( lsm_to_depo_v(l)%match(m) ) 3582 par_a = A_z01( lsm_to_depo_v(l)%match(m), season ) * 1.0E-3_wp 3583 par_l = l_p10( lsm_to_depo_v(l)%match(m) ) * 0.01_wp 3584 ENDIF 3585 ENDIF 3586 3587 DO ib = 1, nbins_aerosol 3588 IF ( aerosol_number(ib)%conc(k,j,i) <= nclim .OR. schmidt_num(k+1,ib) < 1.0_wp ) CYCLE 3589 3590 IF ( depo_surf_par == 'zhang2001' ) THEN 3591 ! 3368 3592 !-- Stokes number for smooth surfaces or surfaces with bluff roughness 3369 !-- elements (Seinfeld and Pandis, 2nd edition (2006): Eq. 19.23) 3370 St = MAX( 0.01_wp, vc(k+1,b) * surf%us(m) ** 2.0_wp / & 3371 ( g * kvis(k+1) ) ) 3372 ! 3373 !-- The overall quasi-laminar resistance for particles (Eq. 5) 3374 rt = MAX( EPSILON( 1.0_wp ), ( 3.0_wp * surf%us(m) * ( & 3375 Sc(k+1,b)**( -gamma ) + ( St / ( alpha + St ) )**2.0_wp & 3376 + 0.5_wp * ( Ra_dry(k,j,i,b) / par_A )**2.0_wp ) * & 3377 EXP( -St**0.5_wp ) ) ) 3378 depo = vc(k+1,b) + rt 3379 3380 ELSEIF ( depo_topo_type == 'petroff2010' ) THEN 3381 ! 3382 !-- vd = v_BD + v_IN + v_IM + v_IT + vc 3383 !-- Deposition efficiencies from Table 1. Constants from Table 2. 3384 C_Br = 1.262_wp 3385 C_IM = 0.130_wp 3386 C_IN = 0.216_wp 3387 C_IT = 0.056_wp 3388 par_A = 0.03_wp ! Here: leaf width (m) 3389 ! 3593 !-- elements (Seinfeld and Pandis, 2nd edition (2006): Eq. 19.23) 3594 stokes_num = MAX( 0.01_wp, vc(k+1,ib) * surf%us(m)**2 / ( g * kvis(k+1) ) ) 3595 ! 3596 !-- The overall quasi-laminar resistance for particles (Eq. 5) 3597 rs = MAX( EPSILON( 1.0_wp ), ( 3.0_wp * surf%us(m) * ( schmidt_num(k+1,ib)**( -gamma )& 3598 + ( stokes_num / ( alpha + stokes_num ) )**2 + 0.5_wp * ( ra_dry(k,j,i,ib) /& 3599 par_a )**2 ) * EXP( -stokes_num**0.5_wp ) ) ) 3600 depo = vc(k+1,ib) + rs 3601 3602 ELSEIF ( depo_surf_par == 'petroff2010' ) THEN 3603 ! 3604 !-- vd = v_BD + v_IN + v_IM + v_IT + vc 3605 ! 3390 3606 !-- Stokes number for smooth surfaces or surfaces with bluff roughness 3391 !-- elements (Seinfeld and Pandis, 2nd edition (2006): Eq. 19.23) 3392 St = MAX( 0.01_wp, vc(k+1,b) * surf%us(m) ** 2.0_wp / & 3393 ( g * kvis(k+1) ) ) 3607 !-- elements (Seinfeld and Pandis, 2nd edition (2006): Eq. 19.23) 3608 stokes_num = MAX( 0.01_wp, vc(k+1,ib) * surf%us(m)**2 / ( g * kvis(k+1) ) ) 3394 3609 ! 3395 3610 !-- Non-dimensional relexation time of the particle on top of canopy 3396 tau_plus = vc(k+1, b) * surf%us(m)**2.0_wp / ( kvis(k+1) * g )3611 tau_plus = vc(k+1,ib) * surf%us(m)**2 / ( kvis(k+1) * g ) 3397 3612 ! 3398 3613 !-- Brownian diffusion 3399 v_bd = mag_u(k+1) * C_Br * Sc(k+1,b)**( -2.0_wp / 3.0_wp ) *&3400 ( mag_u(k+1) * par_ A/ kvis(k+1) )**( -0.5_wp )3614 v_bd = mag_u(k+1) * c_brownian_diff * schmidt_num(k+1,ib)**( -0.666666_wp ) * & 3615 ( mag_u(k+1) * par_l / kvis(k+1) )**( -0.5_wp ) 3401 3616 ! 3402 3617 !-- Interception 3403 v_in = mag_u(k+1) * C_IN * Ra_dry(k,j,i,b)/ par_A * ( 2.0_wp +&3404 LOG( 2.0_wp * par_A / Ra_dry(k,j,i,b) ) )3618 v_in = mag_u(k+1) * c_interception * ra_dry(k,j,i,ib)/ par_l * & 3619 ( 2.0_wp + LOG( 2.0_wp * par_l / ra_dry(k,j,i,ib) ) ) 3405 3620 ! 3406 3621 !-- Impaction: Petroff (2009) Eq. 18 3407 v_im = mag_u(k+1) * C_IM * ( St / ( St + 0.47_wp ) )**2.0_wp3408 3622 v_im = mag_u(k+1) * c_impaction * ( stokes_num / ( stokes_num + beta_im ) )**2 3623 3409 3624 IF ( tau_plus < 20.0_wp ) THEN 3410 v_it = 2.5E-3_wp * C_IT * tau_plus**2.0_wp3625 v_it = 2.5E-3_wp * c_turb_impaction * tau_plus**2 3411 3626 ELSE 3412 v_it = C_IT3627 v_it = c_turb_impaction 3413 3628 ENDIF 3414 depo = v_bd + v_in + v_im + v_it + vc(k+1, b)3415 3629 depo = v_bd + v_in + v_im + v_it + vc(k+1,ib) 3630 3416 3631 ENDIF 3417 IF ( lod_aero == 3 .OR. salsa_source_mode == 'no_source' ) THEN 3418 surf%answs(m,b) = -depo * norm(k) * aerosol_number(b)%conc(k,j,i) 3419 DO c = 1, ncc_tot 3420 surf%amsws(m,(c-1)*nbins+b) = -depo * norm(k) * & 3421 aerosol_mass((c-1)*nbins+b)%conc(k,j,i) 3422 ENDDO ! c 3632 ! 3633 !-- Calculate changes in surface fluxes due to dry deposition 3634 IF ( aero_emission_att%lod == 2 .OR. salsa_emission_mode == 'no_emission' ) THEN 3635 surf%answs(m,ib) = -depo * norm_fac * aerosol_number(ib)%conc(k,j,i) 3636 DO ic = 1, ncomponents_mass 3637 icc = ( ic - 1 ) * nbins_aerosol + ib 3638 surf%amsws(m,icc) = -depo * norm_fac * aerosol_mass(icc)%conc(k,j,i) 3639 ENDDO ! ic 3423 3640 ELSE 3424 surf%answs(m,b) = SUM( aerosol_number(b)%source(:,j,i) ) - & 3425 MAX( 0.0_wp, depo * norm(k) * & 3426 aerosol_number(b)%conc(k,j,i) ) 3427 DO c = 1, ncc_tot 3428 surf%amsws(m,(c-1)*nbins+b) = SUM( & 3429 aerosol_mass((c-1)*nbins+b)%source(:,j,i) ) - & 3430 MAX( 0.0_wp, depo * norm(k) * & 3431 aerosol_mass((c-1)*nbins+b)%conc(k,j,i) ) 3432 ENDDO 3641 surf%answs(m,ib) = aerosol_number(ib)%source(j,i) - & 3642 MAX( 0.0_wp, depo * norm_fac * aerosol_number(ib)%conc(k,j,i) ) 3643 DO ic = 1, ncomponents_mass 3644 icc = ( ic - 1 ) * nbins_aerosol + ib 3645 surf%amsws(m,icc) = aerosol_mass(icc)%source(j,i) - & 3646 MAX( 0.0_wp, depo * norm_fac * aerosol_mass(icc)%conc(k,j,i) ) 3647 ENDDO ! ic 3433 3648 ENDIF 3434 ENDDO ! b3435 ENDDO ! m 3436 3437 END SUBROUTINE depo_ topo3438 3649 ENDDO ! ib 3650 ENDDO ! m 3651 3652 END SUBROUTINE depo_surf 3653 3439 3654 !------------------------------------------------------------------------------! 3440 3655 ! Description: … … 3443 3658 !------------------------------------------------------------------------------! 3444 3659 REAL(wp) FUNCTION terminal_vel( radius, rhop, rhoa, visc, beta ) 3445 3660 3446 3661 IMPLICIT NONE 3447 3662 3448 3663 REAL(wp), INTENT(in) :: beta !< Cunningham correction factor 3449 3664 REAL(wp), INTENT(in) :: radius !< particle radius (m) … … 3451 3666 REAL(wp), INTENT(in) :: rhoa !< air density (kg/m3) 3452 3667 REAL(wp), INTENT(in) :: visc !< molecular viscosity of air (kg/(m*s)) 3453 3668 3454 3669 ! 3455 3670 !-- Stokes law with Cunningham slip correction factor 3456 terminal_vel = ( 4.0_wp * radius**2.0_wp ) * ( rhop - rhoa ) * g * beta / & 3457 ( 18.0_wp * visc ) ! (m/s) 3458 3671 terminal_vel = 4.0_wp * radius**2 * ( rhop - rhoa ) * g * beta / ( 18.0_wp * visc ) ! (m/s) 3672 3459 3673 END FUNCTION terminal_vel 3460 3674 3461 3675 !------------------------------------------------------------------------------! 3462 3676 ! Description: … … 3498 3712 !------------------------------------------------------------------------------! 3499 3713 SUBROUTINE coagulation( paero, ptstep, ptemp, ppres ) 3500 3714 3501 3715 IMPLICIT NONE 3502 3503 !-- Input and output variables 3504 TYPE(t_section), INTENT(inout) :: paero(fn2b) !< Aerosol properties 3505 REAL(wp), INTENT(in) :: ppres !< ambient pressure (Pa) 3506 REAL(wp), INTENT(in) :: ptemp !< ambient temperature (K) 3507 REAL(wp), INTENT(in) :: ptstep !< time step (s) 3508 !-- Local variables 3716 3509 3717 INTEGER(iwp) :: index_2a !< corresponding bin in subrange 2a 3510 3718 INTEGER(iwp) :: index_2b !< corresponding bin in subrange 2b 3511 INTEGER(iwp) :: b !< loop index 3512 INTEGER(iwp) :: ll !< loop index 3513 INTEGER(iwp) :: mm !< loop index 3514 INTEGER(iwp) :: nn !< loop index 3515 REAL(wp) :: pressi !< pressure 3516 REAL(wp) :: temppi !< temperature 3517 REAL(wp) :: zcc(fn2b,fn2b) !< updated coagulation coefficients (m3/s) 3518 REAL(wp) :: zdpart_mm !< diameter of particle (m) 3519 REAL(wp) :: zdpart_nn !< diameter of particle (m) 3520 REAL(wp) :: zminusterm !< coagulation loss in a bin (1/s) 3521 REAL(wp) :: zplusterm(8) !< coagulation gain in a bin (fxm/s) 3522 !< (for each chemical compound) 3523 REAL(wp) :: zmpart(fn2b) !< approximate mass of particles (kg) 3524 3525 zcc = 0.0_wp 3526 zmpart = 0.0_wp 3719 INTEGER(iwp) :: ib !< loop index 3720 INTEGER(iwp) :: ll !< loop index 3721 INTEGER(iwp) :: mm !< loop index 3722 INTEGER(iwp) :: nn !< loop index 3723 3724 REAL(wp) :: pressi !< pressure 3725 REAL(wp) :: temppi !< temperature 3726 REAL(wp) :: zdpart_mm !< diameter of particle (m) 3727 REAL(wp) :: zdpart_nn !< diameter of particle (m) 3728 REAL(wp) :: zminusterm !< coagulation loss in a bin (1/s) 3729 3730 REAL(wp), INTENT(in) :: ppres !< ambient pressure (Pa) 3731 REAL(wp), INTENT(in) :: ptemp !< ambient temperature (K) 3732 REAL(wp), INTENT(in) :: ptstep !< time step (s) 3733 3734 REAL(wp), DIMENSION(nbins_aerosol) :: zmpart !< approximate mass of particles (kg) 3735 REAL(wp), DIMENSION(maxspec+1) :: zplusterm !< coagulation gain in a bin (for each 3736 !< chemical compound) 3737 REAL(wp), DIMENSION(nbins_aerosol,nbins_aerosol) :: zcc !< updated coagulation coefficients (m3/s) 3738 3739 TYPE(t_section), DIMENSION(nbins_aerosol), INTENT(inout) :: paero !< Aerosol properties 3740 3527 3741 zdpart_mm = 0.0_wp 3528 3742 zdpart_nn = 0.0_wp … … 3533 3747 3534 3748 !-- 2) Updating coagulation coefficients 3535 ! 3749 ! 3536 3750 !-- Aerosol mass (kg). Density of 1500 kg/m3 assumed 3537 zmpart(1: fn2b) = api6 * ( MIN( paero(1:fn2b)%dwet, 30.0E-6_wp )**3.0_wp )&3538 * 1500.0_wp3751 zmpart(1:end_subrange_2b) = api6 * ( MIN( paero(1:end_subrange_2b)%dwet, 30.0E-6_wp )**3 ) & 3752 * 1500.0_wp 3539 3753 temppi = ptemp 3540 3754 pressi = ppres … … 3542 3756 ! 3543 3757 !-- Aero-aero coagulation 3544 DO mm = 1, fn2b ! smaller colliding particle3758 DO mm = 1, end_subrange_2b ! smaller colliding particle 3545 3759 IF ( paero(mm)%numc < nclim ) CYCLE 3546 DO nn = mm, fn2b ! larger colliding particle3760 DO nn = mm, end_subrange_2b ! larger colliding particle 3547 3761 IF ( paero(nn)%numc < nclim ) CYCLE 3548 3762 3549 3763 zdpart_mm = MIN( paero(mm)%dwet, 30.0E-6_wp ) ! Limit to 30 um 3550 3764 zdpart_nn = MIN( paero(nn)%dwet, 30.0E-6_wp ) ! Limit to 30 um 3551 ! 3765 ! 3552 3766 !-- Coagulation coefficient of particles (m3/s) 3553 zcc(mm,nn) = coagc( zdpart_mm, zdpart_nn, zmpart(mm), zmpart(nn), & 3554 temppi, pressi ) 3767 zcc(mm,nn) = coagc( zdpart_mm, zdpart_nn, zmpart(mm), zmpart(nn), temppi, pressi ) 3555 3768 zcc(nn,mm) = zcc(mm,nn) 3556 3769 ENDDO 3557 3770 ENDDO 3558 3559 ! 3771 3772 ! 3560 3773 !-- 3) New particle and volume concentrations after coagulation: 3561 3774 !-- Calculated according to Jacobson (2005) eq. 15.9 3562 3775 ! 3563 3776 !-- Aerosols in subrange 1a: 3564 DO b = in1a, fn1a3565 IF ( paero( b)%numc < nclim ) CYCLE3777 DO ib = start_subrange_1a, end_subrange_1a 3778 IF ( paero(ib)%numc < nclim ) CYCLE 3566 3779 zminusterm = 0.0_wp 3567 3780 zplusterm(:) = 0.0_wp 3568 ! 3781 ! 3569 3782 !-- Particles lost by coagulation with larger aerosols 3570 DO ll = b+1, fn2b3571 zminusterm = zminusterm + zcc( b,ll) * paero(ll)%numc3783 DO ll = ib+1, end_subrange_2b 3784 zminusterm = zminusterm + zcc(ib,ll) * paero(ll)%numc 3572 3785 ENDDO 3573 ! 3786 ! 3574 3787 !-- Coagulation gain in a bin: change in volume conc. (cm3/cm3): 3575 DO ll = in1a, b-13576 zplusterm(1:2) = zplusterm(1:2) + zcc(ll, b) * paero(ll)%volc(1:2)3577 zplusterm(6:7) = zplusterm(6:7) + zcc(ll, b) * paero(ll)%volc(6:7)3578 zplusterm(8) = zplusterm(8) + zcc(ll, b) * paero(ll)%volc(8)3788 DO ll = start_subrange_1a, ib - 1 3789 zplusterm(1:2) = zplusterm(1:2) + zcc(ll,ib) * paero(ll)%volc(1:2) 3790 zplusterm(6:7) = zplusterm(6:7) + zcc(ll,ib) * paero(ll)%volc(6:7) 3791 zplusterm(8) = zplusterm(8) + zcc(ll,ib) * paero(ll)%volc(8) 3579 3792 ENDDO 3580 ! 3793 ! 3581 3794 !-- Volume and number concentrations after coagulation update [fxm] 3582 paero(b)%volc(1:2) = ( paero(b)%volc(1:2) + ptstep * zplusterm(1:2) * & 3583 paero(b)%numc ) / ( 1.0_wp + ptstep * zminusterm ) 3584 paero(b)%volc(6:7) = ( paero(b)%volc(6:7) + ptstep * zplusterm(6:7) * & 3585 paero(b)%numc ) / ( 1.0_wp + ptstep * zminusterm ) 3586 paero(b)%volc(8) = ( paero(b)%volc(8) + ptstep * zplusterm(8) * & 3587 paero(b)%numc ) / ( 1.0_wp + ptstep * zminusterm ) 3588 paero(b)%numc = paero(b)%numc / ( 1.0_wp + ptstep * zminusterm + & 3589 0.5_wp * ptstep * zcc(b,b) * paero(b)%numc ) 3795 paero(ib)%volc(1:2) = ( paero(ib)%volc(1:2) + ptstep * zplusterm(1:2) * paero(ib)%numc ) / & 3796 ( 1.0_wp + ptstep * zminusterm ) 3797 paero(ib)%volc(6:8) = ( paero(ib)%volc(6:8) + ptstep * zplusterm(6:8) * paero(ib)%numc ) / & 3798 ( 1.0_wp + ptstep * zminusterm ) 3799 paero(ib)%numc = paero(ib)%numc / ( 1.0_wp + ptstep * zminusterm + 0.5_wp * ptstep * & 3800 zcc(ib,ib) * paero(ib)%numc ) 3590 3801 ENDDO 3591 ! 3802 ! 3592 3803 !-- Aerosols in subrange 2a: 3593 DO b = in2a, fn2a3594 IF ( paero( b)%numc < nclim ) CYCLE3804 DO ib = start_subrange_2a, end_subrange_2a 3805 IF ( paero(ib)%numc < nclim ) CYCLE 3595 3806 zminusterm = 0.0_wp 3596 3807 zplusterm(:) = 0.0_wp 3597 ! 3808 ! 3598 3809 !-- Find corresponding size bin in subrange 2b 3599 index_2b = b - in2a + in2b3600 ! 3810 index_2b = ib - start_subrange_2a + start_subrange_2b 3811 ! 3601 3812 !-- Particles lost by larger particles in 2a 3602 DO ll = b+1, fn2a3603 zminusterm = zminusterm + zcc( b,ll) * paero(ll)%numc3813 DO ll = ib+1, end_subrange_2a 3814 zminusterm = zminusterm + zcc(ib,ll) * paero(ll)%numc 3604 3815 ENDDO 3605 ! 3816 ! 3606 3817 !-- Particles lost by larger particles in 2b 3607 3818 IF ( .NOT. no_insoluble ) THEN 3608 DO ll = index_2b+1, fn2b3609 zminusterm = zminusterm + zcc( b,ll) * paero(ll)%numc3819 DO ll = index_2b+1, end_subrange_2b 3820 zminusterm = zminusterm + zcc(ib,ll) * paero(ll)%numc 3610 3821 ENDDO 3611 3822 ENDIF 3612 ! 3823 ! 3613 3824 !-- Particle volume gained from smaller particles in subranges 1, 2a and 2b 3614 DO ll = in1a, b-1 3615 zplusterm(1:2) = zplusterm(1:2) + zcc(ll,b) * paero(ll)%volc(1:2) 3616 zplusterm(6:7) = zplusterm(6:7) + zcc(ll,b) * paero(ll)%volc(6:7) 3617 zplusterm(8) = zplusterm(8) + zcc(ll,b) * paero(ll)%volc(8) 3618 ENDDO 3619 ! 3825 DO ll = start_subrange_1a, ib-1 3826 zplusterm(1:2) = zplusterm(1:2) + zcc(ll,ib) * paero(ll)%volc(1:2) 3827 zplusterm(6:8) = zplusterm(6:8) + zcc(ll,ib) * paero(ll)%volc(6:8) 3828 ENDDO 3829 ! 3620 3830 !-- Particle volume gained from smaller particles in 2a 3621 3831 !-- (Note, for components not included in the previous loop!) 3622 DO ll = in2a,b-13623 zplusterm(3:5) = zplusterm(3:5) + zcc(ll, b)*paero(ll)%volc(3:5)3832 DO ll = start_subrange_2a, ib-1 3833 zplusterm(3:5) = zplusterm(3:5) + zcc(ll,ib)*paero(ll)%volc(3:5) 3624 3834 ENDDO 3625 3626 ! 3835 ! 3627 3836 !-- Particle volume gained from smaller (and equal) particles in 2b 3628 3837 IF ( .NOT. no_insoluble ) THEN 3629 DO ll = in2b, index_2b3630 zplusterm(1:8) = zplusterm(1:8) + zcc(ll, b) * paero(ll)%volc(1:8)3838 DO ll = start_subrange_2b, index_2b 3839 zplusterm(1:8) = zplusterm(1:8) + zcc(ll,ib) * paero(ll)%volc(1:8) 3631 3840 ENDDO 3632 3841 ENDIF 3633 ! 3842 ! 3634 3843 !-- Volume and number concentrations after coagulation update [fxm] 3635 paero( b)%volc(1:8) = ( paero(b)%volc(1:8) + ptstep * zplusterm(1:8) *&3636 paero(b)%numc ) /( 1.0_wp + ptstep * zminusterm )3637 paero( b)%numc = paero(b)%numc / ( 1.0_wp + ptstep * zminusterm +&3638 0.5_wp * ptstep * zcc(b,b) * paero(b)%numc )3844 paero(ib)%volc(1:8) = ( paero(ib)%volc(1:8) + ptstep * zplusterm(1:8) * paero(ib)%numc ) / & 3845 ( 1.0_wp + ptstep * zminusterm ) 3846 paero(ib)%numc = paero(ib)%numc / ( 1.0_wp + ptstep * zminusterm + 0.5_wp * ptstep * & 3847 zcc(ib,ib) * paero(ib)%numc ) 3639 3848 ENDDO 3640 ! 3849 ! 3641 3850 !-- Aerosols in subrange 2b: 3642 3851 IF ( .NOT. no_insoluble ) THEN 3643 DO b = in2b, fn2b3644 IF ( paero( b)%numc < nclim ) CYCLE3852 DO ib = start_subrange_2b, end_subrange_2b 3853 IF ( paero(ib)%numc < nclim ) CYCLE 3645 3854 zminusterm = 0.0_wp 3646 3855 zplusterm(:) = 0.0_wp 3647 ! 3856 ! 3648 3857 !-- Find corresponding size bin in subsubrange 2a 3649 index_2a = b - in2b + in2a3650 ! 3858 index_2a = ib - start_subrange_2b + start_subrange_2a 3859 ! 3651 3860 !-- Particles lost to larger particles in subranges 2b 3652 DO ll = b+1, fn2b3653 zminusterm = zminusterm + zcc( b,ll) * paero(ll)%numc3861 DO ll = ib + 1, end_subrange_2b 3862 zminusterm = zminusterm + zcc(ib,ll) * paero(ll)%numc 3654 3863 ENDDO 3655 ! 3864 ! 3656 3865 !-- Particles lost to larger and equal particles in 2a 3657 DO ll = index_2a, fn2a3658 zminusterm = zminusterm + zcc( b,ll) * paero(ll)%numc3866 DO ll = index_2a, end_subrange_2a 3867 zminusterm = zminusterm + zcc(ib,ll) * paero(ll)%numc 3659 3868 ENDDO 3660 ! 3869 ! 3661 3870 !-- Particle volume gained from smaller particles in subranges 1 & 2a 3662 DO ll = in1a, index_2a-13663 zplusterm(1:8) = zplusterm(1:8) + zcc(ll, b) * paero(ll)%volc(1:8)3871 DO ll = start_subrange_1a, index_2a - 1 3872 zplusterm(1:8) = zplusterm(1:8) + zcc(ll,ib) * paero(ll)%volc(1:8) 3664 3873 ENDDO 3665 ! 3874 ! 3666 3875 !-- Particle volume gained from smaller particles in 2b 3667 DO ll = in2b, b-13668 zplusterm(1:8) = zplusterm(1:8) + zcc(ll, b) * paero(ll)%volc(1:8)3876 DO ll = start_subrange_2b, ib - 1 3877 zplusterm(1:8) = zplusterm(1:8) + zcc(ll,ib) * paero(ll)%volc(1:8) 3669 3878 ENDDO 3670 ! 3879 ! 3671 3880 !-- Volume and number concentrations after coagulation update [fxm] 3672 paero( b)%volc(1:8) = ( paero(b)%volc(1:8) + ptstep * zplusterm(1:8)&3673 * paero(b)%numc )/ ( 1.0_wp + ptstep * zminusterm )3674 paero( b)%numc = paero(b)%numc / ( 1.0_wp + ptstep * zminusterm +&3675 0.5_wp * ptstep * zcc(b,b) * paero(b)%numc )3881 paero(ib)%volc(1:8) = ( paero(ib)%volc(1:8) + ptstep * zplusterm(1:8) * paero(ib)%numc ) & 3882 / ( 1.0_wp + ptstep * zminusterm ) 3883 paero(ib)%numc = paero(ib)%numc / ( 1.0_wp + ptstep * zminusterm + 0.5_wp * ptstep * & 3884 zcc(ib,ib) * paero(ib)%numc ) 3676 3885 ENDDO 3677 3886 ENDIF … … 3682 3891 ! Description: 3683 3892 ! ------------ 3684 !> Calculation of coagulation coefficients. Extended version of the function 3685 !> originally found in mo_salsa_init. 3686 ! 3687 !> J. Tonttila, FMI, 05/2014 3688 !------------------------------------------------------------------------------! 3893 !> Calculation of coagulation coefficients. Extended version of the function 3894 !> originally found in mo_salsa_init. 3895 ! 3896 !> J. Tonttila, FMI, 05/2014 3897 !------------------------------------------------------------------------------! 3689 3898 REAL(wp) FUNCTION coagc( diam1, diam2, mass1, mass2, temp, pres ) 3690 3899 3691 3900 IMPLICIT NONE 3692 ! 3693 !-- Input and output variables 3694 REAL(wp), INTENT(in) :: diam1 !< diameter of colliding particle 1 (m) 3695 REAL(wp), INTENT(in) :: diam2 !< diameter of colliding particle 2 (m) 3696 REAL(wp), INTENT(in) :: mass1 !< mass of colliding particle 1 (kg) 3697 REAL(wp), INTENT(in) :: mass2 !< mass of colliding particle 2 (kg) 3698 REAL(wp), INTENT(in) :: pres !< ambient pressure (Pa?) [fxm] 3699 REAL(wp), INTENT(in) :: temp !< ambient temperature (K) 3700 ! 3701 !-- Local variables 3702 REAL(wp) :: fmdist !< distance of flux matching (m) 3703 REAL(wp) :: knud_p !< particle Knudsen number 3704 REAL(wp) :: mdiam !< mean diameter of colliding particles (m) 3705 REAL(wp) :: mfp !< mean free path of air molecules (m) 3706 REAL(wp) :: visc !< viscosity of air (kg/(m s)) 3707 REAL(wp), DIMENSION (2) :: beta !< Cunningham correction factor 3708 REAL(wp), DIMENSION (2) :: dfpart !< particle diffusion coefficient 3709 !< (m2/s) 3710 REAL(wp), DIMENSION (2) :: diam !< diameters of particles (m) 3711 REAL(wp), DIMENSION (2) :: flux !< flux in continuum and free molec. 3712 !< regime (m/s) 3713 REAL(wp), DIMENSION (2) :: knud !< particle Knudsen number 3714 REAL(wp), DIMENSION (2) :: mpart !< masses of particles (kg) 3715 REAL(wp), DIMENSION (2) :: mtvel !< particle mean thermal velocity (m/s) 3716 REAL(wp), DIMENSION (2) :: omega !< particle mean free path 3717 REAL(wp), DIMENSION (2) :: tva !< temporary variable (m) 3901 3902 REAL(wp) :: fmdist !< distance of flux matching (m) 3903 REAL(wp) :: knud_p !< particle Knudsen number 3904 REAL(wp) :: mdiam !< mean diameter of colliding particles (m) 3905 REAL(wp) :: mfp !< mean free path of air molecules (m) 3906 REAL(wp) :: visc !< viscosity of air (kg/(m s)) 3907 3908 REAL(wp), INTENT(in) :: diam1 !< diameter of colliding particle 1 (m) 3909 REAL(wp), INTENT(in) :: diam2 !< diameter of colliding particle 2 (m) 3910 REAL(wp), INTENT(in) :: mass1 !< mass of colliding particle 1 (kg) 3911 REAL(wp), INTENT(in) :: mass2 !< mass of colliding particle 2 (kg) 3912 REAL(wp), INTENT(in) :: pres !< ambient pressure (Pa?) [fxm] 3913 REAL(wp), INTENT(in) :: temp !< ambient temperature (K) 3914 3915 REAL(wp), DIMENSION (2) :: beta !< Cunningham correction factor 3916 REAL(wp), DIMENSION (2) :: dfpart !< particle diffusion coefficient (m2/s) 3917 REAL(wp), DIMENSION (2) :: diam !< diameters of particles (m) 3918 REAL(wp), DIMENSION (2) :: flux !< flux in continuum and free molec. regime (m/s) 3919 REAL(wp), DIMENSION (2) :: knud !< particle Knudsen number 3920 REAL(wp), DIMENSION (2) :: mpart !< masses of particles (kg) 3921 REAL(wp), DIMENSION (2) :: mtvel !< particle mean thermal velocity (m/s) 3922 REAL(wp), DIMENSION (2) :: omega !< particle mean free path 3923 REAL(wp), DIMENSION (2) :: tva !< temporary variable (m) 3718 3924 ! 3719 3925 !-- Initialisation … … 3723 3929 diam = (/ diam1, diam2 /) !< particle diameters (m) 3724 3930 mpart = (/ mass1, mass2 /) !< particle masses (kg) 3725 !-- Viscosity of air (kg/(m s)) 3726 visc = ( 7.44523E-3_wp * temp ** 1.5_wp ) / & 3727 ( 5093.0_wp * ( temp + 110.4_wp ) ) 3728 !-- Mean free path of air (m) 3931 ! 3932 !-- Viscosity of air (kg/(m s)) 3933 visc = ( 7.44523E-3_wp * temp ** 1.5_wp ) / ( 5093.0_wp * ( temp + 110.4_wp ) ) 3934 ! 3935 !-- Mean free path of air (m) 3729 3936 mfp = ( 1.656E-10_wp * temp + 1.828E-8_wp ) * ( p_0 + 1325.0_wp ) / pres 3730 3937 ! 3731 3938 !-- 2) Slip correction factor for small particles 3732 3939 knud = 2.0_wp * EXP( LOG(mfp) - LOG(diam) )! Knudsen number for air (15.23) 3733 !-- Cunningham correction factor (Allen and Raabe, Aerosol Sci. Tech. 4, 269) 3940 ! 3941 !-- Cunningham correction factor (Allen and Raabe, Aerosol Sci. Tech. 4, 269) 3734 3942 beta = 1.0_wp + knud * ( 1.142_wp + 0.558_wp * EXP( -0.999_wp / knud ) ) 3735 3943 ! 3736 3944 !-- 3) Particle properties 3737 3945 !-- Diffusion coefficient (m2/s) (Jacobson (2005) eq. 15.29) 3738 dfpart = beta * abo * temp / ( 3.0_wp * pi * visc * diam ) 3946 dfpart = beta * abo * temp / ( 3.0_wp * pi * visc * diam ) 3947 ! 3739 3948 !-- Mean thermal velocity (m/s) (Jacobson (2005) eq. 15.32) 3740 3949 mtvel = SQRT( ( 8.0_wp * abo * temp ) / ( pi * mpart ) ) 3950 ! 3741 3951 !-- Particle mean free path (m) (Jacobson (2005) eq. 15.34 ) 3742 omega = 8.0_wp * dfpart / ( pi * mtvel ) 3952 omega = 8.0_wp * dfpart / ( pi * mtvel ) 3953 ! 3743 3954 !-- Mean diameter (m) 3744 3955 mdiam = 0.5_wp * ( diam(1) + diam(2) ) 3745 3956 ! 3746 !-- 4) Calculation of fluxes (Brownian collision kernels) and flux matching 3957 !-- 4) Calculation of fluxes (Brownian collision kernels) and flux matching 3747 3958 !-- following Jacobson (2005): 3959 ! 3748 3960 !-- Flux in continuum regime (m3/s) (eq. 15.28) 3749 3961 flux(1) = 4.0_wp * pi * mdiam * ( dfpart(1) + dfpart(2) ) 3962 ! 3750 3963 !-- Flux in free molec. regime (m3/s) (eq. 15.31) 3751 flux(2) = pi * SQRT( ( mtvel(1)**2 .0_wp ) + ( mtvel(2)**2.0_wp ) ) * &3752 ( mdiam**2.0_wp ) 3964 flux(2) = pi * SQRT( ( mtvel(1)**2 ) + ( mtvel(2)**2 ) ) * ( mdiam**2 ) 3965 ! 3753 3966 !-- temporary variables (m) to calculate flux matching distance (m) 3754 tva(1) = ( ( mdiam + omega(1) )**3.0_wp - ( mdiam**2.0_wp + & 3755 omega(1)**2.0_wp ) * SQRT( ( mdiam**2.0_wp + omega(1)**2.0_wp ) & 3756 ) ) / ( 3.0_wp * mdiam * omega(1) ) - mdiam 3757 tva(2) = ( ( mdiam + omega(2) )**3.0_wp - ( mdiam**2.0_wp + & 3758 omega(2)**2.0_wp ) * SQRT( ( mdiam**2 + omega(2)**2 ) ) ) / & 3759 ( 3.0_wp * mdiam * omega(2) ) - mdiam 3760 !-- Flux matching distance (m) i.e. the mean distance from the centre of a 3761 !-- sphere reached by particles leaving sphere's surface and travelling a 3762 !-- distance of particle mean free path mfp (eq. 15 34) 3763 fmdist = SQRT( tva(1)**2 + tva(2)**2.0_wp) 3764 ! 3765 !-- 5) Coagulation coefficient (m3/s) (eq. 15.33). Here assumed 3766 !-- coalescence efficiency 1!! 3767 coagc = flux(1) / ( mdiam / ( mdiam + fmdist) + flux(1) / flux(2) ) 3768 !-- coagulation coefficient = coalescence efficiency * collision kernel 3769 ! 3770 !-- Corrected collision kernel following Karl et al., 2016 (ACP): 3771 !-- Inclusion of van der Waals and viscous forces 3967 tva(1) = ( ( mdiam + omega(1) )**3 - ( mdiam**2 + omega(1)**2 ) * SQRT( ( mdiam**2 + & 3968 omega(1)**2 ) ) ) / ( 3.0_wp * mdiam * omega(1) ) - mdiam 3969 tva(2) = ( ( mdiam + omega(2) )**3 - ( mdiam**2 + omega(2)**2 ) * SQRT( ( mdiam**2 + & 3970 omega(2)**2 ) ) ) / ( 3.0_wp * mdiam * omega(2) ) - mdiam 3971 ! 3972 !-- Flux matching distance (m): the mean distance from the centre of a sphere reached by particles 3973 !-- that leave sphere's surface and travel a distance of particle mean free path (eq. 15.34) 3974 fmdist = SQRT( tva(1)**2 + tva(2)**2 ) 3975 ! 3976 !-- 5) Coagulation coefficient = coalescence efficiency * collision kernel (m3/s) (eq. 15.33). 3977 !-- Here assumed coalescence efficiency 1!! 3978 coagc = flux(1) / ( mdiam / ( mdiam + fmdist) + flux(1) / flux(2) ) 3979 ! 3980 !-- Corrected collision kernel (Karl et al., 2016 (ACP)): Include van der Waals and viscous forces 3772 3981 IF ( van_der_waals_coagc ) THEN 3773 knud_p = SQRT( omega(1)**2 + omega(2)**2 ) / mdiam 3982 knud_p = SQRT( omega(1)**2 + omega(2)**2 ) / mdiam 3774 3983 IF ( knud_p >= 0.1_wp .AND. knud_p <= 10.0_wp ) THEN 3775 3984 coagc = coagc * ( 2.0_wp + 0.4_wp * LOG( knud_p ) ) … … 3778 3987 ENDIF 3779 3988 ENDIF 3780 3989 3781 3990 END FUNCTION coagc 3782 3783 !------------------------------------------------------------------------------! 3991 3992 !------------------------------------------------------------------------------! 3784 3993 ! Description: 3785 3994 ! ------------ … … 3799 4008 !> D = {1.d-7*sqrt(1/M_air + 1/M_gas)*T^1.75} / & 3800 4009 ! {p_atm/p_stand * (d_air^(1/3) + d_gas^(1/3))^2 } 3801 ! M_air = 28.965 : molar mass of air (g/mol)3802 ! d_air = 19.70 : diffusion volume of air3803 ! M_h2so4 = 98.08 : molar mass of h2so4 (g/mol)3804 ! d_h2so4 = 51.96 : diffusion volume of h2so44010 !> M_air = 28.965 : molar mass of air (g/mol) 4011 !> d_air = 19.70 : diffusion volume of air 4012 !> M_h2so4 = 98.08 : molar mass of h2so4 (g/mol) 4013 !> d_h2so4 = 51.96 : diffusion volume of h2so4 3805 4014 ! 3806 4015 !> Called from main aerosol model 3807 ! 3808 !> fxm: calculated for empty bins too 3809 !> fxm: same diffusion coefficients and mean free paths used for sulphuric acid 3810 !> and organic vapours (average values? 'real' values for each?) 3811 !> fxm: one should really couple with vapour production and loss terms as well 3812 !> should nucleation be coupled here as well???? 3813 ! 3814 ! Coded by: 3815 ! Hannele Korhonen (FMI) 2005 3816 ! Harri Kokkola (FMI) 2006 3817 ! Juha Tonttila (FMI) 2014 3818 ! Rewritten to PALM by Mona Kurppa (UHel) 2017 3819 !------------------------------------------------------------------------------! 3820 SUBROUTINE condensation( paero, pcsa, pcocnv, pcocsv, pchno3, pcnh3, pcw, pcs,& 3821 ptemp, ppres, ptstep, prtcl ) 3822 4016 !> For equations, see Jacobson, Fundamentals of Atmospheric Modeling, 2nd Edition (2005) 4017 ! 4018 !> Coded by: 4019 !> Hannele Korhonen (FMI) 2005 4020 !> Harri Kokkola (FMI) 2006 4021 !> Juha Tonttila (FMI) 2014 4022 !> Rewritten to PALM by Mona Kurppa (UHel) 2017 4023 !------------------------------------------------------------------------------! 4024 SUBROUTINE condensation( paero, pc_sa, pc_ocnv, pcocsv, pchno3, pc_nh3, pcw, pcs, ptemp, ppres, & 4025 ptstep, prtcl ) 4026 3823 4027 IMPLICIT NONE 3824 3825 !-- Input and output variables 3826 REAL(wp), INTENT(IN) :: ppres !< ambient pressure (Pa) 3827 REAL(wp), INTENT(IN) :: pcs !< Water vapour saturation concentration 3828 !< (kg/m3) 3829 REAL(wp), INTENT(IN) :: ptemp !< ambient temperature (K) 3830 REAL(wp), INTENT(IN) :: ptstep !< timestep (s) 3831 TYPE(component_index), INTENT(in) :: prtcl !< Keeps track which substances 3832 !< are used 3833 REAL(wp), INTENT(INOUT) :: pchno3 !< Gas concentrations (#/m3): 3834 !< nitric acid HNO3 3835 REAL(wp), INTENT(INOUT) :: pcnh3 !< ammonia NH3 3836 REAL(wp), INTENT(INOUT) :: pcocnv !< non-volatile organics 3837 REAL(wp), INTENT(INOUT) :: pcocsv !< semi-volatile organics 3838 REAL(wp), INTENT(INOUT) :: pcsa !< sulphuric acid H2SO4 3839 REAL(wp), INTENT(INOUT) :: pcw !< Water vapor concentration (kg/m3) 3840 TYPE(t_section), INTENT(inout) :: paero(fn2b) !< Aerosol properties 3841 !-- Local variables 3842 REAL(wp) :: zbeta(fn2b) !< transitional correction factor for aerosols 3843 REAL(wp) :: zcolrate(fn2b) !< collision rate of molecules to particles 3844 !< (1/s) 3845 REAL(wp) :: zcolrate_ocnv(fn2b) !< collision rate of organic molecules 3846 !< to particles (1/s) 3847 REAL(wp) :: zcs_ocnv !< condensation sink of nonvolatile organics (1/s) 3848 REAL(wp) :: zcs_ocsv !< condensation sink of semivolatile organics (1/s) 3849 REAL(wp) :: zcs_su !< condensation sink of sulfate (1/s) 3850 REAL(wp) :: zcs_tot!< total condensation sink (1/s) (gases) 3851 !-- vapour concentration after time step (#/m3) 3852 REAL(wp) :: zcvap_new1 !< sulphuric acid 3853 REAL(wp) :: zcvap_new2 !< nonvolatile organics 3854 REAL(wp) :: zcvap_new3 !< semivolatile organics 3855 REAL(wp) :: zdfpart(in1a+1) !< particle diffusion coefficient (m2/s) 3856 REAL(wp) :: zdfvap !< air diffusion coefficient (m2/s) 3857 !-- change in vapour concentration (#/m3) 3858 REAL(wp) :: zdvap1 !< sulphuric acid 3859 REAL(wp) :: zdvap2 !< nonvolatile organics 3860 REAL(wp) :: zdvap3 !< semivolatile organics 3861 REAL(wp) :: zdvoloc(fn2b) !< change of organics volume in each bin [fxm] 3862 REAL(wp) :: zdvolsa(fn2b) !< change of sulphate volume in each bin [fxm] 3863 REAL(wp) :: zj3n3(2) !< Formation massrate of molecules in 3864 !< nucleation, (molec/m3s). 1: H2SO4 3865 !< and 2: organic vapor 3866 REAL(wp) :: zknud(fn2b) !< particle Knudsen number 3867 REAL(wp) :: zmfp !< mean free path of condensing vapour (m) 3868 REAL(wp) :: zrh !< Relative humidity [0-1] 3869 REAL(wp) :: zvisc !< viscosity of air (kg/(m s)) 3870 REAL(wp) :: zn_vs_c !< ratio of nucleation of all mass transfer in the 3871 !< smallest bin 3872 REAL(wp) :: zxocnv !< ratio of organic vapour in 3nm particles 3873 REAL(wp) :: zxsa !< Ratio in 3nm particles: sulphuric acid 3874 4028 4029 INTEGER(iwp) :: ss !< start index 4030 INTEGER(iwp) :: ee !< end index 4031 4032 REAL(wp) :: zcs_ocnv !< condensation sink of nonvolatile organics (1/s) 4033 REAL(wp) :: zcs_ocsv !< condensation sink of semivolatile organics (1/s) 4034 REAL(wp) :: zcs_su !< condensation sink of sulfate (1/s) 4035 REAL(wp) :: zcs_tot !< total condensation sink (1/s) (gases) 4036 REAL(wp) :: zcvap_new1 !< vapour concentration after time step (#/m3): sulphuric acid 4037 REAL(wp) :: zcvap_new2 !< nonvolatile organics 4038 REAL(wp) :: zcvap_new3 !< semivolatile organics 4039 REAL(wp) :: zdfvap !< air diffusion coefficient (m2/s) 4040 REAL(wp) :: zdvap1 !< change in vapour concentration (#/m3): sulphuric acid 4041 REAL(wp) :: zdvap2 !< nonvolatile organics 4042 REAL(wp) :: zdvap3 !< semivolatile organics 4043 REAL(wp) :: zmfp !< mean free path of condensing vapour (m) 4044 REAL(wp) :: zrh !< Relative humidity [0-1] 4045 REAL(wp) :: zvisc !< viscosity of air (kg/(m s)) 4046 REAL(wp) :: zn_vs_c !< ratio of nucleation of all mass transfer in the smallest bin 4047 REAL(wp) :: zxocnv !< ratio of organic vapour in 3nm particles 4048 REAL(wp) :: zxsa !< Ratio in 3nm particles: sulphuric acid 4049 4050 REAL(wp), INTENT(in) :: ppres !< ambient pressure (Pa) 4051 REAL(wp), INTENT(in) :: pcs !< Water vapour saturation concentration (kg/m3) 4052 REAL(wp), INTENT(in) :: ptemp !< ambient temperature (K) 4053 REAL(wp), INTENT(in) :: ptstep !< timestep (s) 4054 4055 REAL(wp), INTENT(inout) :: pchno3 !< Gas concentrations (#/m3): nitric acid HNO3 4056 REAL(wp), INTENT(inout) :: pc_nh3 !< ammonia NH3 4057 REAL(wp), INTENT(inout) :: pc_ocnv !< non-volatile organics 4058 REAL(wp), INTENT(inout) :: pcocsv !< semi-volatile organics 4059 REAL(wp), INTENT(inout) :: pc_sa !< sulphuric acid H2SO4 4060 REAL(wp), INTENT(inout) :: pcw !< Water vapor concentration (kg/m3) 4061 4062 REAL(wp), DIMENSION(nbins_aerosol) :: zbeta !< transitional correction factor 4063 REAL(wp), DIMENSION(nbins_aerosol) :: zcolrate !< collision rate (1/s) 4064 REAL(wp), DIMENSION(nbins_aerosol) :: zcolrate_ocnv !< collision rate of non-vol. OC (1/s) 4065 REAL(wp), DIMENSION(start_subrange_1a+1) :: zdfpart !< particle diffusion coefficient (m2/s) 4066 REAL(wp), DIMENSION(nbins_aerosol) :: zdvoloc !< change of organics volume 4067 REAL(wp), DIMENSION(nbins_aerosol) :: zdvolsa !< change of sulphate volume 4068 REAL(wp), DIMENSION(2) :: zj3n3 !< Formation massrate of molecules 4069 !< in nucleation, (molec/m3s), 4070 !< 1: H2SO4 and 2: organic vapor 4071 REAL(wp), DIMENSION(nbins_aerosol) :: zknud !< particle Knudsen number 4072 4073 TYPE(component_index), INTENT(in) :: prtcl !< Keeps track which substances are used 4074 4075 TYPE(t_section), DIMENSION(nbins_aerosol), INTENT(inout) :: paero !< Aerosol properties 4076 3875 4077 zj3n3 = 0.0_wp 3876 zrh = pcw / pcs 4078 zrh = pcw / pcs 3877 4079 zxocnv = 0.0_wp 3878 4080 zxsa = 0.0_wp … … 3880 4082 !-- Nucleation 3881 4083 IF ( nsnucl > 0 ) THEN 3882 CALL nucleation( paero, ptemp, zrh, ppres, pc sa, pcocnv, pcnh3, ptstep,&3883 z j3n3, zxsa, zxocnv )4084 CALL nucleation( paero, ptemp, zrh, ppres, pc_sa, pc_ocnv, pc_nh3, ptstep, zj3n3, zxsa, & 4085 zxocnv ) 3884 4086 ENDIF 3885 4087 ! … … 3888 4090 ! 3889 4091 !-- Initialise: 3890 zdvolsa = 0.0_wp 4092 zdvolsa = 0.0_wp 3891 4093 zdvoloc = 0.0_wp 3892 4094 zcolrate = 0.0_wp 3893 ! 4095 ! 3894 4096 !-- 1) Properties of air and condensing gases: 3895 4097 !-- Viscosity of air (kg/(m s)) (Eq. 4.54 in Jabonson (2005)) 3896 zvisc = ( 7.44523E-3_wp * ptemp ** 1.5_wp ) / ( 5093.0_wp * &3897 ( ptemp + 110.4_wp ) ) 4098 zvisc = ( 7.44523E-3_wp * ptemp ** 1.5_wp ) / ( 5093.0_wp * ( ptemp + 110.4_wp ) ) 4099 ! 3898 4100 !-- Diffusion coefficient of air (m2/s) 3899 zdfvap = 5.1111E-10_wp * ptemp ** 1.75_wp * ( p_0 + 1325.0_wp ) / ppres 4101 zdfvap = 5.1111E-10_wp * ptemp ** 1.75_wp * ( p_0 + 1325.0_wp ) / ppres 4102 ! 3900 4103 !-- Mean free path (m): same for H2SO4 and organic compounds 3901 4104 zmfp = 3.0_wp * zdfvap * SQRT( pi * amh2so4 / ( 8.0_wp * argas * ptemp ) ) 3902 ! 3903 !-- 2) Transition regime correction factor zbeta for particles: 3904 !-- Fuchs and Sutugin (1971), In: Hidy et al. (ed.) Topics in current 3905 !-- aerosol research, Pergamon. Size of condensing molecule considered 3906 !-- only for nucleation mode (3 - 20 nm) 3907 ! 3908 !-- Particle Knudsen number: condensation of gases on aerosols 3909 zknud(in1a:in1a+1) = 2.0_wp * zmfp / ( paero(in1a:in1a+1)%dwet + d_sa ) 3910 zknud(in1a+2:fn2b) = 2.0_wp * zmfp / paero(in1a+2:fn2b)%dwet 3911 ! 3912 !-- Transitional correction factor: aerosol + gas (the semi-empirical Fuchs- 3913 !-- Sutugin interpolation function (Fuchs and Sutugin, 1971)) 3914 zbeta = ( zknud + 1.0_wp ) / ( 0.377_wp * zknud + 1.0_wp + 4.0_wp / & 3915 ( 3.0_wp * massacc ) * ( zknud + zknud ** 2.0_wp ) ) 3916 ! 4105 ! 4106 !-- 2) Transition regime correction factor zbeta for particles (Fuchs and Sutugin (1971)): 4107 !-- Size of condensing molecule considered only for nucleation mode (3 - 20 nm). 4108 ! 4109 !-- Particle Knudsen number: condensation of gases on aerosols 4110 ss = start_subrange_1a 4111 ee = start_subrange_1a+1 4112 zknud(ss:ee) = 2.0_wp * zmfp / ( paero(ss:ee)%dwet + d_sa ) 4113 ss = start_subrange_1a+2 4114 ee = end_subrange_2b 4115 zknud(ss:ee) = 2.0_wp * zmfp / paero(ss:ee)%dwet 4116 ! 4117 !-- Transitional correction factor: aerosol + gas (the semi-empirical Fuchs- Sutugin 4118 !-- interpolation function (Fuchs and Sutugin, 1971)) 4119 zbeta = ( zknud + 1.0_wp ) / ( 0.377_wp * zknud + 1.0_wp + 4.0_wp / ( 3.0_wp * massacc ) * & 4120 ( zknud + zknud ** 2 ) ) 4121 ! 3917 4122 !-- 3) Collision rate of molecules to particles 3918 !-- Particle diffusion coefficient considered only for nucleation mode 3919 !-- (3 - 20 nm) 4123 !-- Particle diffusion coefficient considered only for nucleation mode (3 - 20 nm) 3920 4124 ! 3921 4125 !-- Particle diffusion coefficient (m2/s) (e.g. Eq. 15.29 in Jacobson (2005)) 3922 zdfpart = abo * ptemp * zbeta(in1a:in1a+1) / ( 3.0_wp * pi * zvisc * & 3923 paero(in1a:in1a+1)%dwet ) 3924 ! 3925 !-- Collision rate (mass-transfer coefficient): gases on aerosols (1/s) 3926 !-- (Eq. 16.64 in Jacobson (2005)) 3927 zcolrate(in1a:in1a+1) = MERGE( 2.0_wp * pi * & 3928 ( paero(in1a:in1a+1)%dwet + d_sa ) * & 3929 ( zdfvap + zdfpart ) * zbeta(in1a:in1a+1)& 3930 * paero(in1a:in1a+1)%numc, 0.0_wp, & 3931 paero(in1a:in1a+1)%numc > nclim ) 3932 zcolrate(in1a+2:fn2b) = MERGE( 2.0_wp * pi * paero(in1a+2:fn2b)%dwet * & 3933 zdfvap * zbeta(in1a+2:fn2b) * & 3934 paero(in1a+2:fn2b)%numc, 0.0_wp, & 3935 paero(in1a+2:fn2b)%numc > nclim ) 3936 ! 4126 zdfpart = abo * ptemp * zbeta(start_subrange_1a:start_subrange_1a+1) / ( 3.0_wp * pi * zvisc& 4127 * paero(start_subrange_1a:start_subrange_1a+1)%dwet) 4128 ! 4129 !-- Collision rate (mass-transfer coefficient): gases on aerosols (1/s) (Eq. 16.64 in 4130 !-- Jacobson (2005)) 4131 ss = start_subrange_1a 4132 ee = start_subrange_1a+1 4133 zcolrate(ss:ee) = MERGE( 2.0_wp * pi * ( paero(ss:ee)%dwet + d_sa ) * ( zdfvap + zdfpart ) *& 4134 zbeta(ss:ee) * paero(ss:ee)%numc, 0.0_wp, paero(ss:ee)%numc > nclim ) 4135 ss = start_subrange_1a+2 4136 ee = end_subrange_2b 4137 zcolrate(ss:ee) = MERGE( 2.0_wp * pi * paero(ss:ee)%dwet * zdfvap * zbeta(ss:ee) * & 4138 paero(ss:ee)%numc, 0.0_wp, paero(ss:ee)%numc > nclim ) 4139 ! 3937 4140 !-- 4) Condensation sink (1/s) 3938 4141 zcs_tot = SUM( zcolrate ) ! total sink … … 3943 4146 ! 3944 4147 !-- 5.1.1) Non-volatile organic compound: condenses onto all bins 3945 IF ( pcocnv > 1.0E+10_wp .AND. zcs_tot > 1.0E-30_wp .AND. & 3946 is_used( prtcl,'OC' ) ) & 4148 IF ( pc_ocnv > 1.0E+10_wp .AND. zcs_tot > 1.0E-30_wp .AND. index_oc > 0 ) & 3947 4149 THEN 3948 !-- Ratio of nucleation vs. condensation rates in the smallest bin 3949 zn_vs_c = 0.0_wp 4150 !-- Ratio of nucleation vs. condensation rates in the smallest bin 4151 zn_vs_c = 0.0_wp 3950 4152 IF ( zj3n3(2) > 1.0_wp ) THEN 3951 zn_vs_c = ( zj3n3(2) ) / ( zj3n3(2) + pc ocnv * zcolrate(in1a) )4153 zn_vs_c = ( zj3n3(2) ) / ( zj3n3(2) + pc_ocnv * zcolrate(start_subrange_1a) ) 3952 4154 ENDIF 3953 ! 3954 !-- Collision rate in the smallest bin, including nucleation and 3955 !-- condensation(see Jacobson, Fundamentals of Atmospheric Modeling, 2nd 3956 !-- Edition (2005), equation (16.73) ) 4155 ! 4156 !-- Collision rate in the smallest bin, including nucleation and condensation (see 4157 !-- Jacobson (2005), eq. (16.73) ) 3957 4158 zcolrate_ocnv = zcolrate 3958 zcolrate_ocnv( in1a) = zcolrate_ocnv(in1a) + zj3n3(2) / pcocnv3959 ! 4159 zcolrate_ocnv(start_subrange_1a) = zcolrate_ocnv(start_subrange_1a) + zj3n3(2) / pc_ocnv 4160 ! 3960 4161 !-- Total sink for organic vapor 3961 zcs_ocnv = zcs_tot + zj3n3(2) / pc ocnv3962 ! 4162 zcs_ocnv = zcs_tot + zj3n3(2) / pc_ocnv 4163 ! 3963 4164 !-- New gas phase concentration (#/m3) 3964 zcvap_new2 = pc ocnv / ( 1.0_wp + ptstep * zcs_ocnv )3965 ! 4165 zcvap_new2 = pc_ocnv / ( 1.0_wp + ptstep * zcs_ocnv ) 4166 ! 3966 4167 !-- Change in gas concentration (#/m3) 3967 zdvap2 = pc ocnv - zcvap_new23968 ! 3969 !-- Updated vapour concentration (#/m3) 3970 pc ocnv = zcvap_new23971 ! 4168 zdvap2 = pc_ocnv - zcvap_new2 4169 ! 4170 !-- Updated vapour concentration (#/m3) 4171 pc_ocnv = zcvap_new2 4172 ! 3972 4173 !-- Volume change of particles (m3(OC)/m3(air)) 3973 zdvoloc = zcolrate_ocnv( in1a:fn2b) / zcs_ocnv * amvoc * zdvap23974 ! 4174 zdvoloc = zcolrate_ocnv(start_subrange_1a:end_subrange_2b) / zcs_ocnv * amvoc * zdvap2 4175 ! 3975 4176 !-- Change of volume due to condensation in 1a-2b 3976 paero( in1a:fn2b)%volc(2) = paero(in1a:fn2b)%volc(2) + zdvoloc3977 ! 3978 ! -- Change of number concentration in the smallest bin caused by3979 !-- nucleation (Jacobson (2005), equation (16.75)). If zxocnv = 0, then3980 !-- the chosen nucleation mechanism doesn't take into account the non-3981 !-- volatile organic vapors and thus the paero doesn't have to be updated.4177 paero(start_subrange_1a:end_subrange_2b)%volc(2) = & 4178 paero(start_subrange_1a:end_subrange_2b)%volc(2) + zdvoloc 4179 ! 4180 !-- Change of number concentration in the smallest bin caused by nucleation (Jacobson (2005), 4181 !-- eq. (16.75)). If zxocnv = 0, then the chosen nucleation mechanism doesn't take into 4182 !-- account the non-volatile organic vapors and thus the paero doesn't have to be updated. 3982 4183 IF ( zxocnv > 0.0_wp ) THEN 3983 paero( in1a)%numc = paero(in1a)%numc + zn_vs_c * zdvoloc(in1a) /&3984 amvoc / ( n3 * zxocnv )4184 paero(start_subrange_1a)%numc = paero(start_subrange_1a)%numc + zn_vs_c * & 4185 zdvoloc(start_subrange_1a) / amvoc / ( n3 * zxocnv ) 3985 4186 ENDIF 3986 4187 ENDIF 3987 ! 4188 ! 3988 4189 !-- 5.1.2) Semivolatile organic compound: all bins except subrange 1 3989 zcs_ocsv = SUM( zcolrate(in2a:fn2b) ) !< sink for semi-volatile organics 3990 IF ( pcocsv > 1.0E+10_wp .AND. zcs_ocsv > 1.0E-30 .AND. & 3991 is_used( prtcl,'OC') ) & 3992 THEN 4190 zcs_ocsv = SUM( zcolrate(start_subrange_2a:end_subrange_2b) ) !< sink for semi-volatile organics 4191 IF ( pcocsv > 1.0E+10_wp .AND. zcs_ocsv > 1.0E-30 .AND. is_used( prtcl,'OC') ) THEN 3993 4192 ! 3994 4193 !-- New gas phase concentration (#/m3) 3995 4194 zcvap_new3 = pcocsv / ( 1.0_wp + ptstep * zcs_ocsv ) 3996 ! 4195 ! 3997 4196 !-- Change in gas concentration (#/m3) 3998 4197 zdvap3 = pcocsv - zcvap_new3 3999 ! 4000 !-- Updated gas concentration (#/m3) 4198 ! 4199 !-- Updated gas concentration (#/m3) 4001 4200 pcocsv = zcvap_new3 4002 ! 4201 ! 4003 4202 !-- Volume change of particles (m3(OC)/m3(air)) 4004 zdvoloc(in2a:fn2b) = zdvoloc(in2a:fn2b) + zcolrate(in2a:fn2b) / & 4005 zcs_ocsv * amvoc * zdvap3 4006 ! 4203 ss = start_subrange_2a 4204 ee = end_subrange_2b 4205 zdvoloc(ss:ee) = zdvoloc(ss:ee) + zcolrate(ss:ee) / zcs_ocsv * amvoc * zdvap3 4206 ! 4007 4207 !-- Change of volume due to condensation in 1a-2b 4008 paero(in1a:fn2b)%volc(2) = paero(in1a:fn2b)%volc(2) + zdvoloc 4009 ENDIF 4010 ! 4011 !-- 5.2) Sulphate: condensed on all bins 4012 IF ( pcsa > 1.0E+10_wp .AND. zcs_tot > 1.0E-30_wp .AND. & 4013 is_used( prtcl,'SO4' ) ) & 4014 THEN 4015 ! 4208 paero(start_subrange_1a:end_subrange_2b)%volc(2) = & 4209 paero(start_subrange_1a:end_subrange_2b)%volc(2) + zdvoloc 4210 ENDIF 4211 ! 4212 !-- 5.2) Sulphate: condensed on all bins 4213 IF ( pc_sa > 1.0E+10_wp .AND. zcs_tot > 1.0E-30_wp .AND. index_so4 > 0 ) THEN 4214 ! 4016 4215 !-- Ratio of mass transfer between nucleation and condensation 4017 4216 zn_vs_c = 0.0_wp 4018 4217 IF ( zj3n3(1) > 1.0_wp ) THEN 4019 zn_vs_c = ( zj3n3(1) ) / ( zj3n3(1) + pc sa * zcolrate(in1a) )4218 zn_vs_c = ( zj3n3(1) ) / ( zj3n3(1) + pc_sa * zcolrate(start_subrange_1a) ) 4020 4219 ENDIF 4021 ! 4022 !-- Collision rate in the smallest bin, including nucleation and 4023 !-- condensation (see Jacobson, Fundamentals of Atmospheric Modeling, 2nd 4024 !-- Edition (2005), equation (16.73)) 4025 zcolrate(in1a) = zcolrate(in1a) + zj3n3(1) / pcsa 4026 ! 4220 ! 4221 !-- Collision rate in the smallest bin, including nucleation and condensation (see 4222 !-- Jacobson (2005), eq. (16.73)) 4223 zcolrate(start_subrange_1a) = zcolrate(start_subrange_1a) + zj3n3(1) / pc_sa 4224 ! 4027 4225 !-- Total sink for sulfate (1/s) 4028 zcs_su = zcs_tot + zj3n3(1) / pc sa4029 ! 4226 zcs_su = zcs_tot + zj3n3(1) / pc_sa 4227 ! 4030 4228 !-- Sulphuric acid: 4031 4229 !-- New gas phase concentration (#/m3) 4032 zcvap_new1 = pc sa / ( 1.0_wp + ptstep * zcs_su )4033 ! 4230 zcvap_new1 = pc_sa / ( 1.0_wp + ptstep * zcs_su ) 4231 ! 4034 4232 !-- Change in gas concentration (#/m3) 4035 zdvap1 = pc sa - zcvap_new14036 ! 4233 zdvap1 = pc_sa - zcvap_new1 4234 ! 4037 4235 !-- Updating vapour concentration (#/m3) 4038 pc sa = zcvap_new14039 ! 4236 pc_sa = zcvap_new1 4237 ! 4040 4238 !-- Volume change of particles (m3(SO4)/m3(air)) by condensation 4041 zdvolsa = zcolrate(in1a:fn2b) / zcs_su * amvh2so4 * zdvap1 4042 !-- For validation: zdvolsa = 5.5 mum3/cm3 per 12 h 4043 ! zdvolsa = zdvolsa / SUM( zdvolsa ) * 5.5E-12_wp * dt_salsa / 43200.0_wp 4044 !0.3E-12_wp, 0.6E-12_wp, 11.0E-12_wp, 4.6E-12_wp, 9.2E-12_wp 4045 ! 4239 zdvolsa = zcolrate(start_subrange_1a:end_subrange_2b) / zcs_su * amvh2so4 * zdvap1 4240 ! 4046 4241 !-- Change of volume concentration of sulphate in aerosol [fxm] 4047 paero(in1a:fn2b)%volc(1) = paero(in1a:fn2b)%volc(1) + zdvolsa 4048 ! 4242 paero(start_subrange_1a:end_subrange_2b)%volc(1) = & 4243 paero(start_subrange_1a:end_subrange_2b)%volc(1) + zdvolsa 4244 ! 4049 4245 !-- Change of number concentration in the smallest bin caused by nucleation 4050 4246 !-- (Jacobson (2005), equation (16.75)) 4051 4247 IF ( zxsa > 0.0_wp ) THEN 4052 paero( in1a)%numc = paero(in1a)%numc + zn_vs_c * zdvolsa(in1a) /&4053 amvh2so4 / ( n3 * zxsa)4248 paero(start_subrange_1a)%numc = paero(start_subrange_1a)%numc + zn_vs_c * & 4249 zdvolsa(start_subrange_1a) / amvh2so4 / ( n3 * zxsa) 4054 4250 ENDIF 4055 4251 ENDIF 4252 ! 4253 !-- Partitioning of H2O, HNO3, and NH3: Dissolutional growth 4254 IF ( lspartition .AND. ( pchno3 > 1.0E+10_wp .OR. pc_nh3 > 1.0E+10_wp ) ) THEN 4255 CALL gpparthno3( ppres, ptemp, paero, pchno3, pc_nh3, pcw, pcs, zbeta, ptstep ) 4256 ENDIF 4056 4257 ENDIF 4057 !4058 4258 ! 4059 4259 !-- Condensation of water vapour … … 4061 4261 CALL gpparth2o( paero, ptemp, ppres, pcs, pcw, ptstep ) 4062 4262 ENDIF 4063 ! 4064 ! 4065 !-- Partitioning of H2O, HNO3, and NH3: Dissolutional growth 4066 IF ( lscndgas .AND. ino > 0 .AND. inh > 0 .AND. & 4067 ( pchno3 > 1.0E+10_wp .OR. pcnh3 > 1.0E+10_wp ) ) & 4068 THEN 4069 CALL gpparthno3( ppres, ptemp, paero, pchno3, pcnh3, pcw, pcs, zbeta, & 4070 ptstep ) 4071 ENDIF 4072 4263 4073 4264 END SUBROUTINE condensation 4074 4265 4075 4266 !------------------------------------------------------------------------------! 4076 4267 ! Description: … … 4091 4282 !> nj3 = 3: Anttila et al. (2010), J. Aerosol Sci., 41(7), 621-636. 4092 4283 ! 4284 !> c = aerosol of critical radius (1 nm) 4285 !> x = aerosol with radius 3 nm 4286 !> 2 = wet or mean droplet 4287 ! 4093 4288 !> Called from subroutine condensation (in module salsa_dynamics_mod.f90) 4094 4289 ! … … 4109 4304 !------------------------------------------------------------------------------! 4110 4305 4111 SUBROUTINE nucleation( paero, ptemp, prh, ppres, pcsa, pcocnv, pcnh3, ptstep, & 4112 pj3n3, pxsa, pxocnv ) 4306 SUBROUTINE nucleation( paero, ptemp, prh, ppres, pc_sa, pc_ocnv, pc_nh3, ptstep, pj3n3, pxsa, & 4307 pxocnv ) 4308 4113 4309 IMPLICIT NONE 4114 ! 4115 !-- Input and output variables 4116 REAL(wp), INTENT(in) :: pcnh3 !< ammonia concentration (#/m3) 4117 REAL(wp), INTENT(in) :: pcocnv !< conc. of non-volatile OC (#/m3) 4118 REAL(wp), INTENT(in) :: pcsa !< sulphuric acid conc. (#/m3) 4310 4311 INTEGER(iwp) :: iteration 4312 4313 REAL(wp) :: zc_h2so4 !< H2SO4 conc. (#/cm3) !UNITS! 4314 REAL(wp) :: zc_org !< organic vapour conc. (#/cm3) 4315 REAL(wp) :: zcc_c !< Cunningham correct factor for c = critical (1nm) 4316 REAL(wp) :: zcc_x !< Cunningham correct factor for x = 3nm 4317 REAL(wp) :: zcoags_c !< coagulation sink (1/s) for c = critical (1nm) 4318 REAL(wp) :: zcoags_x !< coagulation sink (1/s) for x = 3nm 4319 REAL(wp) :: zcoagstot !< total particle losses due to coagulation, including condensation 4320 !< and self-coagulation 4321 REAL(wp) :: zcocnv_local !< organic vapour conc. (#/m3) 4322 REAL(wp) :: zcsink !< condensational sink (#/m2) 4323 REAL(wp) :: zcsa_local !< H2SO4 conc. (#/m3) 4324 REAL(wp) :: zcv_c !< mean relative thermal velocity (m/s) for c = critical (1nm) 4325 REAL(wp) :: zcv_x !< mean relative thermal velocity (m/s) for x = 3nm 4326 REAL(wp) :: zdcrit !< diameter of critical cluster (m) 4327 REAL(wp) :: zdelta_vap !< change of H2SO4 and organic vapour concentration (#/m3) 4328 REAL(wp) :: zdfvap !< air diffusion coefficient (m2/s) 4329 REAL(wp) :: zdmean !< mean diameter of existing particles (m) 4330 REAL(wp) :: zeta !< constant: proportional to ratio of CS/GR (m) 4331 !< (condensation sink / growth rate) 4332 REAL(wp) :: zgamma !< proportionality factor ((nm2*m2)/h) 4333 REAL(wp) :: z_gr_clust !< growth rate of formed clusters (nm/h) 4334 REAL(wp) :: z_gr_tot !< total growth rate 4335 REAL(wp) :: zj3 !< number conc. of formed 3nm particles (#/m3) 4336 REAL(wp) :: zjnuc !< nucleation rate at ~1nm (#/m3s) 4337 REAL(wp) :: z_k_eff !< effective cogulation coefficient for freshly nucleated particles 4338 REAL(wp) :: zknud_c !< Knudsen number for c = critical (1nm) 4339 REAL(wp) :: zknud_x !< Knudsen number for x = 3nm 4340 REAL(wp) :: zkocnv !< lever: zkocnv=1 --> organic compounds involved in nucleation 4341 REAL(wp) :: zksa !< lever: zksa=1 --> H2SO4 involved in nucleation 4342 REAL(wp) :: zlambda !< parameter for adjusting the growth rate due to self-coagulation 4343 REAL(wp) :: zm_c !< particle mass (kg) for c = critical (1nm) 4344 REAL(wp) :: zm_para !< Parameter m for calculating the coagulation sink (Eq. 5&6 in 4345 !< Lehtinen et al. 2007) 4346 REAL(wp) :: zm_x !< particle mass (kg) for x = 3nm 4347 REAL(wp) :: zmfp !< mean free path of condesing vapour(m) 4348 REAL(wp) :: zmixnh3 !< ammonia mixing ratio (ppt) 4349 REAL(wp) :: zmyy !< gas dynamic viscosity (N*s/m2) 4350 REAL(wp) :: z_n_nuc !< number of clusters/particles at the size range d1-dx (#/m3) 4351 REAL(wp) :: znoc !< number of organic molecules in critical cluster 4352 REAL(wp) :: znsa !< number of H2SO4 molecules in critical cluster 4353 4354 REAL(wp), INTENT(in) :: pc_nh3 !< ammonia concentration (#/m3) 4355 REAL(wp), INTENT(in) :: pc_ocnv !< conc. of non-volatile OC (#/m3) 4356 REAL(wp), INTENT(in) :: pc_sa !< sulphuric acid conc. (#/m3) 4119 4357 REAL(wp), INTENT(in) :: ppres !< ambient air pressure (Pa) 4120 REAL(wp), INTENT(in) :: prh !< ambient rel. humidity [0-1] 4358 REAL(wp), INTENT(in) :: prh !< ambient rel. humidity [0-1] 4121 4359 REAL(wp), INTENT(in) :: ptemp !< ambient temperature (K) 4122 4360 REAL(wp), INTENT(in) :: ptstep !< time step (s) of SALSA 4123 TYPE(t_section), INTENT(inout) :: paero(fn2b) !< aerosol properties 4124 REAL(wp), INTENT(inout) :: pj3n3(2) !< formation mass rate of molecules 4125 !< (molec/m3s) for 1: H2SO4 and 4126 !< 2: organic vapour 4127 REAL(wp), INTENT(out) :: pxocnv !< ratio of non-volatile organic vapours in 4128 !< 3nm aerosol particles 4129 REAL(wp), INTENT(out) :: pxsa !< ratio of H2SO4 in 3nm aerosol particles 4130 !-- Local variables 4131 INTEGER(iwp) :: iteration 4132 REAL(wp) :: zbeta(fn2b) !< transitional correction factor 4133 REAL(wp) :: zc_h2so4 !< H2SO4 conc. (#/cm3) !UNITS! 4134 REAL(wp) :: zc_org !< organic vapour conc. (#/cm3) 4135 REAL(wp) :: zCoagStot !< total losses due to coagulation, including 4136 !< condensation and self-coagulation 4137 REAL(wp) :: zcocnv_local !< organic vapour conc. (#/m3) 4138 REAL(wp) :: zcsink !< condensational sink (#/m2) 4139 REAL(wp) :: zcsa_local !< H2SO4 conc. (#/m3) 4140 REAL(wp) :: zdcrit !< diameter of critical cluster (m) 4141 REAL(wp) :: zdelta_vap !< change of H2SO4 and organic vapour 4142 !< concentration (#/m3) 4143 REAL(wp) :: zdfvap !< air diffusion coefficient (m2/s) 4144 REAL(wp) :: zdmean !< mean diameter of existing particles (m) 4145 REAL(wp) :: zeta !< constant: proportional to ratio of CS/GR (m) 4146 !< (condensation sink / growth rate) 4147 REAL(wp) :: zgamma !< proportionality factor ((nm2*m2)/h) 4148 REAL(wp) :: zGRclust !< growth rate of formed clusters (nm/h) 4149 REAL(wp) :: zGRtot !< total growth rate 4150 REAL(wp) :: zj3 !< number conc. of formed 3nm particles (#/m3) 4151 REAL(wp) :: zjnuc !< nucleation rate at ~1nm (#/m3s) 4152 REAL(wp) :: zKeff !< effective cogulation coefficient between 4153 !< freshly nucleated particles 4154 REAL(wp) :: zknud(fn2b) !< particle Knudsen number 4155 REAL(wp) :: zkocnv !< lever: zkocnv=1 --> organic compounds involved 4156 !< in nucleation 4157 REAL(wp) :: zksa !< lever: zksa=1 --> H2SO4 involved in nucleation 4158 REAL(wp) :: zlambda !< parameter for adjusting the growth rate due to 4159 !< self-coagulation 4160 REAL(wp) :: zmfp !< mean free path of condesing vapour(m) 4161 REAL(wp) :: zmixnh3 !< ammonia mixing ratio (ppt) 4162 REAL(wp) :: zNnuc !< number of clusters/particles at the size range 4163 !< d1-dx (#/m3) 4164 REAL(wp) :: znoc !< number of organic molecules in critical cluster 4165 REAL(wp) :: znsa !< number of H2SO4 molecules in critical cluster 4166 ! 4167 !-- Variable determined for the m-parameter 4168 REAL(wp) :: zCc_2(fn2b) !< 4169 REAL(wp) :: zCc_c !< 4170 REAL(wp) :: zCc_x !< 4171 REAL(wp) :: zCoagS_c !< 4172 REAL(wp) :: zCoagS_x !< 4173 REAL(wp) :: zcv_2(fn2b) !< 4174 REAL(wp) :: zcv_c !< 4175 REAL(wp) :: zcv_c2(fn2b) !< 4176 REAL(wp) :: zcv_x !< 4177 REAL(wp) :: zcv_x2(fn2b) !< 4178 REAL(wp) :: zDc_2(fn2b) !< 4179 REAL(wp) :: zDc_c(fn2b) !< 4180 REAL(wp) :: zDc_c2(fn2b) !< 4181 REAL(wp) :: zDc_x(fn2b) !< 4182 REAL(wp) :: zDc_x2(fn2b) !< 4183 REAL(wp) :: zgammaF_2(fn2b) !< 4184 REAL(wp) :: zgammaF_c(fn2b) !< 4185 REAL(wp) :: zgammaF_x(fn2b) !< 4186 REAL(wp) :: zK_c2(fn2b) !< 4187 REAL(wp) :: zK_x2(fn2b) !< 4188 REAL(wp) :: zknud_2(fn2b) !< 4189 REAL(wp) :: zknud_c !< 4190 REAL(wp) :: zknud_x !< 4191 REAL(wp) :: zm_2(fn2b) !< 4192 REAL(wp) :: zm_c !< 4193 REAL(wp) :: zm_para !< 4194 REAL(wp) :: zm_x !< 4195 REAL(wp) :: zmyy !< 4196 REAL(wp) :: zomega_2c(fn2b) !< 4197 REAL(wp) :: zomega_2x(fn2b) !< 4198 REAL(wp) :: zomega_c(fn2b) !< 4199 REAL(wp) :: zomega_x(fn2b) !< 4200 REAL(wp) :: zRc2(fn2b) !< 4201 REAL(wp) :: zRx2(fn2b) !< 4202 REAL(wp) :: zsigma_c2(fn2b) !< 4203 REAL(wp) :: zsigma_x2(fn2b) !< 4361 4362 REAL(wp), INTENT(inout) :: pj3n3(2) !< formation mass rate of molecules (molec/m3s) for 4363 !< 1: H2SO4 and 2: organic vapour 4364 4365 REAL(wp), INTENT(out) :: pxocnv !< ratio of non-volatile organic vapours in 3 nm particles 4366 REAL(wp), INTENT(out) :: pxsa !< ratio of H2SO4 in 3 nm aerosol particles 4367 4368 REAL(wp), DIMENSION(nbins_aerosol) :: zbeta !< transitional correction factor 4369 REAL(wp), DIMENSION(nbins_aerosol) :: zcc_2 !< Cunningham correct factor:2 4370 REAL(wp), DIMENSION(nbins_aerosol) :: zcv_2 !< mean relative thermal velocity (m/s): 2 4371 REAL(wp), DIMENSION(nbins_aerosol) :: zcv_c2 !< average velocity after coagulation: c & 2 4372 REAL(wp), DIMENSION(nbins_aerosol) :: zcv_x2 !< average velocity after coagulation: x & 2 4373 REAL(wp), DIMENSION(nbins_aerosol) :: zdc_2 !< particle diffusion coefficient (m2/s): 2 4374 REAL(wp), DIMENSION(nbins_aerosol) :: zdc_c !< particle diffusion coefficient (m2/s): c 4375 REAL(wp), DIMENSION(nbins_aerosol) :: zdc_c2 !< sum of diffusion coef. for c and 2 4376 REAL(wp), DIMENSION(nbins_aerosol) :: zdc_x !< particle diffusion coefficient (m2/s): x 4377 REAL(wp), DIMENSION(nbins_aerosol) :: zdc_x2 !< sum of diffusion coef. for: x & 2 4378 REAL(wp), DIMENSION(nbins_aerosol) :: zgamma_f_2 !< zgamma_f for calculating zomega 4379 REAL(wp), DIMENSION(nbins_aerosol) :: zgamma_f_c !< zgamma_f for calculating zomega 4380 REAL(wp), DIMENSION(nbins_aerosol) :: zgamma_f_x !< zgamma_f for calculating zomega 4381 REAL(wp), DIMENSION(nbins_aerosol) :: z_k_c2 !< coagulation coef. in the continuum 4382 !< regime: c & 2 4383 REAL(wp), DIMENSION(nbins_aerosol) :: z_k_x2 !< coagulation coef. in the continuum 4384 !< regime: x & 2 4385 REAL(wp), DIMENSION(nbins_aerosol) :: zknud !< particle Knudsen number 4386 REAL(wp), DIMENSION(nbins_aerosol) :: zknud_2 !< particle Knudsen number: 2 4387 REAL(wp), DIMENSION(nbins_aerosol) :: zm_2 !< particle mass (kg): 2 4388 REAL(wp), DIMENSION(nbins_aerosol) :: zomega_2c !< zomega (m) for calculating zsigma: c & 2 4389 REAL(wp), DIMENSION(nbins_aerosol) :: zomega_2x !< zomega (m) for calculating zsigma: x & 2 4390 REAL(wp), DIMENSION(nbins_aerosol) :: zomega_c !< zomega (m) for calculating zsigma: c 4391 REAL(wp), DIMENSION(nbins_aerosol) :: zomega_x !< zomega (m) for calculating zsigma: x 4392 REAL(wp), DIMENSION(nbins_aerosol) :: z_r_c2 !< sum of the radii: c & 2 4393 REAL(wp), DIMENSION(nbins_aerosol) :: z_r_x2 !< sum of the radii: x & 2 4394 REAL(wp), DIMENSION(nbins_aerosol) :: zsigma_c2 !< 4395 REAL(wp), DIMENSION(nbins_aerosol) :: zsigma_x2 !< 4396 4397 TYPE(t_section), DIMENSION(nbins_aerosol), INTENT(inout) :: paero !< aerosol properties 4204 4398 ! 4205 4399 !-- 1) Nucleation rate (zjnuc) and diameter of critical cluster (zdcrit) … … 4210 4404 zksa = 0.0_wp 4211 4405 zkocnv = 0.0_wp 4212 4406 4213 4407 SELECT CASE ( nsnucl ) 4214 4215 CASE(1) ! Binary H2SO4-H2O nucleation 4216 4217 zc_h2so4 = pcsa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4218 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, & 4219 zkocnv ) 4220 4221 CASE(2) ! Activation type nucleation 4222 4223 zc_h2so4 = pcsa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4224 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, & 4225 zkocnv ) 4226 CALL actnucl( pcsa, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv, act_coeff ) 4227 4228 CASE(3) ! Kinetically limited nucleation of (NH4)HSO4 clusters 4229 4230 zc_h2so4 = pcsa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4231 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, & 4232 zkocnv ) 4233 4234 CALL kinnucl( zc_h2so4, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv ) 4235 4236 CASE(4) ! Ternary H2SO4-H2O-NH3 nucleation 4237 4238 zmixnh3 = pcnh3 * ptemp * argas / ( ppres * avo ) 4239 zc_h2so4 = pcsa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4240 CALL ternucl( zc_h2so4, zmixnh3, ptemp, prh, zjnuc, znsa, znoc, zdcrit, & 4241 zksa, zkocnv ) 4242 4243 CASE(5) ! Organic nucleation, J~[ORG] or J~[ORG]**2 4244 4245 zc_org = pcocnv * 1.0E-6_wp ! conc. of non-volatile OC to #/cm3 4246 zc_h2so4 = pcsa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4247 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, & 4248 zkocnv ) 4249 CALL orgnucl( pcocnv, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv ) 4250 4251 CASE(6) ! Sum of H2SO4 and organic activation type nucleation, 4252 ! J~[H2SO4]+[ORG] 4253 4254 zc_h2so4 = pcsa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4255 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, & 4256 zkocnv ) 4257 CALL sumnucl( pcsa, pcocnv, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv ) 4258 4259 4260 CASE(7) ! Heteromolecular nucleation, J~[H2SO4]*[ORG] 4261 4262 zc_h2so4 = pcsa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4263 zc_org = pcocnv * 1.0E-6_wp ! conc. of non-volatile OC to #/cm3 4264 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, & 4265 zkocnv ) 4266 CALL hetnucl( zc_h2so4, zc_org, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv ) 4267 4268 CASE(8) ! Homomolecular nucleation of H2SO4 and heteromolecular 4269 ! nucleation of H2SO4 and organic vapour, 4270 ! J~[H2SO4]**2 + [H2SO4]*[ORG] (EUCAARI project) 4271 zc_h2so4 = pcsa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4272 zc_org = pcocnv * 1.0E-6_wp ! conc. of non-volatile OC to #/cm3 4273 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, & 4274 zkocnv ) 4275 CALL SAnucl( zc_h2so4, zc_org, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv ) 4276 4277 CASE(9) ! Homomolecular nucleation of H2SO4 and organic vapour and 4278 ! heteromolecular nucleation of H2SO4 and organic vapour, 4279 ! J~[H2SO4]**2 + [H2SO4]*[ORG]+[ORG]**2 (EUCAARI project) 4280 4281 zc_h2so4 = pcsa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4282 zc_org = pcocnv * 1.0E-6_wp ! conc. of non-volatile OC to #/cm3 4283 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, & 4284 zkocnv ) 4285 4286 CALL SAORGnucl( zc_h2so4, zc_org, zjnuc, zdcrit, znsa, znoc, zksa, & 4287 zkocnv ) 4408 ! 4409 !-- Binary H2SO4-H2O nucleation 4410 CASE(1) 4411 4412 zc_h2so4 = pc_sa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4413 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, zkocnv ) 4414 ! 4415 !-- Activation type nucleation 4416 CASE(2) 4417 4418 zc_h2so4 = pc_sa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4419 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, zkocnv ) 4420 CALL actnucl( pc_sa, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv, act_coeff ) 4421 ! 4422 !-- Kinetically limited nucleation of (NH4)HSO4 clusters 4423 CASE(3) 4424 4425 zc_h2so4 = pc_sa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4426 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, zkocnv ) 4427 CALL kinnucl( zc_h2so4, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv ) 4428 ! 4429 !-- Ternary H2SO4-H2O-NH3 nucleation 4430 CASE(4) 4431 4432 zmixnh3 = pc_nh3 * ptemp * argas / ( ppres * avo ) 4433 zc_h2so4 = pc_sa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4434 CALL ternucl( zc_h2so4, zmixnh3, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, zkocnv ) 4435 ! 4436 !-- Organic nucleation, J~[ORG] or J~[ORG]**2 4437 CASE(5) 4438 4439 zc_org = pc_ocnv * 1.0E-6_wp ! conc. of non-volatile OC to #/cm3 4440 zc_h2so4 = pc_sa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4441 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, zkocnv ) 4442 CALL orgnucl( pc_ocnv, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv ) 4443 ! 4444 !-- Sum of H2SO4 and organic activation type nucleation, J~[H2SO4]+[ORG] 4445 CASE(6) 4446 4447 zc_h2so4 = pc_sa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4448 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, zkocnv ) 4449 CALL sumnucl( pc_sa, pc_ocnv, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv ) 4450 ! 4451 !-- Heteromolecular nucleation, J~[H2SO4]*[ORG] 4452 CASE(7) 4453 4454 zc_h2so4 = pc_sa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4455 zc_org = pc_ocnv * 1.0E-6_wp ! conc. of non-volatile OC to #/cm3 4456 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, zkocnv ) 4457 CALL hetnucl( zc_h2so4, zc_org, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv ) 4458 ! 4459 !-- Homomolecular nucleation of H2SO4 and heteromolecular nucleation of H2SO4 and organic vapour, 4460 !-- J~[H2SO4]**2 + [H2SO4]*[ORG] (EUCAARI project) 4461 CASE(8) 4462 zc_h2so4 = pc_sa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4463 zc_org = pc_ocnv * 1.0E-6_wp ! conc. of non-volatile OC to #/cm3 4464 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, zkocnv ) 4465 CALL SAnucl( zc_h2so4, zc_org, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv ) 4466 ! 4467 !-- Homomolecular nucleation of H2SO4 and organic vapour and heteromolecular nucleation of H2SO4 4468 !-- and organic vapour, J~[H2SO4]**2 + [H2SO4]*[ORG]+[ORG]**2 (EUCAARI project) 4469 CASE(9) 4470 4471 zc_h2so4 = pc_sa * 1.0E-6_wp ! sulphuric acid conc. to #/cm3 4472 zc_org = pc_ocnv * 1.0E-6_wp ! conc. of non-volatile OC to #/cm3 4473 CALL binnucl( zc_h2so4, ptemp, prh, zjnuc, znsa, znoc, zdcrit, zksa, zkocnv ) 4474 CALL SAORGnucl( zc_h2so4, zc_org, zjnuc, zdcrit, znsa, znoc, zksa, zkocnv ) 4475 4288 4476 END SELECT 4289 4290 zcsa_local = pc sa4291 zcocnv_local = pc ocnv4477 4478 zcsa_local = pc_sa 4479 zcocnv_local = pc_ocnv 4292 4480 ! 4293 4481 !-- 2) Change of particle and gas concentrations due to nucleation 4294 ! 4295 !-- 2.1) Check that there is enough H2SO4 and organic vapour to produce the 4296 !-- nucleation 4482 ! 4483 !-- 2.1) Check that there is enough H2SO4 and organic vapour to produce the nucleation 4297 4484 IF ( nsnucl <= 4 ) THEN 4298 ! -- If the chosen nucleation scheme is 1-4, nucleation occurs only due to4299 !-- H2SO4. All of the total vapour concentration that is taking part to the4300 !-- nucleation is there for sulphuric acid (sa = H2SO4) and non-volatile4301 !-- organic vapour is zero.4302 pxsa = 1.0_wp ! ratio of sulphuric acid in 3nm particles 4485 ! 4486 !-- If the chosen nucleation scheme is 1-4, nucleation occurs only due to H2SO4. All of the total 4487 !-- vapour concentration that is taking part to the nucleation is there for sulphuric acid 4488 !-- (sa = H2SO4) and non-volatile organic vapour is zero. 4489 pxsa = 1.0_wp ! ratio of sulphuric acid in 3nm particles 4303 4490 pxocnv = 0.0_wp ! ratio of non-volatile origanic vapour 4304 4491 ! in 3nm particles 4305 4492 ELSEIF ( nsnucl > 4 ) THEN 4306 ! -- If the chosen nucleation scheme is 5-9, nucleation occurs due to organic4307 !-- vapour or the combination of organic vapour and H2SO4. The number of4308 !-- needed molecules depends on the chosen nucleation type and it has an4309 !-- effect also on the minimum ratio of the molecules present.4310 IF ( pc sa * znsa + pcocnv * znoc < 1.E-14_wp ) THEN4493 ! 4494 !-- If the chosen nucleation scheme is 5-9, nucleation occurs due to organic vapour or the 4495 !-- combination of organic vapour and H2SO4. The number of needed molecules depends on the chosen 4496 !-- nucleation type and it has an effect also on the minimum ratio of the molecules present. 4497 IF ( pc_sa * znsa + pc_ocnv * znoc < 1.E-14_wp ) THEN 4311 4498 pxsa = 0.0_wp 4312 pxocnv = 0.0_wp 4499 pxocnv = 0.0_wp 4313 4500 ELSE 4314 pxsa = pc sa * znsa / ( pcsa * znsa + pcocnv * znoc )4315 pxocnv = pc ocnv * znoc / ( pcsa * znsa + pcocnv * znoc )4316 ENDIF 4501 pxsa = pc_sa * znsa / ( pc_sa * znsa + pc_ocnv * znoc ) 4502 pxocnv = pc_ocnv * znoc / ( pc_sa * znsa + pc_ocnv * znoc ) 4503 ENDIF 4317 4504 ENDIF 4318 ! 4319 !-- The change in total vapour concentration is the sum of the concentrations 4320 !-- of the vapours taking part to the nucleation (depends on the chosen 4321 !-- nucleation scheme) 4322 zdelta_vap = MIN( zjnuc * ( znoc + znsa ), ( pcocnv * zkocnv + pcsa * & 4323 zksa ) / ptstep ) 4324 ! 4325 !-- Nucleation rate J at ~1nm (#/m3s) 4505 ! 4506 !-- The change in total vapour concentration is the sum of the concentrations of the vapours taking 4507 !-- part to the nucleation (depends on the chosen nucleation scheme) 4508 zdelta_vap = MIN( zjnuc * ( znoc + znsa ), ( pc_ocnv * zkocnv + pc_sa * zksa ) / ptstep ) 4509 ! 4510 !-- Nucleation rate J at ~1nm (#/m3s) 4326 4511 zjnuc = zdelta_vap / ( znoc + znsa ) 4327 ! 4328 !-- H2SO4 concentration after nucleation in #/m34329 zcsa_local = MAX( 1.0_wp, pc sa - zdelta_vap * pxsa )4330 ! 4512 ! 4513 !-- H2SO4 concentration after nucleation (#/m3) 4514 zcsa_local = MAX( 1.0_wp, pc_sa - zdelta_vap * pxsa ) 4515 ! 4331 4516 !-- Non-volative organic vapour concentration after nucleation (#/m3) 4332 zcocnv_local = MAX( 1.0_wp, pc ocnv - zdelta_vap * pxocnv )4517 zcocnv_local = MAX( 1.0_wp, pc_ocnv - zdelta_vap * pxocnv ) 4333 4518 ! 4334 4519 !-- 2.2) Formation rate of 3 nm particles (Kerminen & Kulmala, 2002) 4335 4520 ! 4336 !-- 2.2.1) Growth rate of clusters formed by H2SO4 4337 ! 4338 !-- GR = 3.0e-15 / dens_clus * sum( molecspeed * molarmass * conc ) 4339 ! 4340 !-- dens_clus = density of the clusters (here 1830 kg/m3) 4341 !-- molarmass = molar mass of condensing species (here 98.08 g/mol) 4342 !-- conc = concentration of condensing species [#/m3] 4343 !-- molecspeed = molecular speed of condensing species [m/s] 4344 !-- = sqrt( 8.0 * R * ptemp / ( pi * molarmass ) ) 4345 !-- (Seinfeld & Pandis, 1998) 4346 ! 4347 !-- Growth rate by H2SO4 and organic vapour in nm/h (Eq. 21) 4348 zGRclust = 2.3623E-15_wp * SQRT( ptemp ) * ( zcsa_local + zcocnv_local ) 4349 ! 4521 !-- Growth rate by H2SO4 and organic vapour (nm/h, Eq. 21) 4522 z_gr_clust = 2.3623E-15_wp * SQRT( ptemp ) * ( zcsa_local + zcocnv_local ) 4523 ! 4350 4524 !-- 2.2.2) Condensational sink of pre-existing particle population 4351 4525 ! 4352 4526 !-- Diffusion coefficient (m2/s) 4353 zdfvap = 5.1111E-10_wp * ptemp **1.75_wp * ( p_0 + 1325.0_wp ) / ppres4354 ! -- Mean free path of condensing vapour (m) (Jacobson (2005), Eq. 15.25 and4355 !-- 16.29)4527 zdfvap = 5.1111E-10_wp * ptemp**1.75_wp * ( p_0 + 1325.0_wp ) / ppres 4528 ! 4529 !-- Mean free path of condensing vapour (m) (Jacobson (2005), Eq. 15.25 and 16.29) 4356 4530 zmfp = 3.0_wp * zdfvap * SQRT( pi * amh2so4 / ( 8.0_wp * argas * ptemp ) ) 4357 !-- Knudsen number 4358 zknud = 2.0_wp * zmfp / ( paero(:)%dwet + d_sa ) 4359 !-- Transitional regime correction factor (zbeta) according to Fuchs and 4360 !-- Sutugin (1971), In: Hidy et al. (ed.), Topics in current aerosol research, 4361 !-- Pergamon. (Eq. 4 in Kerminen and Kulmala, 2002) 4362 zbeta = ( zknud + 1.0_wp) / ( 0.377_wp * zknud + 1.0_wp + 4.0_wp / & 4363 ( 3.0_wp * massacc ) * ( zknud + zknud ** 2 ) ) 4364 !-- Condensational sink (#/m2) (Eq. 3) 4531 ! 4532 !-- Knudsen number 4533 zknud = 2.0_wp * zmfp / ( paero(:)%dwet + d_sa ) 4534 ! 4535 !-- Transitional regime correction factor (zbeta) according to Fuchs and Sutugin (1971) (Eq. 4 in 4536 !-- Kerminen and Kulmala, 2002) 4537 zbeta = ( zknud + 1.0_wp) / ( 0.377_wp * zknud + 1.0_wp + 4.0_wp / ( 3.0_wp * massacc ) * & 4538 ( zknud + zknud**2 ) ) 4539 ! 4540 !-- Condensational sink (#/m2, Eq. 3) 4365 4541 zcsink = SUM( paero(:)%dwet * zbeta * paero(:)%numc ) 4366 4542 ! 4367 !-- Parameterised formation rate of detectable 3 nm particles (i.e. J3)4543 !-- 2.2.3) Parameterised formation rate of detectable 3 nm particles (i.e. J3) 4368 4544 IF ( nj3 == 1 ) THEN ! Kerminen and Kulmala (2002) 4369 !-- 2.2.3) Parameterised formation rate of detectable 3 nm particles 4370 !-- Constants needed for the parameterisation: 4371 !-- dapp = 3 nm and dens_nuc = 1830 kg/m3 4372 IF ( zcsink < 1.0E-30_wp ) THEN 4545 ! 4546 !-- Constants needed for the parameterisation: dapp = 3 nm and dens_nuc = 1830 kg/m3 4547 IF ( zcsink < 1.0E-30_wp ) THEN 4373 4548 zeta = 0._dp 4374 4549 ELSE 4550 ! 4375 4551 !-- Mean diameter of backgroud population (nm) 4376 zdmean = 1.0_wp / SUM( paero(:)%numc ) * SUM( paero(:)%numc * &4377 paero(:)%dwet ) * 1.0E+9_wp 4552 zdmean = 1.0_wp / SUM( paero(:)%numc ) * SUM( paero(:)%numc * paero(:)%dwet ) * 1.0E+9_wp 4553 ! 4378 4554 !-- Proportionality factor (nm2*m2/h) (Eq. 22) 4379 zgamma = 0.23_wp * ( zdcrit * 1.0E+9_wp ) ** 0.2_wp * ( zdmean / & 4380 150.0_wp ) ** 0.048_wp * ( ptemp / 293.0_wp ) ** ( -0.75_wp ) & 4381 * ( arhoh2so4 / 1000.0_wp ) ** ( -0.33_wp ) 4382 !-- Factor eta (nm) (Eq. 11) 4383 zeta = MIN( zgamma * zcsink / zGRclust, zdcrit * 1.0E11_wp ) 4384 ENDIF 4385 ! 4386 !-- Number conc. of clusters surviving to 3 nm in a time step (#/m3) (Eq.14) 4387 zj3 = zjnuc * EXP( MIN( 0.0_wp, zeta / 3.0_wp - zeta / & 4388 ( zdcrit * 1.0E9_wp ) ) ) 4389 4390 ELSEIF ( nj3 > 1 ) THEN 4391 !-- Defining the value for zm_para. The growth is investigated between 4392 !-- [d1,reglim(1)] = [zdcrit,3nm] 4393 !-- m = LOG( CoagS_dx / CoagX_zdcrit ) / LOG( reglim / zdcrit ) 4394 !-- (Lehtinen et al. 2007, Eq. 5) 4395 !-- The steps for the coagulation sink for reglim = 3nm and zdcrit ~= 1nm are 4396 !-- explained in article of Kulmala et al. (2001). The particles of diameter 4397 !-- zdcrit ~1.14 nm and reglim = 3nm are both in turn the "number 1" 4398 !-- variables (Kulmala et al. 2001). 4555 zgamma = 0.23_wp * ( zdcrit * 1.0E+9_wp )**0.2_wp * ( zdmean / 150.0_wp )**0.048_wp * & 4556 ( ptemp / 293.0_wp )**( -0.75_wp ) * ( arhoh2so4 / 1000.0_wp )**( -0.33_wp ) 4557 ! 4558 !-- Factor eta (nm, Eq. 11) 4559 zeta = MIN( zgamma * zcsink / z_gr_clust, zdcrit * 1.0E11_wp ) 4560 ENDIF 4561 ! 4562 !-- Number conc. of clusters surviving to 3 nm in a time step (#/m3, Eq.14) 4563 zj3 = zjnuc * EXP( MIN( 0.0_wp, zeta / 3.0_wp - zeta / ( zdcrit * 1.0E9_wp ) ) ) 4564 4565 ELSEIF ( nj3 > 1 ) THEN ! Lehtinen et al. (2007) or Anttila et al. (2010) 4566 ! 4567 !-- Defining the parameter m (zm_para) for calculating the coagulation sink onto background 4568 !-- particles (Eq. 5&6 in Lehtinen et al. 2007). The growth is investigated between 4569 !-- [d1,reglim(1)] = [zdcrit,3nm] and m = LOG( CoagS_dx / CoagX_zdcrit ) / LOG( reglim / zdcrit ) 4570 !-- (Lehtinen et al. 2007, Eq. 6). 4571 !-- The steps for the coagulation sink for reglim = 3nm and zdcrit ~= 1nm are explained in 4572 !-- Kulmala et al. (2001). The particles of diameter zdcrit ~1.14 nm and reglim = 3nm are both 4573 !-- in turn the "number 1" variables (Kulmala et al. 2001). 4399 4574 !-- c = critical (1nm), x = 3nm, 2 = wet or mean droplet 4400 !-- Sum of the radii, R12 = R1 + zR2 (m) of two particles 1 and 2 4401 zRc2 = zdcrit / 2.0_wp + paero(:)%dwet / 2.0_wp 4402 zRx2 = reglim(1) / 2.0_wp + paero(:)%dwet / 2.0_wp 4403 ! 4404 !-- The mass of particle (kg) (comes only from H2SO4) 4405 zm_c = 4.0_wp / 3.0_wp * pi * ( zdcrit / 2.0_wp ) ** 3.0_wp * arhoh2so4 4406 zm_x = 4.0_wp / 3.0_wp * pi * ( reglim(1) / 2.0_wp ) ** 3.0_wp * & 4407 arhoh2so4 4408 zm_2 = 4.0_wp / 3.0_wp * pi * ( paero(:)%dwet / 2.0_wp )** 3.0_wp * & 4409 arhoh2so4 4410 ! 4575 ! 4576 !-- Sum of the radii, R12 = R1 + R2 (m) of two particles 1 and 2 4577 z_r_c2 = zdcrit / 2.0_wp + paero(:)%dwet / 2.0_wp 4578 z_r_x2 = reglim(1) / 2.0_wp + paero(:)%dwet / 2.0_wp 4579 ! 4580 !-- Particle mass (kg) (comes only from H2SO4) 4581 zm_c = 4.0_wp / 3.0_wp * pi * ( zdcrit / 2.0_wp )**3 * arhoh2so4 4582 zm_x = 4.0_wp / 3.0_wp * pi * ( reglim(1) / 2.0_wp )**3 * arhoh2so4 4583 zm_2 = 4.0_wp / 3.0_wp * pi * ( 0.5_wp * paero(:)%dwet )**3 * arhoh2so4 4584 ! 4411 4585 !-- Mean relative thermal velocity between the particles (m/s) 4412 4586 zcv_c = SQRT( 8.0_wp * abo * ptemp / ( pi * zm_c ) ) 4413 4587 zcv_x = SQRT( 8.0_wp * abo * ptemp / ( pi * zm_x ) ) 4414 4588 zcv_2 = SQRT( 8.0_wp * abo * ptemp / ( pi * zm_2 ) ) 4415 ! 4416 !-- Average velocity after coagulation 4417 zcv_c2 = SQRT( zcv_c ** 2.0_wp + zcv_2 ** 2.0_wp)4418 zcv_x2 = SQRT( zcv_x ** 2.0_wp + zcv_2 ** 2.0_wp)4419 ! 4589 ! 4590 !-- Average velocity after coagulation 4591 zcv_c2(:) = SQRT( zcv_c**2 + zcv_2**2 ) 4592 zcv_x2(:) = SQRT( zcv_x**2 + zcv_2**2 ) 4593 ! 4420 4594 !-- Knudsen number (zmfp = mean free path of condensing vapour) 4421 4595 zknud_c = 2.0_wp * zmfp / zdcrit 4422 4596 zknud_x = 2.0_wp * zmfp / reglim(1) 4423 zknud_2 = MAX( 0.0_wp, 2.0_wp * zmfp / paero(:)%dwet ) 4424 ! 4425 !-- Cunningham correction factor 4426 zCc_c = 1.0_wp + zknud_c * ( 1.142_wp + 0.558_wp * & 4427 EXP( -0.999_wp / zknud_c ) ) 4428 zCc_x = 1.0_wp + zknud_x * ( 1.142_wp + 0.558_wp * & 4429 EXP( -0.999_wp / zknud_x ) ) 4430 zCc_2 = 1.0_wp + zknud_2 * ( 1.142_wp + 0.558_wp * & 4431 EXP( -0.999_wp / zknud_2 ) ) 4432 ! 4433 !-- Gas dynamic viscosity (N*s/m2). 4434 !-- Viscocity(air @20C) = 1.81e-5_dp N/m2 *s (Hinds, p. 25) 4435 zmyy = 1.81E-5_wp * ( ptemp / 293.0_wp) ** ( 0.74_wp ) 4436 ! 4437 !-- Particle diffusion coefficient (m2/s) 4438 zDc_c = abo * ptemp * zCc_c / ( 3.0_wp * pi * zmyy * zdcrit ) 4439 zDc_x = abo * ptemp * zCc_x / ( 3.0_wp * pi * zmyy * reglim(1) ) 4440 zDc_2 = abo * ptemp * zCc_2 / ( 3.0_wp * pi * zmyy * paero(:)%dwet ) 4441 ! 4597 zknud_2(:) = MAX( 0.0_wp, 2.0_wp * zmfp / paero(:)%dwet ) 4598 ! 4599 !-- Cunningham correction factors (Allen and Raabe, 1985) 4600 zcc_c = 1.0_wp + zknud_c * ( 1.142_wp + 0.558_wp * EXP( -0.999_wp / zknud_c ) ) 4601 zcc_x = 1.0_wp + zknud_x * ( 1.142_wp + 0.558_wp * EXP( -0.999_wp / zknud_x ) ) 4602 zcc_2(:) = 1.0_wp + zknud_2(:) * ( 1.142_wp + 0.558_wp * EXP( -0.999_wp / zknud_2(:) ) ) 4603 ! 4604 !-- Gas dynamic viscosity (N*s/m2). Here, viscocity(air @20C) = 1.81e-5_dp N/m2 *s (Hinds, p. 25) 4605 zmyy = 1.81E-5_wp * ( ptemp / 293.0_wp )**0.74_wp 4606 ! 4607 !-- Particle diffusion coefficient (m2/s) (continuum regime) 4608 zdc_c(:) = abo * ptemp * zcc_c / ( 3.0_wp * pi * zmyy * zdcrit ) 4609 zdc_x(:) = abo * ptemp * zcc_x / ( 3.0_wp * pi * zmyy * reglim(1) ) 4610 zdc_2(:) = abo * ptemp * zcc_2(:) / ( 3.0_wp * pi * zmyy * paero(:)%dwet ) 4611 ! 4442 4612 !-- D12 = D1+D2 (Seinfield and Pandis, 2nd ed. Eq. 13.38) 4443 zDc_c2 = zDc_c + zDc_2 4444 zDc_x2 = zDc_x + zDc_2 4445 ! 4446 !-- zgammaF = 8*D/pi/zcv (m) for calculating zomega 4447 zgammaF_c = 8.0_wp * zDc_c / pi / zcv_c 4448 zgammaF_x = 8.0_wp * zDc_x / pi / zcv_x 4449 zgammaF_2 = 8.0_wp * zDc_2 / pi / zcv_2 4450 ! 4451 !-- zomega (m) for calculating zsigma 4452 zomega_c = ( ( zRc2 + zgammaF_c ) ** 3 - ( zRc2 ** 2 + & 4453 zgammaF_c ) ** ( 3.0_wp / 2.0_wp ) ) / ( 3.0_wp * & 4454 zRc2 * zgammaF_c ) - zRc2 4455 zomega_x = ( ( zRx2 + zgammaF_x ) ** 3.0_wp - ( zRx2 ** 2.0_wp + & 4456 zgammaF_x ) ** ( 3.0_wp / 2.0_wp ) ) / ( 3.0_wp * & 4457 zRx2 * zgammaF_x ) - zRx2 4458 zomega_2c = ( ( zRc2 + zgammaF_2 ) ** 3.0_wp - ( zRc2 ** 2.0_wp + & 4459 zgammaF_2 ) ** ( 3.0_wp / 2.0_wp ) ) / ( 3.0_wp * & 4460 zRc2 * zgammaF_2 ) - zRc2 4461 zomega_2x = ( ( zRx2 + zgammaF_2 ) ** 3.0_wp - ( zRx2 ** 2.0_wp + & 4462 zgammaF_2 ) ** ( 3.0_wp / 2.0_wp ) ) / ( 3.0_wp * & 4463 zRx2 * zgammaF_2 ) - zRx2 4464 ! 4465 !-- The distance (m) at which the two fluxes are matched (condensation and 4466 !-- coagulation sinks?) 4467 zsigma_c2 = SQRT( zomega_c ** 2.0_wp + zomega_2c ** 2.0_wp ) 4468 zsigma_x2 = SQRT( zomega_x ** 2.0_wp + zomega_2x ** 2.0_wp ) 4469 ! 4470 !-- Coagulation coefficient in the continuum regime (m*m2/s) 4471 zK_c2 = 4.0_wp * pi * zRc2 * zDc_c2 / ( zRc2 / ( zRc2 + zsigma_c2 ) + & 4472 4.0_wp * zDc_c2 / ( zcv_c2 * zRc2 ) ) 4473 zK_x2 = 4.0_wp * pi * zRx2 * zDc_x2 / ( zRx2 / ( zRx2 + zsigma_x2 ) + & 4474 4.0_wp * zDc_x2 / ( zcv_x2 * zRx2 ) ) 4475 ! 4476 !-- Coagulation sink (1/s) 4477 zCoagS_c = MAX( 1.0E-20_wp, SUM( zK_c2 * paero(:)%numc ) ) 4478 zCoagS_x = MAX( 1.0E-20_wp, SUM( zK_x2 * paero(:)%numc ) ) 4479 ! 4480 !-- Parameter m for calculating the coagulation sink onto background 4481 !-- particles (Eq. 5&6 in Lehtinen et al. 2007) 4482 zm_para = LOG( zCoagS_x / zCoagS_c ) / LOG( reglim(1) / zdcrit ) 4483 ! 4613 zdc_c2 = zdc_c + zdc_2 4614 zdc_x2 = zdc_x + zdc_2 4615 ! 4616 !-- zgamma_f = 8*D/pi/zcv (m) for calculating zomega (Fuchs, 1964) 4617 zgamma_f_c = 8.0_wp * zdc_c / pi / zcv_c 4618 zgamma_f_x = 8.0_wp * zdc_x / pi / zcv_x 4619 zgamma_f_2 = 8.0_wp * zdc_2 / pi / zcv_2 4620 ! 4621 !-- zomega (m) for calculating zsigma 4622 zomega_c = ( ( z_r_c2 + zgamma_f_c )**3 - ( z_r_c2 ** 2 + zgamma_f_c )**1.5_wp ) / & 4623 ( 3.0_wp * z_r_c2 * zgamma_f_c ) - z_r_c2 4624 zomega_x = ( ( z_r_x2 + zgamma_f_x )**3 - ( z_r_x2**2 + zgamma_f_x )** 1.5_wp ) / & 4625 ( 3.0_wp * z_r_x2 * zgamma_f_x ) - z_r_x2 4626 zomega_2c = ( ( z_r_c2 + zgamma_f_2 )**3 - ( z_r_c2**2 + zgamma_f_2 )**1.5_wp ) / & 4627 ( 3.0_wp * z_r_c2 * zgamma_f_2 ) - z_r_c2 4628 zomega_2x = ( ( z_r_x2 + zgamma_f_2 )**3 - ( z_r_x2**2 + zgamma_f_2 )**1.5_wp ) / & 4629 ( 3.0_wp * z_r_x2 * zgamma_f_2 ) - z_r_x2 4630 ! 4631 !-- The distance (m) at which the two fluxes are matched (condensation and coagulation sinks) 4632 zsigma_c2 = SQRT( zomega_c**2 + zomega_2c**2 ) 4633 zsigma_x2 = SQRT( zomega_x**2 + zomega_2x**2 ) 4634 ! 4635 !-- Coagulation coefficient in the continuum regime (m*m2/s, Eq. 17 in Kulmala et al., 2001) 4636 z_k_c2 = 4.0_wp * pi * z_r_c2 * zdc_c2 / ( z_r_c2 / ( z_r_c2 + zsigma_c2 ) + & 4637 4.0_wp * zdc_c2 / ( zcv_c2 * z_r_c2 ) ) 4638 z_k_x2 = 4.0_wp * pi * z_r_x2 * zdc_x2 / ( z_r_x2 / ( z_r_x2 + zsigma_x2 ) + & 4639 4.0_wp * zdc_x2 / ( zcv_x2 * z_r_x2 ) ) 4640 ! 4641 !-- Coagulation sink (1/s, Eq. 16 in Kulmala et al., 2001) 4642 zcoags_c = MAX( 1.0E-20_wp, SUM( z_k_c2 * paero(:)%numc ) ) 4643 zcoags_x = MAX( 1.0E-20_wp, SUM( z_k_x2 * paero(:)%numc ) ) 4644 ! 4645 !-- Parameter m for calculating the coagulation sink onto background particles (Eq. 5&6 in 4646 !-- Lehtinen et al. 2007) 4647 zm_para = LOG( zcoags_x / zcoags_c ) / LOG( reglim(1) / zdcrit ) 4648 ! 4484 4649 !-- Parameter gamma for calculating the formation rate J of particles having 4485 !-- a diameter zdcrit < d < reglim(1) (Anttila et al. 2010, eq. 5) 4486 zgamma = ( ( ( reglim(1) / zdcrit ) ** ( zm_para + 1.0_wp ) ) - 1.0_wp )& 4487 / ( zm_para + 1.0_wp ) 4488 4489 IF ( nj3 == 2 ) THEN ! Coagulation sink 4490 ! 4491 !-- Formation rate J before iteration (#/m3s) 4492 zj3 = zjnuc * EXP( MIN( 0.0_wp, -zgamma * zdcrit * zCoagS_c / & 4493 ( zGRclust * 1.0E-9_wp / ( 60.0_wp ** 2.0_wp ) ) ) ) 4494 4495 ELSEIF ( nj3 == 3 ) THEN ! Coagulation sink and self-coag. 4496 !-- IF polluted air... then the self-coagulation becomes important. 4497 !-- Self-coagulation of small particles < 3 nm. 4498 ! 4499 !-- "Effective" coagulation coefficient between freshly-nucleated 4500 !-- particles: 4501 zKeff = 5.0E-16_wp ! cm3/s 4502 ! 4503 !-- zlambda parameter for "adjusting" the growth rate due to the 4504 !-- self-coagulation 4505 zlambda = 6.0_wp 4650 !-- a diameter zdcrit < d < reglim(1) (Anttila et al. 2010, eq. 5 or Lehtinen et al.,2007, eq. 7) 4651 zgamma = ( ( ( reglim(1) / zdcrit )**( zm_para + 1.0_wp ) ) - 1.0_wp ) / ( zm_para + 1.0_wp ) 4652 4653 IF ( nj3 == 2 ) THEN ! Lehtinen et al. (2007): coagulation sink 4654 ! 4655 !-- Formation rate J before iteration (#/m3s) 4656 zj3 = zjnuc * EXP( MIN( 0.0_wp, -zgamma * zdcrit * zcoags_c / ( z_gr_clust * 1.0E-9_wp / & 4657 60.0_wp**2 ) ) ) 4658 4659 ELSEIF ( nj3 == 3 ) THEN ! Anttila et al. (2010): coagulation sink and self-coag. 4660 ! 4661 !-- If air is polluted, the self-coagulation becomes important. Self-coagulation of small 4662 !-- particles < 3 nm. 4663 ! 4664 !-- "Effective" coagulation coefficient between freshly-nucleated particles: 4665 z_k_eff = 5.0E-16_wp ! m3/s 4666 ! 4667 !-- zlambda parameter for "adjusting" the growth rate due to the self-coagulation 4668 zlambda = 6.0_wp 4669 4506 4670 IF ( reglim(1) >= 10.0E-9_wp ) THEN ! for particles >10 nm: 4507 z Keff = 5.0E-17_wp4671 z_k_eff = 5.0E-17_wp 4508 4672 zlambda = 3.0_wp 4509 4673 ENDIF 4510 ! 4674 ! 4511 4675 !-- Initial values for coagulation sink and growth rate (m/s) 4512 z CoagStot = zCoagS_c4513 z GRtot = zGRclust * 1.0E-9_wp / 60.0_wp ** 2.0_wp4514 ! 4676 zcoagstot = zcoags_c 4677 z_gr_tot = z_gr_clust * 1.0E-9_wp / 60.0_wp**2 4678 ! 4515 4679 !-- Number of clusters/particles at the size range [d1,dx] (#/m3): 4516 z Nnuc = zjnuc / zCoagStot !< Initial guess4517 ! 4680 z_n_nuc = zjnuc / zcoagstot !< Initial guess 4681 ! 4518 4682 !-- Coagulation sink and growth rate due to self-coagulation: 4519 4683 DO iteration = 1, 5 4520 zCoagStot = zCoagS_c + zKeff * zNnuc * 1.0E-6_wp ! (1/s) 4521 zGRtot = zGRclust * 1.0E-9_wp / ( 3600.0_wp ) + 1.5708E-6_wp * & 4522 zlambda * zdcrit ** 3.0_wp * ( zNnuc * 1.0E-6_wp ) * & 4523 zcv_c * avo * 1.0E-9_wp / 3600.0_wp 4524 zeta = - zCoagStot / ( ( zm_para + 1.0_wp ) * zGRtot * ( zdcrit **& 4525 zm_para ) ) ! Eq. 7b (Anttila) 4526 zNnuc = zNnuc_tayl( zdcrit, reglim(1), zm_para, zjnuc, zeta, & 4527 zGRtot ) 4684 zcoagstot = zcoags_c + z_k_eff * z_n_nuc * 1.0E-6_wp ! (1/s, Anttila et al., eq. 1) 4685 z_gr_tot = z_gr_clust * 2.77777777E-7_wp + 1.5708E-6_wp * zlambda * zdcrit**3 * & 4686 ( z_n_nuc * 1.0E-6_wp ) * zcv_c * avo * 2.77777777E-7_wp ! (Eq. 3) 4687 zeta = - zcoagstot / ( ( zm_para + 1.0_wp ) * z_gr_tot * ( zdcrit**zm_para ) ) ! (Eq. 7b) 4688 ! 4689 !-- Calculate Eq. 7a (Taylor series for the number of particles between [d1,dx]) 4690 z_n_nuc = z_n_nuc_tayl( zdcrit, reglim(1), zm_para, zjnuc, zeta, z_gr_tot ) 4528 4691 ENDDO 4529 ! 4530 !-- Calculate the final values with new zNnuc: 4531 zCoagStot = zCoagS_c + zKeff * zNnuc * 1.0E-6_wp ! (1/s) 4532 zGRtot = zGRclust * 1.0E-9_wp / 3600.0_wp + 1.5708E-6_wp * zlambda & 4533 * zdcrit ** 3.0_wp * ( zNnuc * 1.0E-6_wp ) * zcv_c * avo * & 4534 1.0E-9_wp / 3600.0_wp !< (m/s) 4535 zj3 = zjnuc * EXP( MIN( 0.0_wp, -zgamma * zdcrit * zCoagStot / & 4536 zGRtot ) ) ! (Eq. 5a) (#/m3s) 4537 4538 ENDIF 4539 4692 ! 4693 !-- Calculate the final values with new z_n_nuc: 4694 zcoagstot = zcoags_c + z_k_eff * z_n_nuc * 1.0E-6_wp ! (1/s) 4695 z_gr_tot = z_gr_clust * 1.0E-9_wp / 3600.0_wp + 1.5708E-6_wp * zlambda * zdcrit**3 * & 4696 ( z_n_nuc * 1.0E-6_wp ) * zcv_c * avo * 1.0E-9_wp / 3600.0_wp !< (m/s) 4697 zj3 = zjnuc * EXP( MIN( 0.0_wp, -zgamma * zdcrit * zcoagstot / z_gr_tot ) ) ! (#/m3s, Eq. 5a) 4698 4699 ENDIF 4540 4700 ENDIF 4541 !-- If J3 very small (< 1 #/cm3), neglect particle formation. In real atmosphere 4542 !-- this would mean that clusters form but coagulate to pre-existing particles 4543 !-- who gain sulphate. Since CoagS ~ CS (4piD*CS'), we do *not* update H2SO4 4544 !-- concentration here but let condensation take care of it. 4545 !-- Formation mass rate of molecules (molec/m3s) for 1: H2SO4 and 2: organic 4546 !-- vapour 4701 ! 4702 !-- If J3 very small (< 1 #/cm3), neglect particle formation. In real atmosphere this would mean 4703 !-- that clusters form but coagulate to pre-existing particles who gain sulphate. Since 4704 !-- CoagS ~ CS (4piD*CS'), we do *not* update H2SO4 concentration here but let condensation take 4705 !-- care of it. Formation mass rate of molecules (molec/m3s) for 1: H2SO4 and 2: organic vapour 4547 4706 pj3n3(1) = zj3 * n3 * pxsa 4548 4707 pj3n3(2) = zj3 * n3 * pxocnv 4549 4550 4708 4551 4709 END SUBROUTINE nucleation 4552 4710 … … 4555 4713 ! ------------ 4556 4714 !> Calculate the nucleation rate and the size of critical clusters assuming 4557 !> binary nucleation. 4715 !> binary nucleation. 4558 4716 !> Parametrisation according to Vehkamaki et al. (2002), J. Geophys. Res., 4559 4717 !> 107(D22), 4622. Called from subroutine nucleation. 4560 4718 !------------------------------------------------------------------------------! 4561 SUBROUTINE binnucl( pc_sa, ptemp, prh, pnuc_rate, pn_crit_sa, pn_crit_ocnv, &4562 p d_crit, pk_sa, pk_ocnv )4563 4719 SUBROUTINE binnucl( pc_sa, ptemp, prh, pnuc_rate, pn_crit_sa, pn_crit_ocnv, pd_crit, pk_sa, & 4720 pk_ocnv ) 4721 4564 4722 IMPLICIT NONE 4565 ! 4566 !-- Input and output variables 4567 REAL(wp), INTENT(in) :: pc_sa !< H2SO4 conc. (#/cm3) 4568 REAL(wp), INTENT(in) :: prh !< relative humidity [0-1] 4569 REAL(wp), INTENT(in) :: ptemp !< ambient temperature (K) 4570 REAL(wp), INTENT(out) :: pnuc_rate !< nucleation rate (#/(m3 s)) 4571 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in 4572 !< cluster (#) 4573 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in 4574 !< cluster (#) 4575 REAL(wp), INTENT(out) :: pd_crit !< diameter of critical cluster (m) 4576 REAL(wp), INTENT(out) :: pk_sa !< Lever: if pk_sa = 1, H2SO4 is 4577 !< involved in nucleation. 4578 REAL(wp), INTENT(out) :: pk_ocnv !< Lever: if pk_ocnv = 1, organic 4579 !< compounds are involved in 4580 !< nucleation. 4581 !-- Local variables 4582 REAL(wp) :: zx !< mole fraction of sulphate in critical cluster 4583 REAL(wp) :: zntot !< number of molecules in critical cluster 4584 REAL(wp) :: zt !< temperature 4585 REAL(wp) :: zpcsa !< sulfuric acid concentration 4586 REAL(wp) :: zrh !< relative humidity 4587 REAL(wp) :: zma !< 4588 REAL(wp) :: zmw !< 4589 REAL(wp) :: zxmass!< 4590 REAL(wp) :: za !< 4591 REAL(wp) :: zb !< 4592 REAL(wp) :: zc !< 4593 REAL(wp) :: zroo !< 4594 REAL(wp) :: zm1 !< 4595 REAL(wp) :: zm2 !< 4596 REAL(wp) :: zv1 !< 4597 REAL(wp) :: zv2 !< 4598 REAL(wp) :: zcoll !< 4599 4723 4724 REAL(wp) :: za !< 4725 REAL(wp) :: zb !< 4726 REAL(wp) :: zc !< 4727 REAL(wp) :: zcoll !< 4728 REAL(wp) :: zlogsa !< LOG( zpcsa ) 4729 REAL(wp) :: zlogrh !< LOG( zrh ) 4730 REAL(wp) :: zm1 !< 4731 REAL(wp) :: zm2 !< 4732 REAL(wp) :: zma !< 4733 REAL(wp) :: zmw !< 4734 REAL(wp) :: zntot !< number of molecules in critical cluster 4735 REAL(wp) :: zpcsa !< sulfuric acid concentration 4736 REAL(wp) :: zrh !< relative humidity 4737 REAL(wp) :: zroo !< 4738 REAL(wp) :: zt !< temperature 4739 REAL(wp) :: zv1 !< 4740 REAL(wp) :: zv2 !< 4741 REAL(wp) :: zx !< mole fraction of sulphate in critical cluster 4742 REAL(wp) :: zxmass !< 4743 4744 REAL(wp), INTENT(in) :: pc_sa !< H2SO4 conc. (#/cm3) 4745 REAL(wp), INTENT(in) :: prh !< relative humidity [0-1 4746 REAL(wp), INTENT(in) :: ptemp !< ambient temperature (K) 4747 4748 REAL(wp), INTENT(out) :: pnuc_rate !< nucleation rate (#/(m3 s)) 4749 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in cluster (#) 4750 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in cluster (#) 4751 REAL(wp), INTENT(out) :: pd_crit !< diameter of critical cluster (m) 4752 REAL(wp), INTENT(out) :: pk_sa !< Lever: if pk_sa = 1, H2SO4 is involved in nucleation. 4753 REAL(wp), INTENT(out) :: pk_ocnv !< Lever: if pk_ocnv = 1, organic compounds are involved 4754 4600 4755 pnuc_rate = 0.0_wp 4601 4756 pd_crit = 1.0E-9_wp 4602 4603 ! 4604 !-- 1) Checking that we are in the validity range of the parameterization 4605 zt = MAX( ptemp, 190.15_wp ) 4606 zt = MIN( zt, 300.15_wp ) 4607 zpcsa = MAX( pc_sa, 1.0E4_wp ) 4608 zpcsa = MIN( zpcsa, 1.0E11_wp ) 4609 zrh = MAX( prh, 0.0001_wp ) 4610 zrh = MIN( zrh, 1.0_wp ) 4611 ! 4757 ! 4758 !-- 1) Checking that we are in the validity range of the parameterization 4759 zpcsa = MAX( pc_sa, 1.0E4_wp ) 4760 zpcsa = MIN( zpcsa, 1.0E11_wp ) 4761 zrh = MAX( prh, 0.0001_wp ) 4762 zrh = MIN( zrh, 1.0_wp ) 4763 zt = MAX( ptemp, 190.15_wp ) 4764 zt = MIN( zt, 300.15_wp ) 4765 4766 zlogsa = LOG( zpcsa ) 4767 zlogrh = LOG( prh ) 4768 ! 4612 4769 !-- 2) Mole fraction of sulphate in a critical cluster (Eq. 11) 4613 zx = 0.7409967177282139_wp & 4614 - 0.002663785665140117_wp * zt & 4615 + 0.002010478847383187_wp * LOG( zrh ) & 4616 - 0.0001832894131464668_wp* zt * LOG( zrh ) & 4617 + 0.001574072538464286_wp * LOG( zrh ) ** 2 & 4618 - 0.00001790589121766952_wp * zt * LOG( zrh ) ** 2 & 4619 + 0.0001844027436573778_wp * LOG( zrh ) ** 3 & 4620 - 1.503452308794887E-6_wp * zt * LOG( zrh ) ** 3 & 4621 - 0.003499978417957668_wp * LOG( zpcsa ) & 4622 + 0.0000504021689382576_wp * zt * LOG( zpcsa ) 4623 ! 4770 zx = 0.7409967177282139_wp - 0.002663785665140117_wp * zt + & 4771 0.002010478847383187_wp * zlogrh - 0.0001832894131464668_wp* zt * zlogrh + & 4772 0.001574072538464286_wp * zlogrh**2 - 0.00001790589121766952_wp * zt * zlogrh**2 + & 4773 0.0001844027436573778_wp * zlogrh**3 - 1.503452308794887E-6_wp * zt * zlogrh**3 - & 4774 0.003499978417957668_wp * zlogsa + 0.0000504021689382576_wp * zt * zlogsa 4775 ! 4624 4776 !-- 3) Nucleation rate (Eq. 12) 4625 pnuc_rate = 0.1430901615568665_wp & 4626 + 2.219563673425199_wp * zt & 4627 - 0.02739106114964264_wp * zt ** 2 & 4628 + 0.00007228107239317088_wp * zt ** 3 & 4629 + 5.91822263375044_wp / zx & 4630 + 0.1174886643003278_wp * LOG( zrh ) & 4631 + 0.4625315047693772_wp * zt * LOG( zrh ) & 4632 - 0.01180591129059253_wp * zt ** 2 * LOG( zrh ) & 4633 + 0.0000404196487152575_wp * zt ** 3 * LOG( zrh ) & 4634 + ( 15.79628615047088_wp * LOG( zrh ) ) / zx & 4635 - 0.215553951893509_wp * LOG( zrh ) ** 2 & 4636 - 0.0810269192332194_wp * zt * LOG( zrh ) ** 2 & 4637 + 0.001435808434184642_wp * zt ** 2 * LOG( zrh ) ** 2 & 4638 - 4.775796947178588E-6_wp * zt ** 3 * LOG( zrh ) ** 2 & 4639 - (2.912974063702185_wp * LOG( zrh ) ** 2 ) / zx & 4640 - 3.588557942822751_wp * LOG( zrh ) ** 3 & 4641 + 0.04950795302831703_wp * zt * LOG( zrh ) ** 3 & 4642 - 0.0002138195118737068_wp * zt ** 2 * LOG( zrh ) ** 3 & 4643 + 3.108005107949533E-7_wp * zt ** 3 * LOG( zrh ) ** 3 & 4644 - ( 0.02933332747098296_wp * LOG( zrh ) ** 3 ) / zx & 4645 + 1.145983818561277_wp * LOG( zpcsa ) & 4646 - 0.6007956227856778_wp * zt * LOG( zpcsa ) & 4647 + 0.00864244733283759_wp * zt ** 2 * LOG( zpcsa ) & 4648 - 0.00002289467254710888_wp * zt ** 3 * LOG( zpcsa ) & 4649 - ( 8.44984513869014_wp * LOG( zpcsa ) ) / zx & 4650 + 2.158548369286559_wp * LOG( zrh ) * LOG( zpcsa ) & 4651 + 0.0808121412840917_wp * zt * LOG( zrh ) * LOG( zpcsa ) & 4652 - 0.0004073815255395214_wp * zt ** 2 * LOG( zrh ) * LOG( zpcsa ) & 4653 - 4.019572560156515E-7_wp * zt ** 3 * LOG( zrh ) * LOG( zpcsa ) & 4654 + ( 0.7213255852557236_wp * LOG( zrh ) * LOG( zpcsa ) ) / zx & 4655 + 1.62409850488771_wp * LOG( zrh ) ** 2 * LOG( zpcsa ) & 4656 - 0.01601062035325362_wp * zt * LOG( zrh ) ** 2 * LOG( zpcsa ) & 4657 + 0.00003771238979714162_wp*zt**2* LOG( zrh )**2 * LOG( zpcsa ) & 4658 + 3.217942606371182E-8_wp * zt**3 * LOG( zrh )**2 * LOG( zpcsa ) & 4659 - (0.01132550810022116_wp * LOG( zrh )**2 * LOG( zpcsa ) ) / zx & 4660 + 9.71681713056504_wp * LOG( zpcsa ) ** 2 & 4661 - 0.1150478558347306_wp * zt * LOG( zpcsa ) ** 2 & 4662 + 0.0001570982486038294_wp * zt ** 2 * LOG( zpcsa ) ** 2 & 4663 + 4.009144680125015E-7_wp * zt ** 3 * LOG( zpcsa ) ** 2 & 4664 + ( 0.7118597859976135_wp * LOG( zpcsa ) ** 2 ) / zx & 4665 - 1.056105824379897_wp * LOG( zrh ) * LOG( zpcsa ) ** 2 & 4666 + 0.00903377584628419_wp * zt * LOG( zrh ) * LOG( zpcsa )**2 & 4667 - 0.00001984167387090606_wp*zt**2*LOG( zrh )*LOG( zpcsa )**2 & 4668 + 2.460478196482179E-8_wp * zt**3 * LOG( zrh ) * LOG( zpcsa )**2 & 4669 - ( 0.05790872906645181_wp * LOG( zrh ) * LOG( zpcsa )**2 ) / zx & 4670 - 0.1487119673397459_wp * LOG( zpcsa ) ** 3 & 4671 + 0.002835082097822667_wp * zt * LOG( zpcsa ) ** 3 & 4672 - 9.24618825471694E-6_wp * zt ** 2 * LOG( zpcsa ) ** 3 & 4673 + 5.004267665960894E-9_wp * zt ** 3 * LOG( zpcsa ) ** 3 & 4674 - ( 0.01270805101481648_wp * LOG( zpcsa ) ** 3 ) / zx 4675 ! 4777 pnuc_rate = 0.1430901615568665_wp + 2.219563673425199_wp * zt - & 4778 0.02739106114964264_wp * zt**2 + 0.00007228107239317088_wp * zt**3 + & 4779 5.91822263375044_wp / zx + 0.1174886643003278_wp * zlogrh + & 4780 0.4625315047693772_wp * zt * zlogrh - 0.01180591129059253_wp * zt**2 * zlogrh + & 4781 0.0000404196487152575_wp * zt**3 * zlogrh + & 4782 ( 15.79628615047088_wp * zlogrh ) / zx - 0.215553951893509_wp * zlogrh**2 - & 4783 0.0810269192332194_wp * zt * zlogrh**2 + & 4784 0.001435808434184642_wp * zt**2 * zlogrh**2 - & 4785 4.775796947178588E-6_wp * zt**3 * zlogrh**2 - & 4786 ( 2.912974063702185_wp * zlogrh**2 ) / zx - 3.588557942822751_wp * zlogrh**3 + & 4787 0.04950795302831703_wp * zt * zlogrh**3 - & 4788 0.0002138195118737068_wp * zt**2 * zlogrh**3 + & 4789 3.108005107949533E-7_wp * zt**3 * zlogrh**3 - & 4790 ( 0.02933332747098296_wp * zlogrh**3 ) / zx + 1.145983818561277_wp * zlogsa - & 4791 0.6007956227856778_wp * zt * zlogsa + 0.00864244733283759_wp * zt**2 * zlogsa - & 4792 0.00002289467254710888_wp * zt**3 * zlogsa - & 4793 ( 8.44984513869014_wp * zlogsa ) / zx + 2.158548369286559_wp * zlogrh * zlogsa + & 4794 0.0808121412840917_wp * zt * zlogrh * zlogsa - & 4795 0.0004073815255395214_wp * zt**2 * zlogrh * zlogsa - & 4796 4.019572560156515E-7_wp * zt**3 * zlogrh * zlogsa + & 4797 ( 0.7213255852557236_wp * zlogrh * zlogsa ) / zx + & 4798 1.62409850488771_wp * zlogrh**2 * zlogsa - & 4799 0.01601062035325362_wp * zt * zlogrh**2 * zlogsa + & 4800 0.00003771238979714162_wp*zt**2* zlogrh**2 * zlogsa + & 4801 3.217942606371182E-8_wp * zt**3 * zlogrh**2 * zlogsa - & 4802 ( 0.01132550810022116_wp * zlogrh**2 * zlogsa ) / zx + & 4803 9.71681713056504_wp * zlogsa**2 - 0.1150478558347306_wp * zt * zlogsa**2 + & 4804 0.0001570982486038294_wp * zt**2 * zlogsa**2 + & 4805 4.009144680125015E-7_wp * zt**3 * zlogsa**2 + & 4806 ( 0.7118597859976135_wp * zlogsa**2 ) / zx - & 4807 1.056105824379897_wp * zlogrh * zlogsa**2 + & 4808 0.00903377584628419_wp * zt * zlogrh * zlogsa**2 - & 4809 0.00001984167387090606_wp * zt**2 * zlogrh * zlogsa**2 + & 4810 2.460478196482179E-8_wp * zt**3 * zlogrh * zlogsa**2 - & 4811 ( 0.05790872906645181_wp * zlogrh * zlogsa**2 ) / zx - & 4812 0.1487119673397459_wp * zlogsa**3 + 0.002835082097822667_wp * zt * zlogsa**3 - & 4813 9.24618825471694E-6_wp * zt**2 * zlogsa**3 + & 4814 5.004267665960894E-9_wp * zt**3 * zlogsa**3 - & 4815 ( 0.01270805101481648_wp * zlogsa**3 ) / zx 4816 ! 4676 4817 !-- Nucleation rate in #/(cm3 s) 4677 4818 pnuc_rate = EXP( pnuc_rate ) 4678 ! 4819 ! 4679 4820 !-- Check the validity of parameterization 4680 4821 IF ( pnuc_rate < 1.0E-7_wp ) THEN … … 4682 4823 pd_crit = 1.0E-9_wp 4683 4824 ENDIF 4684 ! 4825 ! 4685 4826 !-- 4) Total number of molecules in the critical cluster (Eq. 13) 4686 zntot = - 0.002954125078716302_wp & 4687 - 0.0976834264241286_wp * zt & 4688 + 0.001024847927067835_wp * zt ** 2 & 4689 - 2.186459697726116E-6_wp * zt ** 3 & 4690 - 0.1017165718716887_wp / zx & 4691 - 0.002050640345231486_wp * LOG( zrh ) & 4692 - 0.007585041382707174_wp * zt * LOG( zrh ) & 4693 + 0.0001926539658089536_wp * zt ** 2 * LOG( zrh ) & 4694 - 6.70429719683894E-7_wp * zt ** 3 * LOG( zrh ) & 4695 - ( 0.2557744774673163_wp * LOG( zrh ) ) / zx & 4696 + 0.003223076552477191_wp * LOG( zrh ) ** 2 & 4697 + 0.000852636632240633_wp * zt * LOG( zrh ) ** 2 & 4698 - 0.00001547571354871789_wp * zt ** 2 * LOG( zrh ) ** 2 & 4699 + 5.666608424980593E-8_wp * zt ** 3 * LOG( zrh ) ** 2 & 4700 + ( 0.03384437400744206_wp * LOG( zrh ) ** 2 ) / zx & 4701 + 0.04743226764572505_wp * LOG( zrh ) ** 3 & 4702 - 0.0006251042204583412_wp * zt * LOG( zrh ) ** 3 & 4703 + 2.650663328519478E-6_wp * zt ** 2 * LOG( zrh ) ** 3 & 4704 - 3.674710848763778E-9_wp * zt ** 3 * LOG( zrh ) ** 3 & 4705 - ( 0.0002672510825259393_wp * LOG( zrh ) ** 3 ) / zx & 4706 - 0.01252108546759328_wp * LOG( zpcsa ) & 4707 + 0.005806550506277202_wp * zt * LOG( zpcsa ) & 4708 - 0.0001016735312443444_wp * zt ** 2 * LOG( zpcsa ) & 4709 + 2.881946187214505E-7_wp * zt ** 3 * LOG( zpcsa ) & 4710 + ( 0.0942243379396279_wp * LOG( zpcsa ) ) / zx & 4711 - 0.0385459592773097_wp * LOG( zrh ) * LOG( zpcsa ) & 4712 - 0.0006723156277391984_wp * zt * LOG( zrh ) * LOG( zpcsa ) & 4713 + 2.602884877659698E-6_wp * zt ** 2 * LOG( zrh ) * LOG( zpcsa ) & 4714 + 1.194163699688297E-8_wp * zt ** 3 * LOG( zrh ) * LOG( zpcsa ) & 4715 - ( 0.00851515345806281_wp * LOG( zrh ) * LOG( zpcsa ) ) / zx & 4716 - 0.01837488495738111_wp * LOG( zrh ) ** 2 * LOG( zpcsa ) & 4717 + 0.0001720723574407498_wp * zt * LOG( zrh ) ** 2 * LOG( zpcsa ) & 4718 - 3.717657974086814E-7_wp * zt**2 * LOG( zrh )**2 * LOG( zpcsa ) & 4719 - 5.148746022615196E-10_wp * zt**3 * LOG( zrh )**2 * LOG( zpcsa ) & 4720 + ( 0.0002686602132926594_wp * LOG(zrh)**2 * LOG(zpcsa) ) / zx & 4721 - 0.06199739728812199_wp * LOG( zpcsa ) ** 2 & 4722 + 0.000906958053583576_wp * zt * LOG( zpcsa ) ** 2 & 4723 - 9.11727926129757E-7_wp * zt ** 2 * LOG( zpcsa ) ** 2 & 4724 - 5.367963396508457E-9_wp * zt ** 3 * LOG( zpcsa ) ** 2 & 4725 - ( 0.007742343393937707_wp * LOG( zpcsa ) ** 2 ) / zx & 4726 + 0.0121827103101659_wp * LOG( zrh ) * LOG( zpcsa ) ** 2 & 4727 - 0.0001066499571188091_wp * zt * LOG( zrh ) * LOG( zpcsa ) ** 2 & 4728 + 2.534598655067518E-7_wp * zt**2 * LOG( zrh ) * LOG( zpcsa )**2 & 4729 - 3.635186504599571E-10_wp * zt**3 * LOG( zrh ) * LOG( zpcsa )**2 & 4730 + ( 0.0006100650851863252_wp * LOG( zrh ) * LOG( zpcsa ) **2 )/ zx & 4731 + 0.0003201836700403512_wp * LOG( zpcsa ) ** 3 & 4732 - 0.0000174761713262546_wp * zt * LOG( zpcsa ) ** 3 & 4733 + 6.065037668052182E-8_wp * zt ** 2 * LOG( zpcsa ) ** 3 & 4734 - 1.421771723004557E-11_wp * zt ** 3 * LOG( zpcsa ) ** 3 & 4735 + ( 0.0001357509859501723_wp * LOG( zpcsa ) ** 3 ) / zx 4827 zntot = - 0.002954125078716302_wp - 0.0976834264241286_wp * zt + & 4828 0.001024847927067835_wp * zt**2 - 2.186459697726116E-6_wp * zt**3 - & 4829 0.1017165718716887_wp / zx - 0.002050640345231486_wp * zlogrh - & 4830 0.007585041382707174_wp * zt * zlogrh + 0.0001926539658089536_wp * zt**2 * zlogrh - & 4831 6.70429719683894E-7_wp * zt**3 * zlogrh - ( 0.2557744774673163_wp * zlogrh ) / zx + & 4832 0.003223076552477191_wp * zlogrh**2 + 0.000852636632240633_wp * zt * zlogrh**2 - & 4833 0.00001547571354871789_wp * zt**2 * zlogrh**2 + & 4834 5.666608424980593E-8_wp * zt**3 * zlogrh**2 + & 4835 ( 0.03384437400744206_wp * zlogrh**2 ) / zx + & 4836 0.04743226764572505_wp * zlogrh**3 - 0.0006251042204583412_wp * zt * zlogrh**3 + & 4837 2.650663328519478E-6_wp * zt**2 * zlogrh**3 - & 4838 3.674710848763778E-9_wp * zt**3 * zlogrh**3 - & 4839 ( 0.0002672510825259393_wp * zlogrh**3 ) / zx - 0.01252108546759328_wp * zlogsa + & 4840 0.005806550506277202_wp * zt * zlogsa - 0.0001016735312443444_wp * zt**2 * zlogsa + & 4841 2.881946187214505E-7_wp * zt**3 * zlogsa + ( 0.0942243379396279_wp * zlogsa ) / zx - & 4842 0.0385459592773097_wp * zlogrh * zlogsa - & 4843 0.0006723156277391984_wp * zt * zlogrh * zlogsa + & 4844 2.602884877659698E-6_wp * zt**2 * zlogrh * zlogsa + & 4845 1.194163699688297E-8_wp * zt**3 * zlogrh * zlogsa - & 4846 ( 0.00851515345806281_wp * zlogrh * zlogsa ) / zx - & 4847 0.01837488495738111_wp * zlogrh**2 * zlogsa + & 4848 0.0001720723574407498_wp * zt * zlogrh**2 * zlogsa - & 4849 3.717657974086814E-7_wp * zt**2 * zlogrh**2 * zlogsa - & 4850 5.148746022615196E-10_wp * zt**3 * zlogrh**2 * zlogsa + & 4851 ( 0.0002686602132926594_wp * zlogrh**2 * zlogsa ) / zx - & 4852 0.06199739728812199_wp * zlogsa**2 + 0.000906958053583576_wp * zt * zlogsa**2 - & 4853 9.11727926129757E-7_wp * zt**2 * zlogsa**2 - & 4854 5.367963396508457E-9_wp * zt**3 * zlogsa**2 - & 4855 ( 0.007742343393937707_wp * zlogsa**2 ) / zx + & 4856 0.0121827103101659_wp * zlogrh * zlogsa**2 - & 4857 0.0001066499571188091_wp * zt * zlogrh * zlogsa**2 + & 4858 2.534598655067518E-7_wp * zt**2 * zlogrh * zlogsa**2 - & 4859 3.635186504599571E-10_wp * zt**3 * zlogrh * zlogsa**2 + & 4860 ( 0.0006100650851863252_wp * zlogrh * zlogsa **2 ) / zx + & 4861 0.0003201836700403512_wp * zlogsa**3 - 0.0000174761713262546_wp * zt * zlogsa**3 + & 4862 6.065037668052182E-8_wp * zt**2 * zlogsa**3 - & 4863 1.421771723004557E-11_wp * zt**3 * zlogsa**3 + & 4864 ( 0.0001357509859501723_wp * zlogsa**3 ) / zx 4736 4865 zntot = EXP( zntot ) ! in # 4737 4866 ! 4738 4867 !-- 5) Size of the critical cluster pd_crit (m) (diameter) (Eq. 14) 4739 4868 pn_crit_sa = zx * zntot 4740 pd_crit = 2.0E-9_wp * EXP( -1.6524245_wp + 0.42316402_wp * zx + & 4741 0.33466487_wp * LOG( zntot ) ) 4869 pd_crit = 2.0E-9_wp * EXP( -1.6524245_wp + 0.42316402_wp * zx + 0.33466487_wp * LOG( zntot ) ) 4742 4870 ! 4743 4871 !-- 6) Organic compounds not involved when binary nucleation is assumed … … 4745 4873 pk_sa = 1.0_wp ! if = 1, H2SO4 involved in nucleation 4746 4874 pk_ocnv = 0.0_wp ! if = 1, organic compounds involved 4747 ! 4748 !-- Set nucleation rate to collision rate 4875 ! 4876 !-- Set nucleation rate to collision rate 4749 4877 IF ( pn_crit_sa < 4.0_wp ) THEN 4750 ! 4878 ! 4751 4879 !-- Volumes of the colliding objects 4752 4880 zma = 96.0_wp ! molar mass of SO4 in g/mol 4753 4881 zmw = 18.0_wp ! molar mass of water in g/mol 4754 4882 zxmass = 1.0_wp ! mass fraction of H2SO4 4755 za = 0.7681724_wp + zxmass * ( 2.1847140_wp + zxmass * ( & 4756 7.1630022_wp + zxmass * ( -44.31447_wp + zxmass * ( & 4757 88.75606 + zxmass * ( -75.73729_wp + zxmass * & 4758 23.43228_wp ) ) ) ) ) 4759 zb = 1.808225E-3_wp + zxmass * ( -9.294656E-3_wp + zxmass * & 4760 ( -0.03742148_wp + zxmass * ( 0.2565321_wp + zxmass * & 4761 ( -0.5362872_wp + zxmass * ( 0.4857736 - zxmass * & 4762 0.1629592_wp ) ) ) ) ) 4763 zc = - 3.478524E-6_wp + zxmass * ( 1.335867E-5_wp + zxmass * & 4764 ( 5.195706E-5_wp + zxmass * ( -3.717636E-4_wp + zxmass * & 4765 ( 7.990811E-4_wp + zxmass * ( -7.458060E-4_wp + zxmass * & 4766 2.58139E-4_wp ) ) ) ) ) 4767 ! 4883 za = 0.7681724_wp + zxmass * ( 2.1847140_wp + zxmass * & 4884 ( 7.1630022_wp + zxmass * & 4885 ( -44.31447_wp + zxmass * & 4886 ( 88.75606 + zxmass * & 4887 ( -75.73729_wp + zxmass * 23.43228_wp ) ) ) ) ) 4888 zb = 1.808225E-3_wp + zxmass * ( -9.294656E-3_wp + zxmass * & 4889 ( -0.03742148_wp + zxmass * & 4890 ( 0.2565321_wp + zxmass * & 4891 ( -0.5362872_wp + zxmass * & 4892 ( 0.4857736 - zxmass * 0.1629592_wp ) ) ) ) ) 4893 zc = - 3.478524E-6_wp + zxmass * ( 1.335867E-5_wp + zxmass * & 4894 ( 5.195706E-5_wp + zxmass * & 4895 ( -3.717636E-4_wp + zxmass * & 4896 ( 7.990811E-4_wp + zxmass * & 4897 ( -7.458060E-4_wp + zxmass * 2.58139E-4_wp ) ) ) ) ) 4898 ! 4768 4899 !-- Density for the sulphuric acid solution (Eq. 10 in Vehkamaki) 4769 zroo = za + zt * ( zb + zc * zt ) ! g/cm^3 4770 zroo = zroo * 1.0E+3_wp ! kg/m^3 4900 zroo = ( za + zt * ( zb + zc * zt ) ) * 1.0E+3_wp ! (kg/m^3 4771 4901 zm1 = 0.098_wp ! molar mass of H2SO4 in kg/mol 4772 4902 zm2 = zm1 4773 zv1 = zm1 / avo / zroo ! volume 4903 zv1 = zm1 / avo / zroo ! volume 4774 4904 zv2 = zv1 4775 ! 4776 !-- Collision rate 4777 zcoll = zpcsa * zpcsa * ( 3.0_wp * pi / 4.0_wp ) ** ( 1.0_wp / 6.0_wp )& 4778 * SQRT( 6.0_wp * argas * zt / zm1 + 6.0_wp * argas * zt / zm2 )& 4779 * ( zv1 ** ( 1.0_wp / 3.0_wp ) + zv2 ** ( 1.0_wp /3.0_wp ) ) **& 4780 2.0_wp * 1.0E+6_wp ! m3 -> cm3 4781 4782 zcoll = MIN( zcoll, 1.0E+10_wp ) 4905 ! 4906 !-- Collision rate 4907 zcoll = zpcsa * zpcsa * ( 3.0_wp * pi / 4.0_wp )**0.16666666_wp * & 4908 SQRT( 6.0_wp * argas * zt / zm1 + 6.0_wp * argas * zt / zm2 ) * & 4909 ( zv1**0.33333333_wp + zv2**0.33333333_wp )**2 * 1.0E+6_wp ! m3 -> cm3 4910 zcoll = MIN( zcoll, 1.0E+10_wp ) 4783 4911 pnuc_rate = zcoll ! (#/(cm3 s)) 4784 4785 ELSE 4786 pnuc_rate = MIN( pnuc_rate, 1.0E+10_wp ) 4787 ENDIF 4912 4913 ELSE 4914 pnuc_rate = MIN( pnuc_rate, 1.0E+10_wp ) 4915 ENDIF 4788 4916 pnuc_rate = pnuc_rate * 1.0E+6_wp ! (#/(m3 s)) 4789 4917 4790 4918 END SUBROUTINE binnucl 4791 4919 … … 4794 4922 ! ------------ 4795 4923 !> Calculate the nucleation rate and the size of critical clusters assuming 4796 !> ternary nucleation. Parametrisation according to: 4797 !> Napari et al. (2002), J. Chem. Phys., 116, 4221-4227 and 4798 !> Napari et al. (2002), J. Geophys. Res., 107(D19), AAC 6-1-ACC 6-6. 4799 !> Called from subroutine nucleation. 4800 !------------------------------------------------------------------------------! 4801 SUBROUTINE ternucl( pc_sa, pc_nh3, ptemp, prh, pnuc_rate, pn_crit_sa, & 4802 pn_crit_ocnv, pd_crit, pk_sa, pk_ocnv ) 4803 4924 !> ternary nucleation. Parametrisation according to: 4925 !> Napari et al. (2002), J. Chem. Phys., 116, 4221-4227 and 4926 !> Napari et al. (2002), J. Geophys. Res., 107(D19), AAC 6-1-ACC 6-6. 4927 !------------------------------------------------------------------------------! 4928 SUBROUTINE ternucl( pc_sa, pc_nh3, ptemp, prh, pnuc_rate, pn_crit_sa, pn_crit_ocnv, pd_crit, & 4929 pk_sa, pk_ocnv ) 4930 4804 4931 IMPLICIT NONE 4805 4806 !-- Input and output variables 4807 REAL(wp), INTENT(in) :: pc_nh3 !< ammonia mixing ratio (ppt) 4932 4933 REAL(wp) :: zlnj !< logarithm of nucleation rate 4934 REAL(wp) :: zlognh3 !< LOG( pc_nh3 ) 4935 REAL(wp) :: zlogrh !< LOG( prh ) 4936 REAL(wp) :: zlogsa !< LOG( pc_sa ) 4937 4938 REAL(wp), INTENT(in) :: pc_nh3 !< ammonia mixing ratio (ppt) 4808 4939 REAL(wp), INTENT(in) :: pc_sa !< H2SO4 conc. (#/cm3) 4809 4940 REAL(wp), INTENT(in) :: prh !< relative humidity [0-1] 4810 4941 REAL(wp), INTENT(in) :: ptemp !< ambient temperature (K) 4811 REAL(wp), INTENT(out) :: pd_crit !< diameter of critical 4812 !< cluster (m) 4813 REAL(wp), INTENT(out) :: pk_ocnv !< Lever: if pk_ocnv = 1,organic compounds 4814 !< are involved in nucleation 4815 REAL(wp), INTENT(out) :: pk_sa !< Lever: if pk_sa = 1, H2SO4 is involved 4816 !< in nucleation 4817 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in 4818 !< cluster (#) 4819 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in 4820 !< cluster (#) 4821 REAL(wp), INTENT(out) :: pnuc_rate !< nucleation rate (#/(m3 s)) 4822 !-- Local variables 4823 REAL(wp) :: zlnj !< logarithm of nucleation rate 4824 4825 !-- 1) Checking that we are in the validity range of the parameterization. 4942 4943 REAL(wp), INTENT(out) :: pd_crit !< diameter of critical cluster (m) 4944 REAL(wp), INTENT(out) :: pk_ocnv !< if pk_ocnv = 1, organic compounds participate in nucleation 4945 REAL(wp), INTENT(out) :: pk_sa !< if pk_sa = 1, H2SO4 participate in nucleation 4946 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in cluster (#) 4947 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in cluster (#) 4948 REAL(wp), INTENT(out) :: pnuc_rate !< nucleation rate (#/(m3 s)) 4949 ! 4950 !-- 1) Checking that we are in the validity range of the parameterization. 4826 4951 !-- Validity of parameterization : DO NOT REMOVE! 4827 4952 IF ( ptemp < 240.0_wp .OR. ptemp > 300.0_wp ) THEN 4828 4953 message_string = 'Invalid input value: ptemp' 4829 CALL message( 'salsa_mod: ternucl', ' SA0045', 1, 2, 0, 6, 0 )4954 CALL message( 'salsa_mod: ternucl', 'PA0619', 1, 2, 0, 6, 0 ) 4830 4955 ENDIF 4831 4956 IF ( prh < 0.05_wp .OR. prh > 0.95_wp ) THEN 4832 4957 message_string = 'Invalid input value: prh' 4833 CALL message( 'salsa_mod: ternucl', ' SA0046', 1, 2, 0, 6, 0 )4958 CALL message( 'salsa_mod: ternucl', 'PA0620', 1, 2, 0, 6, 0 ) 4834 4959 ENDIF 4835 4960 IF ( pc_sa < 1.0E+4_wp .OR. pc_sa > 1.0E+9_wp ) THEN 4836 4961 message_string = 'Invalid input value: pc_sa' 4837 CALL message( 'salsa_mod: ternucl', ' SA0047', 1, 2, 0, 6, 0 )4962 CALL message( 'salsa_mod: ternucl', 'PA0621', 1, 2, 0, 6, 0 ) 4838 4963 ENDIF 4839 4964 IF ( pc_nh3 < 0.1_wp .OR. pc_nh3 > 100.0_wp ) THEN 4840 4965 message_string = 'Invalid input value: pc_nh3' 4841 CALL message( 'salsa_mod: ternucl', ' SA0048', 1, 2, 0, 6, 0 )4966 CALL message( 'salsa_mod: ternucl', 'PA0622', 1, 2, 0, 6, 0 ) 4842 4967 ENDIF 4968 4969 zlognh3 = LOG( pc_nh3 ) 4970 zlogrh = LOG( prh ) 4971 zlogsa = LOG( pc_sa ) 4843 4972 ! 4844 4973 !-- 2) Nucleation rate (Eq. 7 in Napari et al., 2002: Parameterization of 4845 4974 !-- ternary nucleation of sulfuric acid - ammonia - water. 4846 zlnj = - 84.7551114741543_wp & 4847 + 0.3117595133628944_wp * prh & 4848 + 1.640089605712946_wp * prh * ptemp & 4849 - 0.003438516933381083_wp * prh * ptemp ** 2.0_wp & 4850 - 0.00001097530402419113_wp * prh * ptemp ** 3.0_wp & 4851 - 0.3552967070274677_wp / LOG( pc_sa ) & 4852 - ( 0.06651397829765026_wp * prh ) / LOG( pc_sa ) & 4853 - ( 33.84493989762471_wp * ptemp ) / LOG( pc_sa ) & 4854 - ( 7.823815852128623_wp * prh * ptemp ) / LOG( pc_sa) & 4855 + ( 0.3453602302090915_wp * ptemp ** 2.0_wp ) / LOG( pc_sa ) & 4856 + ( 0.01229375748100015_wp * prh * ptemp ** 2.0_wp ) / LOG( pc_sa ) & 4857 - ( 0.000824007160514956_wp *ptemp ** 3.0_wp ) / LOG( pc_sa ) & 4858 + ( 0.00006185539100670249_wp * prh * ptemp ** 3.0_wp ) & 4859 / LOG( pc_sa ) & 4860 + 3.137345238574998_wp * LOG( pc_sa ) & 4861 + 3.680240980277051_wp * prh * LOG( pc_sa ) & 4862 - 0.7728606202085936_wp * ptemp * LOG( pc_sa ) & 4863 - 0.204098217156962_wp * prh * ptemp * LOG( pc_sa ) & 4864 + 0.005612037586790018_wp * ptemp ** 2.0_wp * LOG( pc_sa ) & 4865 + 0.001062588391907444_wp * prh * ptemp ** 2.0_wp * LOG( pc_sa ) & 4866 - 9.74575691760229E-6_wp * ptemp ** 3.0_wp * LOG( pc_sa ) & 4867 - 1.265595265137352E-6_wp * prh * ptemp ** 3.0_wp * LOG( pc_sa ) & 4868 + 19.03593713032114_wp * LOG( pc_sa ) ** 2.0_wp & 4869 - 0.1709570721236754_wp * ptemp * LOG( pc_sa ) ** 2.0_wp & 4870 + 0.000479808018162089_wp * ptemp ** 2.0_wp * LOG( pc_sa ) ** 2.0_wp& 4871 - 4.146989369117246E-7_wp * ptemp ** 3.0_wp * LOG( pc_sa ) ** 2.0_wp& 4872 + 1.076046750412183_wp * LOG( pc_nh3 ) & 4873 + 0.6587399318567337_wp * prh * LOG( pc_nh3 ) & 4874 + 1.48932164750748_wp * ptemp * LOG( pc_nh3 ) & 4875 + 0.1905424394695381_wp * prh * ptemp * LOG( pc_nh3 ) & 4876 - 0.007960522921316015_wp * ptemp ** 2.0_wp * LOG( pc_nh3 ) & 4877 - 0.001657184248661241_wp * prh * ptemp ** 2.0_wp * LOG( pc_nh3 ) & 4878 + 7.612287245047392E-6_wp * ptemp ** 3.0_wp * LOG( pc_nh3 ) & 4879 + 3.417436525881869E-6_wp * prh * ptemp ** 3.0_wp * LOG( pc_nh3 ) & 4880 + ( 0.1655358260404061_wp * LOG( pc_nh3 ) ) / LOG( pc_sa) & 4881 + ( 0.05301667612522116_wp * prh * LOG( pc_nh3 ) ) / LOG( pc_sa ) & 4882 + ( 3.26622914116752_wp * ptemp * LOG( pc_nh3 ) ) / LOG( pc_sa ) & 4883 - ( 1.988145079742164_wp * prh * ptemp * LOG( pc_nh3 ) ) & 4884 / LOG( pc_sa ) & 4885 - ( 0.04897027401984064_wp * ptemp ** 2.0_wp * LOG( pc_nh3) ) & 4886 / LOG( pc_sa ) & 4887 + ( 0.01578269253599732_wp * prh * ptemp ** 2.0_wp * LOG( pc_nh3 ) & 4888 ) / LOG( pc_sa ) & 4889 + ( 0.0001469672236351303_wp * ptemp ** 3.0_wp * LOG( pc_nh3 ) ) & 4890 / LOG( pc_sa ) & 4891 - ( 0.00002935642836387197_wp * prh * ptemp ** 3.0_wp *LOG( pc_nh3 )& 4892 ) / LOG( pc_sa ) & 4893 + 6.526451177887659_wp * LOG( pc_sa ) * LOG( pc_nh3 ) & 4894 - 0.2580021816722099_wp * ptemp * LOG( pc_sa ) * LOG( pc_nh3 ) & 4895 + 0.001434563104474292_wp * ptemp ** 2.0_wp * LOG( pc_sa ) & 4896 * LOG( pc_nh3 ) & 4897 - 2.020361939304473E-6_wp * ptemp ** 3.0_wp * LOG( pc_sa ) & 4898 * LOG( pc_nh3 ) & 4899 - 0.160335824596627_wp * LOG( pc_sa ) ** 2.0_wp * LOG( pc_nh3 ) & 4900 + 0.00889880721460806_wp * ptemp * LOG( pc_sa ) ** 2.0_wp & 4901 * LOG( pc_nh3 ) & 4902 - 0.00005395139051155007_wp * ptemp ** 2.0_wp & 4903 * LOG( pc_sa) ** 2.0_wp * LOG( pc_nh3 ) & 4904 + 8.39521718689596E-8_wp * ptemp ** 3.0_wp * LOG( pc_sa ) ** 2.0_wp& 4905 * LOG( pc_nh3 ) & 4906 + 6.091597586754857_wp * LOG( pc_nh3 ) ** 2.0_wp & 4907 + 8.5786763679309_wp * prh * LOG( pc_nh3 ) ** 2.0_wp & 4908 - 1.253783854872055_wp * ptemp * LOG( pc_nh3 ) ** 2.0_wp & 4909 - 0.1123577232346848_wp * prh * ptemp * LOG( pc_nh3 ) ** 2.0_wp & 4910 + 0.00939835595219825_wp * ptemp ** 2.0_wp * LOG( pc_nh3 ) ** 2.0_wp& 4911 + 0.0004726256283031513_wp * prh * ptemp ** 2.0_wp & 4912 * LOG( pc_nh3) ** 2.0_wp & 4913 - 0.00001749269360523252_wp * ptemp ** 3.0_wp & 4914 * LOG( pc_nh3 ) ** 2.0_wp & 4915 - 6.483647863710339E-7_wp * prh * ptemp ** 3.0_wp & 4916 * LOG( pc_nh3 ) ** 2.0_wp & 4917 + ( 0.7284285726576598_wp * LOG( pc_nh3 ) ** 2.0_wp ) / LOG( pc_sa )& 4918 + ( 3.647355600846383_wp * ptemp * LOG( pc_nh3 ) ** 2.0_wp ) & 4919 / LOG( pc_sa ) & 4920 - ( 0.02742195276078021_wp * ptemp ** 2.0_wp & 4921 * LOG( pc_nh3) ** 2.0_wp ) / LOG( pc_sa ) & 4922 + ( 0.00004934777934047135_wp * ptemp ** 3.0_wp & 4923 * LOG( pc_nh3 ) ** 2.0_wp ) / LOG( pc_sa ) & 4924 + 41.30162491567873_wp * LOG( pc_sa ) * LOG( pc_nh3 ) ** 2.0_wp & 4925 - 0.357520416800604_wp * ptemp * LOG( pc_sa ) & 4926 * LOG( pc_nh3 ) ** 2.0_wp & 4927 + 0.000904383005178356_wp * ptemp ** 2.0_wp * LOG( pc_sa ) & 4928 * LOG( pc_nh3 ) ** 2.0_wp & 4929 - 5.737876676408978E-7_wp * ptemp ** 3.0_wp * LOG( pc_sa ) & 4930 * LOG( pc_nh3 ) ** 2.0_wp & 4931 - 2.327363918851818_wp * LOG( pc_sa ) ** 2.0_wp & 4932 * LOG( pc_nh3 ) ** 2.0_wp & 4933 + 0.02346464261919324_wp * ptemp * LOG( pc_sa ) ** 2.0_wp & 4934 * LOG( pc_nh3 ) ** 2.0_wp & 4935 - 0.000076518969516405_wp * ptemp ** 2.0_wp & 4936 * LOG( pc_sa ) ** 2.0_wp * LOG( pc_nh3 ) ** 2.0_wp & 4937 + 8.04589834836395E-8_wp * ptemp ** 3.0_wp * LOG( pc_sa ) ** 2.0_wp & 4938 * LOG( pc_nh3 ) ** 2.0_wp & 4939 - 0.02007379204248076_wp * LOG( prh ) & 4940 - 0.7521152446208771_wp * ptemp * LOG( prh ) & 4941 + 0.005258130151226247_wp * ptemp ** 2.0_wp * LOG( prh ) & 4942 - 8.98037634284419E-6_wp * ptemp ** 3.0_wp * LOG( prh ) & 4943 + ( 0.05993213079516759_wp * LOG( prh ) ) / LOG( pc_sa ) & 4944 + ( 5.964746463184173_wp * ptemp * LOG( prh ) ) / LOG( pc_sa ) & 4945 - ( 0.03624322255690942_wp * ptemp ** 2.0_wp * LOG( prh ) ) & 4946 / LOG( pc_sa ) & 4947 + ( 0.00004933369382462509_wp * ptemp ** 3.0_wp * LOG( prh ) ) & 4948 / LOG( pc_sa ) & 4949 - 0.7327310805365114_wp * LOG( pc_nh3 ) * LOG( prh ) & 4950 - 0.01841792282958795_wp * ptemp * LOG( pc_nh3 ) * LOG( prh ) & 4951 + 0.0001471855981005184_wp * ptemp ** 2.0_wp * LOG( pc_nh3 ) & 4952 * LOG( prh ) & 4953 - 2.377113195631848E-7_wp * ptemp ** 3.0_wp * LOG( pc_nh3 ) & 4954 * LOG( prh ) 4975 zlnj = - 84.7551114741543_wp + 0.3117595133628944_wp * prh + & 4976 1.640089605712946_wp * prh * ptemp - 0.003438516933381083_wp * prh * ptemp**2 - & 4977 0.00001097530402419113_wp * prh * ptemp**3 - 0.3552967070274677_wp / zlogsa - & 4978 ( 0.06651397829765026_wp * prh ) / zlogsa - ( 33.84493989762471_wp * ptemp ) / zlogsa - & 4979 ( 7.823815852128623_wp * prh * ptemp ) / zlogsa + & 4980 ( 0.3453602302090915_wp * ptemp**2 ) / zlogsa + & 4981 ( 0.01229375748100015_wp * prh * ptemp**2 ) / zlogsa - & 4982 ( 0.000824007160514956_wp *ptemp**3 ) / zlogsa + & 4983 ( 0.00006185539100670249_wp * prh * ptemp**3 ) / zlogsa + & 4984 3.137345238574998_wp * zlogsa + 3.680240980277051_wp * prh * zlogsa - & 4985 0.7728606202085936_wp * ptemp * zlogsa - 0.204098217156962_wp * prh * ptemp * zlogsa + & 4986 0.005612037586790018_wp * ptemp**2 * zlogsa + & 4987 0.001062588391907444_wp * prh * ptemp**2 * zlogsa - & 4988 9.74575691760229E-6_wp * ptemp**3 * zlogsa - & 4989 1.265595265137352E-6_wp * prh * ptemp**3 * zlogsa + 19.03593713032114_wp * zlogsa**2 - & 4990 0.1709570721236754_wp * ptemp * zlogsa**2 + & 4991 0.000479808018162089_wp * ptemp**2 * zlogsa**2 - & 4992 4.146989369117246E-7_wp * ptemp**3 * zlogsa**2 + 1.076046750412183_wp * zlognh3 + & 4993 0.6587399318567337_wp * prh * zlognh3 + 1.48932164750748_wp * ptemp * zlognh3 + & 4994 0.1905424394695381_wp * prh * ptemp * zlognh3 - & 4995 0.007960522921316015_wp * ptemp**2 * zlognh3 - & 4996 0.001657184248661241_wp * prh * ptemp**2 * zlognh3 + & 4997 7.612287245047392E-6_wp * ptemp**3 * zlognh3 + & 4998 3.417436525881869E-6_wp * prh * ptemp**3 * zlognh3 + & 4999 ( 0.1655358260404061_wp * zlognh3 ) / zlogsa + & 5000 ( 0.05301667612522116_wp * prh * zlognh3 ) / zlogsa + & 5001 ( 3.26622914116752_wp * ptemp * zlognh3 ) / zlogsa - & 5002 ( 1.988145079742164_wp * prh * ptemp * zlognh3 ) / zlogsa - & 5003 ( 0.04897027401984064_wp * ptemp**2 * zlognh3 ) / zlogsa + & 5004 ( 0.01578269253599732_wp * prh * ptemp**2 * zlognh3 ) / zlogsa + & 5005 ( 0.0001469672236351303_wp * ptemp**3 * zlognh3 ) / zlogsa - & 5006 ( 0.00002935642836387197_wp * prh * ptemp**3 *zlognh3 ) / zlogsa + & 5007 6.526451177887659_wp * zlogsa * zlognh3 - & 5008 0.2580021816722099_wp * ptemp * zlogsa * zlognh3 + & 5009 0.001434563104474292_wp * ptemp**2 * zlogsa * zlognh3 - & 5010 2.020361939304473E-6_wp * ptemp**3 * zlogsa * zlognh3 - & 5011 0.160335824596627_wp * zlogsa**2 * zlognh3 + & 5012 0.00889880721460806_wp * ptemp * zlogsa**2 * zlognh3 - & 5013 0.00005395139051155007_wp * ptemp**2 * zlogsa**2 * zlognh3 + & 5014 8.39521718689596E-8_wp * ptemp**3 * zlogsa**2 * zlognh3 + & 5015 6.091597586754857_wp * zlognh3**2 + 8.5786763679309_wp * prh * zlognh3**2 - & 5016 1.253783854872055_wp * ptemp * zlognh3**2 - & 5017 0.1123577232346848_wp * prh * ptemp * zlognh3**2 + & 5018 0.00939835595219825_wp * ptemp**2 * zlognh3**2 + & 5019 0.0004726256283031513_wp * prh * ptemp**2 * zlognh3**2 - & 5020 0.00001749269360523252_wp * ptemp**3 * zlognh3**2 - & 5021 6.483647863710339E-7_wp * prh * ptemp**3 * zlognh3**2 + & 5022 ( 0.7284285726576598_wp * zlognh3**2 ) / zlogsa + & 5023 ( 3.647355600846383_wp * ptemp * zlognh3**2 ) / zlogsa - & 5024 ( 0.02742195276078021_wp * ptemp**2 * zlognh3**2 ) / zlogsa + & 5025 ( 0.00004934777934047135_wp * ptemp**3 * zlognh3**2 ) / zlogsa + & 5026 41.30162491567873_wp * zlogsa * zlognh3**2 - & 5027 0.357520416800604_wp * ptemp * zlogsa * zlognh3**2 + & 5028 0.000904383005178356_wp * ptemp**2 * zlogsa * zlognh3**2 - & 5029 5.737876676408978E-7_wp * ptemp**3 * zlogsa * zlognh3**2 - & 5030 2.327363918851818_wp * zlogsa**2 * zlognh3**2 + & 5031 0.02346464261919324_wp * ptemp * zlogsa**2 * zlognh3**2 - & 5032 0.000076518969516405_wp * ptemp**2 * zlogsa**2 * zlognh3**2 + & 5033 8.04589834836395E-8_wp * ptemp**3 * zlogsa**2 * zlognh3**2 - & 5034 0.02007379204248076_wp * zlogrh - 0.7521152446208771_wp * ptemp * zlogrh + & 5035 0.005258130151226247_wp * ptemp**2 * zlogrh - & 5036 8.98037634284419E-6_wp * ptemp**3 * zlogrh + & 5037 ( 0.05993213079516759_wp * zlogrh ) / zlogsa + & 5038 ( 5.964746463184173_wp * ptemp * zlogrh ) / zlogsa - & 5039 ( 0.03624322255690942_wp * ptemp**2 * zlogrh ) / zlogsa + & 5040 ( 0.00004933369382462509_wp * ptemp**3 * zlogrh ) / zlogsa - & 5041 0.7327310805365114_wp * zlognh3 * zlogrh - & 5042 0.01841792282958795_wp * ptemp * zlognh3 * zlogrh + & 5043 0.0001471855981005184_wp * ptemp**2 * zlognh3 * zlogrh - & 5044 2.377113195631848E-7_wp * ptemp**3 * zlognh3 * zlogrh 4955 5045 pnuc_rate = EXP( zlnj ) ! (#/(cm3 s)) 4956 ! 4957 !-- Check validity of parametrization 4958 IF ( pnuc_rate < 1.0E-5_wp ) THEN 5046 ! 5047 !-- Check validity of parametrization 5048 IF ( pnuc_rate < 1.0E-5_wp ) THEN 4959 5049 pnuc_rate = 0.0_wp 4960 5050 pd_crit = 1.0E-9_wp 4961 5051 ELSEIF ( pnuc_rate > 1.0E6_wp ) THEN 4962 5052 message_string = 'Invalid output value: nucleation rate > 10^6 1/cm3s' 4963 CALL message( 'salsa_mod: ternucl', ' SA0049', 1, 2, 0, 6, 0 )5053 CALL message( 'salsa_mod: ternucl', 'PA0623', 1, 2, 0, 6, 0 ) 4964 5054 ENDIF 4965 5055 pnuc_rate = pnuc_rate * 1.0E6_wp ! (#/(m3 s)) 4966 ! 5056 ! 4967 5057 !-- 3) Number of H2SO4 molecules in a critical cluster (Eq. 9) 4968 pn_crit_sa = 38.16448247950508_wp + 0.7741058259731187_wp * zlnj + & 4969 0.002988789927230632_wp * zlnj ** 2.0_wp - & 4970 0.3576046920535017_wp * ptemp - & 4971 0.003663583011953248_wp * zlnj * ptemp + & 4972 0.000855300153372776_wp * ptemp ** 2.0_wp 4973 !-- Kinetic limit: at least 2 H2SO4 molecules in a cluster 4974 pn_crit_sa = MAX( pn_crit_sa, 2.0E0_wp ) 4975 ! 5058 pn_crit_sa = 38.16448247950508_wp + 0.7741058259731187_wp * zlnj + & 5059 0.002988789927230632_wp * zlnj**2 - 0.3576046920535017_wp * ptemp - & 5060 0.003663583011953248_wp * zlnj * ptemp + 0.000855300153372776_wp * ptemp**2 5061 ! 5062 !-- Kinetic limit: at least 2 H2SO4 molecules in a cluster 5063 pn_crit_sa = MAX( pn_crit_sa, 2.0E0_wp ) 5064 ! 4976 5065 !-- 4) Size of the critical cluster in nm (Eq. 12) 4977 pd_crit = 0.1410271086638381_wp - 0.001226253898894878_wp * zlnj - & 4978 7.822111731550752E-6_wp * zlnj ** 2.0_wp - & 4979 0.001567273351921166_wp * ptemp - & 4980 0.00003075996088273962_wp * zlnj * ptemp + & 4981 0.00001083754117202233_wp * ptemp ** 2.0_wp 5066 pd_crit = 0.1410271086638381_wp - 0.001226253898894878_wp * zlnj - & 5067 7.822111731550752E-6_wp * zlnj**2 - 0.001567273351921166_wp * ptemp - & 5068 0.00003075996088273962_wp * zlnj * ptemp + 0.00001083754117202233_wp * ptemp**2 4982 5069 pd_crit = pd_crit * 2.0E-9_wp ! Diameter in m 4983 5070 ! 4984 5071 !-- 5) Organic compounds not involved when ternary nucleation assumed 4985 pn_crit_ocnv = 0.0_wp 5072 pn_crit_ocnv = 0.0_wp 4986 5073 pk_sa = 1.0_wp 4987 5074 pk_ocnv = 0.0_wp 4988 5075 4989 5076 END SUBROUTINE ternucl 4990 5077 4991 5078 !------------------------------------------------------------------------------! 4992 5079 ! Description: 4993 5080 ! ------------ 4994 !> Calculate the nucleation rate and the size of critical clusters assuming 4995 !> kinetic nucleation. Each sulphuric acid molecule forms an (NH4)HSO4 molecule 5081 !> Calculate the nucleation rate and the size of critical clusters assuming 5082 !> kinetic nucleation. Each sulphuric acid molecule forms an (NH4)HSO4 molecule 4996 5083 !> in the atmosphere and two colliding (NH4)HSO4 molecules form a stable 4997 5084 !> cluster. See Sihto et al. (2006), Atmos. Chem. Phys., 6(12), 4079-4091. … … 5003 5090 !> dens_abs = 1465 density of - " - [kg/m3] 5004 5091 !------------------------------------------------------------------------------! 5005 SUBROUTINE kinnucl( pc_sa, pnuc_rate, pd_crit, pn_crit_sa, pn_crit_ocnv, & 5006 pk_sa, pk_ocnv ) 5007 5092 SUBROUTINE kinnucl( pc_sa, pnuc_rate, pd_crit, pn_crit_sa, pn_crit_ocnv, pk_sa, pk_ocnv ) 5093 5008 5094 IMPLICIT NONE 5009 5010 !-- Input and output variables 5011 REAL(wp), INTENT(in) :: pc_sa !< H2SO4 conc. (#/m3) 5095 5096 REAL(wp), INTENT(in) :: pc_sa !< H2SO4 conc. (#/m3) 5097 5012 5098 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5013 REAL(wp), INTENT(out) :: pk_ocnv !< Lever: if pk_ocnv = 1, organic 5014 !< compounds are involved in nucleation 5015 REAL(wp), INTENT(out) :: pk_sa !< Lever: if pk_sa = 1, H2SO4 is involved 5016 !< in nucleation 5017 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in 5018 !< cluster (#) 5019 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in 5020 !< cluster (#) 5021 REAL(wp), INTENT(out) :: pnuc_rate !< nucl. rate (#/(m3 s)) 5022 5099 REAL(wp), INTENT(out) :: pk_ocnv !< if pk_ocnv = 1, organic compounds participate in nucleation 5100 REAL(wp), INTENT(out) :: pk_sa !< if pk_sa = 1, H2SO4 is participate in nucleation 5101 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in cluster (#) 5102 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in cluster (#) 5103 REAL(wp), INTENT(out) :: pnuc_rate !< nucl. rate (#/(m3 s)) 5104 ! 5023 5105 !-- Nucleation rate (#/(m3 s)) 5024 pnuc_rate = 5.0E-13_wp * pc_sa ** 2.0_wp * 1.0E+6_wp 5106 pnuc_rate = 5.0E-13_wp * pc_sa**2.0_wp * 1.0E+6_wp 5107 ! 5025 5108 !-- Organic compounds not involved when kinetic nucleation is assumed. 5026 5109 pn_crit_sa = 2.0_wp 5027 pn_crit_ocnv = 0.0_wp 5110 pn_crit_ocnv = 0.0_wp 5028 5111 pk_sa = 1.0_wp 5029 pk_ocnv = 0.0_wp 5112 pk_ocnv = 0.0_wp 5030 5113 pd_crit = 7.9375E-10_wp ! (m) 5031 5114 5032 5115 END SUBROUTINE kinnucl 5116 5033 5117 !------------------------------------------------------------------------------! 5034 5118 ! Description: … … 5038 5122 !> See Riipinen et al. (2007), Atmos. Chem. Phys., 7(8), 1899-1914. 5039 5123 !------------------------------------------------------------------------------! 5040 SUBROUTINE actnucl( psa_conc, pnuc_rate, pd_crit, pn_crit_sa, pn_crit_ocnv, & 5041 pk_sa, pk_ocnv, activ ) 5124 SUBROUTINE actnucl( psa_conc, pnuc_rate, pd_crit, pn_crit_sa, pn_crit_ocnv, pk_sa, pk_ocnv, activ ) 5042 5125 5043 5126 IMPLICIT NONE 5044 5045 !-- Input and output variables 5046 REAL(wp), INTENT(in) :: psa_conc !< H2SO4 conc. (#/m3) 5047 REAL(wp), INTENT(in) :: activ !< 5048 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5049 REAL(wp), INTENT(out) :: pk_ocnv !< Lever: if pk_ocnv = 1, organic 5050 !< compounds are involved in nucleation 5051 REAL(wp), INTENT(out) :: pk_sa !< Lever: if pk_sa = 1, H2SO4 is involved 5052 !< in nucleation 5053 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in 5054 !< cluster (#) 5055 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in 5056 !< cluster (#) 5057 REAL(wp), INTENT(out) :: pnuc_rate !< nucl. rate (#/(m3 s)) 5058 5059 !-- act_coeff 1e-7 by default 5127 5128 REAL(wp), INTENT(in) :: activ !< activation coefficient (1e-7 by default) 5129 REAL(wp), INTENT(in) :: psa_conc !< H2SO4 conc. (#/m3) 5130 5131 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5132 REAL(wp), INTENT(out) :: pk_ocnv !< if pk_ocnv = 1, organic compounds participate in nucleation 5133 REAL(wp), INTENT(out) :: pk_sa !< if pk_sa = 1, H2SO4 participate in nucleation 5134 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in cluster (#) 5135 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in cluster (#) 5136 REAL(wp), INTENT(out) :: pnuc_rate !< nucl. rate (#/(m3 s)) 5137 ! 5138 !-- Nucleation rate (#/(m3 s)) 5060 5139 pnuc_rate = activ * psa_conc ! (#/(m3 s)) 5140 ! 5061 5141 !-- Organic compounds not involved when kinetic nucleation is assumed. 5062 5142 pn_crit_sa = 2.0_wp 5063 pn_crit_ocnv = 0.0_wp 5143 pn_crit_ocnv = 0.0_wp 5064 5144 pk_sa = 1.0_wp 5065 5145 pk_ocnv = 0.0_wp 5066 5146 pd_crit = 7.9375E-10_wp ! (m) 5147 5067 5148 END SUBROUTINE actnucl 5149 5068 5150 !------------------------------------------------------------------------------! 5069 5151 ! Description: … … 5078 5160 5079 5161 IMPLICIT NONE 5080 5081 !-- Input and output variables 5162 5163 REAL(wp) :: a_org = 1.3E-7_wp !< (1/s) (Paasonen et al. Table 4: median) 5164 5082 5165 REAL(wp), INTENT(in) :: pc_org !< organic vapour concentration (#/m3) 5083 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5084 REAL(wp), INTENT(out) :: pk_ocnv !< Lever: if pk_ocnv = 1, organic 5085 !< compounds are involved in nucleation 5086 REAL(wp), INTENT(out) :: pk_sa !< Lever: if pk_sa = 1, H2SO4 is involved 5087 !< in nucleation 5088 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in 5089 !< cluster (#) 5090 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in 5091 !< cluster (#) 5092 REAL(wp), INTENT(out) :: pnuc_rate !< nucl. rate (#/(m3 s)) 5093 !-- Local variables 5094 REAL(wp) :: Aorg = 1.3E-7_wp !< (1/s) (Paasonen et al. Table 4: median) 5095 5096 !-- Homomolecular nuleation - which one? 5097 pnuc_rate = Aorg * pc_org 5166 5167 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5168 REAL(wp), INTENT(out) :: pk_ocnv !< if pk_ocnv = 1, organic compounds participate in nucleation 5169 REAL(wp), INTENT(out) :: pk_sa !< if pk_sa = 1, H2SO4 participate in nucleation 5170 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in cluster (#) 5171 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in cluster (#) 5172 REAL(wp), INTENT(out) :: pnuc_rate !< nucl. rate (#/(m3 s)) 5173 ! 5174 !-- Homomolecular nuleation rate 5175 pnuc_rate = a_org * pc_org 5176 ! 5098 5177 !-- H2SO4 not involved when pure organic nucleation is assumed. 5099 5178 pn_crit_sa = 0.0_wp 5100 pn_crit_ocnv = 1.0_wp 5179 pn_crit_ocnv = 1.0_wp 5101 5180 pk_sa = 0.0_wp 5102 5181 pk_ocnv = 1.0_wp 5103 5182 pd_crit = 1.5E-9_wp ! (m) 5104 5183 5105 5184 END SUBROUTINE orgnucl 5185 5106 5186 !------------------------------------------------------------------------------! 5107 5187 ! Description: … … 5111 5191 !> See Paasonen et al. (2010), Atmos. Chem. Phys., 10, 11223-11242. 5112 5192 !------------------------------------------------------------------------------! 5113 SUBROUTINE sumnucl( pc_sa, pc_org, pnuc_rate, pd_crit, pn_crit_sa, & 5114 pn_crit_ocnv, pk_sa, pk_ocnv ) 5193 SUBROUTINE sumnucl( pc_sa, pc_org, pnuc_rate, pd_crit, pn_crit_sa, pn_crit_ocnv, pk_sa, pk_ocnv ) 5115 5194 5116 5195 IMPLICIT NONE 5117 5118 !-- Input and output variables 5196 5197 REAL(wp) :: a_s1 = 6.1E-7_wp !< (1/s) 5198 REAL(wp) :: a_s2 = 0.39E-7_wp !< (1/s) (Paasonen et al. Table 3.) 5199 5119 5200 REAL(wp), INTENT(in) :: pc_org !< organic vapour concentration (#/m3) 5120 5201 REAL(wp), INTENT(in) :: pc_sa !< H2SO4 conc. (#/m3) 5121 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5122 REAL(wp), INTENT(out) :: pk_ocnv !< Lever: if pk_ocnv = 1, organic 5123 !< compounds are involved in nucleation 5124 REAL(wp), INTENT(out) :: pk_sa !< Lever: if pk_sa = 1, H2SO4 is involved 5125 !< in nucleation 5126 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in 5127 !< cluster (#) 5128 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in 5129 !< cluster (#) 5130 REAL(wp), INTENT(out) :: pnuc_rate !< nucl. rate (#/(m3 s)) 5131 !-- Local variables 5132 REAL(wp) :: As1 = 6.1E-7_wp !< (1/s) 5133 REAL(wp) :: As2 = 0.39E-7_wp !< (1/s) (Paasonen et al. Table 3.) 5134 5202 5203 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5204 REAL(wp), INTENT(out) :: pk_ocnv !< if pk_ocnv = 1, organic compounds participate in nucleation 5205 REAL(wp), INTENT(out) :: pk_sa !< if pk_sa = 1, H2SO4 participate in nucleation 5206 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in cluster (#) 5207 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in cluster (#) 5208 REAL(wp), INTENT(out) :: pnuc_rate !< nucl. rate (#/(m3 s)) 5209 ! 5135 5210 !-- Nucleation rate (#/m3/s) 5136 pnuc_rate = As1 * pc_sa + As2 * pc_org 5137 !-- Both Organic compounds and H2SO4 are involved when SUMnucleation is assumed. 5211 pnuc_rate = a_s1 * pc_sa + a_s2 * pc_org 5212 ! 5213 !-- Both organic compounds and H2SO4 are involved when sumnucleation is assumed. 5138 5214 pn_crit_sa = 1.0_wp 5139 pn_crit_ocnv = 1.0_wp 5215 pn_crit_ocnv = 1.0_wp 5140 5216 pk_sa = 1.0_wp 5141 pk_ocnv = 1.0_wp 5217 pk_ocnv = 1.0_wp 5142 5218 pd_crit = 1.5E-9_wp ! (m) 5143 5219 5144 5220 END SUBROUTINE sumnucl 5221 5145 5222 !------------------------------------------------------------------------------! 5146 5223 ! Description: … … 5150 5227 !> See Paasonen et al. (2010), Atmos. Chem. Phys., 10, 11223-11242. 5151 5228 !------------------------------------------------------------------------------! 5152 SUBROUTINE hetnucl( pc_sa, pc_org, pnuc_rate, pd_crit, pn_crit_sa, & 5153 pn_crit_ocnv, pk_sa, pk_ocnv ) 5229 SUBROUTINE hetnucl( pc_sa, pc_org, pnuc_rate, pd_crit, pn_crit_sa, pn_crit_ocnv, pk_sa, pk_ocnv ) 5154 5230 5155 5231 IMPLICIT NONE 5156 5157 !-- Input and output variables 5232 5233 REAL(wp) :: z_k_het = 4.1E-14_wp !< (cm3/s) (Paasonen et al. Table 4: median) 5234 5158 5235 REAL(wp), INTENT(in) :: pc_org !< organic vapour concentration (#/m3) 5159 5236 REAL(wp), INTENT(in) :: pc_sa !< H2SO4 conc. (#/m3) 5160 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5161 REAL(wp), INTENT(out) :: pk_ocnv !< Lever: if pk_ocnv = 1, organic 5162 !< compounds are involved in nucleation 5163 REAL(wp), INTENT(out) :: pk_sa !< Lever: if pk_sa = 1, H2SO4 is involved 5164 !< in nucleation 5165 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in 5166 !< cluster (#) 5167 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in 5168 !< cluster (#) 5169 REAL(wp), INTENT(out) :: pnuc_rate !< nucl. rate (#/(m3 s)) 5170 !-- Local variables 5171 REAL(wp) :: zKhet = 4.1E-14_wp !< (cm3/s) (Paasonen et al. Table 4: median) 5172 5237 5238 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5239 REAL(wp), INTENT(out) :: pk_ocnv !< if pk_ocnv = 1, organic compounds participate in nucleation 5240 REAL(wp), INTENT(out) :: pk_sa !< if pk_sa = 1, H2SO4 participate in nucleation 5241 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in cluster (#) 5242 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in cluster (#) 5243 REAL(wp), INTENT(out) :: pnuc_rate !< nucl. rate (#/(m3 s)) 5244 ! 5173 5245 !-- Nucleation rate (#/m3/s) 5174 pnuc_rate = zKhet * pc_sa * pc_org * 1.0E6_wp 5175 !-- Both Organic compounds and H2SO4 are involved when heteromolecular 5246 pnuc_rate = z_k_het * pc_sa * pc_org * 1.0E6_wp 5247 ! 5248 !-- Both organic compounds and H2SO4 are involved when heteromolecular 5176 5249 !-- nucleation is assumed. 5177 5250 pn_crit_sa = 1.0_wp 5178 pn_crit_ocnv = 1.0_wp 5251 pn_crit_ocnv = 1.0_wp 5179 5252 pk_sa = 1.0_wp 5180 pk_ocnv = 1.0_wp 5253 pk_ocnv = 1.0_wp 5181 5254 pd_crit = 1.5E-9_wp ! (m) 5182 5255 5183 5256 END SUBROUTINE hetnucl 5257 5184 5258 !------------------------------------------------------------------------------! 5185 5259 ! Description: 5186 5260 ! ------------ 5187 !> Takes into account the homomolecular nucleation of sulphuric acid H2SO4 with 5261 !> Takes into account the homomolecular nucleation of sulphuric acid H2SO4 with 5188 5262 !> both of the available vapours. 5189 5263 !> See Paasonen et al. (2010), Atmos. Chem. Phys., 10, 11223-11242. 5190 5264 !------------------------------------------------------------------------------! 5191 SUBROUTINE SAnucl( pc_sa, pc_org, pnuc_rate, pd_crit, pn_crit_sa, & 5192 pn_crit_ocnv, pk_sa, pk_ocnv ) 5265 SUBROUTINE SAnucl( pc_sa, pc_org, pnuc_rate, pd_crit, pn_crit_sa, pn_crit_ocnv, pk_sa, pk_ocnv ) 5193 5266 5194 5267 IMPLICIT NONE 5195 5196 !-- Input and output variables 5268 5269 REAL(wp) :: z_k_sa1 = 1.1E-14_wp !< (cm3/s) 5270 REAL(wp) :: z_k_sa2 = 3.2E-14_wp !< (cm3/s) (Paasonen et al. Table 3.) 5271 5197 5272 REAL(wp), INTENT(in) :: pc_org !< organic vapour concentration (#/m3) 5198 5273 REAL(wp), INTENT(in) :: pc_sa !< H2SO4 conc. (#/m3) 5199 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5200 REAL(wp), INTENT(out) :: pk_ocnv !< Lever: if pk_ocnv = 1, organic 5201 !< compounds are involved in nucleation 5202 REAL(wp), INTENT(out) :: pk_sa !< Lever: if pk_sa = 1, H2SO4 is involved 5203 !< in nucleation 5204 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in 5205 !< cluster (#) 5206 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in 5207 !< cluster (#) 5208 REAL(wp), INTENT(out) :: pnuc_rate !< nucleation rate (#/(m3 s)) 5209 !-- Local variables 5210 REAL(wp) :: zKsa1 = 1.1E-14_wp !< (cm3/s) 5211 REAL(wp) :: zKsa2 = 3.2E-14_wp !< (cm3/s) (Paasonen et al. Table 3.) 5212 5274 5275 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5276 REAL(wp), INTENT(out) :: pk_ocnv !< if pk_ocnv = 1, organic compounds participate nucleation 5277 REAL(wp), INTENT(out) :: pk_sa !< if pk_sa = 1, H2SO4 participate in nucleation 5278 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in cluster (#) 5279 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in cluster (#) 5280 REAL(wp), INTENT(out) :: pnuc_rate !< nucleation rate (#/(m3 s)) 5281 ! 5213 5282 !-- Nucleation rate (#/m3/s) 5214 pnuc_rate = ( zKsa1 * pc_sa ** 2.0_wp + zKsa2 * pc_sa * pc_org ) * 1.0E+6_wp 5215 !-- Both Organic compounds and H2SO4 are involved when SAnucleation is assumed. 5283 pnuc_rate = ( z_k_sa1 * pc_sa**2 + z_k_sa2 * pc_sa * pc_org ) * 1.0E+6_wp 5284 ! 5285 !-- Both organic compounds and H2SO4 are involved when SAnucleation is assumed. 5216 5286 pn_crit_sa = 3.0_wp 5217 5287 pn_crit_ocnv = 1.0_wp … … 5219 5289 pk_ocnv = 1.0_wp 5220 5290 pd_crit = 1.5E-9_wp ! (m) 5221 5291 5222 5292 END SUBROUTINE SAnucl 5293 5223 5294 !------------------------------------------------------------------------------! 5224 5295 ! Description: … … 5228 5299 !> See Paasonen et al. (2010), Atmos. Chem. Phys., 10, 11223-11242. 5229 5300 !------------------------------------------------------------------------------! 5230 SUBROUTINE SAORGnucl( pc_sa, pc_org, pnuc_rate, pd_crit, pn_crit_sa, & 5231 pn_crit_ocnv, pk_sa, pk_ocnv ) 5301 SUBROUTINE SAORGnucl( pc_sa, pc_org, pnuc_rate, pd_crit, pn_crit_sa, pn_crit_ocnv, pk_sa, pk_ocnv ) 5232 5302 5233 5303 IMPLICIT NONE 5234 5235 !-- Input and output variables 5304 5305 REAL(wp) :: z_k_s1 = 1.4E-14_wp !< (cm3/s]) 5306 REAL(wp) :: z_k_s2 = 2.6E-14_wp !< (cm3/s]) 5307 REAL(wp) :: z_k_s3 = 0.037E-14_wp !< (cm3/s]) (Paasonen et al. Table 3.) 5308 5236 5309 REAL(wp), INTENT(in) :: pc_org !< organic vapour concentration (#/m3) 5237 5310 REAL(wp), INTENT(in) :: pc_sa !< H2SO4 conc. (#/m3) 5238 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5239 REAL(wp), INTENT(out) :: pk_ocnv !< Lever: if pk_ocnv = 1, organic 5240 !< compounds are involved in nucleation 5241 REAL(wp), INTENT(out) :: pk_sa !< Lever: if pk_sa = 1, H2SO4 is involved 5242 !< in nucleation 5243 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in 5244 !< cluster (#) 5245 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in 5246 !< cluster (#) 5247 REAL(wp), INTENT(out) :: pnuc_rate !< nucl. rate (#/(m3 s)) 5248 !-- Local variables 5249 REAL(wp) :: zKs1 = 1.4E-14_wp !< (cm3/s]) 5250 REAL(wp) :: zKs2 = 2.6E-14_wp !< (cm3/s]) 5251 REAL(wp) :: zKs3 = 0.037E-14_wp !< (cm3/s]) (Paasonen et al. Table 3.) 5252 5253 !-- Nucleation rate (#/m3/s) 5254 pnuc_rate = ( zKs1 * pc_sa **2 + zKs2 * pc_sa * pc_org + zKs3 * & 5255 pc_org ** 2.0_wp ) * 1.0E+6_wp 5311 5312 REAL(wp), INTENT(out) :: pd_crit !< critical diameter of clusters (m) 5313 REAL(wp), INTENT(out) :: pk_ocnv !< if pk_ocnv = 1, organic compounds participate in nucleation 5314 REAL(wp), INTENT(out) :: pk_sa !< if pk_sa = 1, H2SO4 participate in nucleation 5315 REAL(wp), INTENT(out) :: pn_crit_ocnv !< number of organic molecules in cluster (#) 5316 REAL(wp), INTENT(out) :: pn_crit_sa !< number of H2SO4 molecules in cluster (#) 5317 REAL(wp), INTENT(out) :: pnuc_rate !< nucl. rate (#/(m3 s)) 5318 ! 5319 !-- Nucleation rate (#/m3/s) 5320 pnuc_rate = ( z_k_s1 * pc_sa**2 + z_k_s2 * pc_sa * pc_org + z_k_s3 * pc_org**2 ) * 1.0E+6_wp 5321 ! 5256 5322 !-- Organic compounds not involved when kinetic nucleation is assumed. 5257 5323 pn_crit_sa = 3.0_wp 5258 pn_crit_ocnv = 3.0_wp 5324 pn_crit_ocnv = 3.0_wp 5259 5325 pk_sa = 1.0_wp 5260 5326 pk_ocnv = 1.0_wp 5261 5327 pd_crit = 1.5E-9_wp ! (m) 5262 5328 5263 5329 END SUBROUTINE SAORGnucl 5264 5330 5265 5331 !------------------------------------------------------------------------------! 5266 5332 ! Description: 5267 5333 ! ------------ 5268 !> Function z Nnuc_tayl is connected to the calculation of self-coagualtion of5334 !> Function z_n_nuc_tayl is connected to the calculation of self-coagualtion of 5269 5335 !> small particles. It calculates number of the particles in the size range 5270 5336 !> [zdcrit,dx] using Taylor-expansion (please note that the expansion is not 5271 5337 !> valid for certain rational numbers, e.g. -4/3 and -3/2) 5272 5338 !------------------------------------------------------------------------------! 5273 FUNCTION zNnuc_tayl( d1, dx, zm_para, zjnuc_t, zeta, zGRtot ) 5339 FUNCTION z_n_nuc_tayl( d1, dx, zm_para, zjnuc_t, zeta, z_gr_tot ) 5340 5274 5341 IMPLICIT NONE 5275 5276 INTEGER(iwp) :: i 5277 REAL(wp) :: d1 5278 REAL(wp) :: dx 5279 REAL(wp) :: zjnuc_t 5280 REAL(wp) :: zeta 5281 REAL(wp) :: term1 5282 REAL(wp) :: term2 5283 REAL(wp) :: term3 5284 REAL(wp) :: term4 5285 REAL(wp) :: term5 5286 REAL(wp) :: zNnuc_tayl 5287 REAL(wp) :: zGRtot 5288 REAL(wp) :: zm_para 5289 5290 zNnuc_tayl = 0.0_wp 5342 5343 INTEGER(iwp) :: i !< running index 5344 5345 REAL(wp) :: d1 !< lower diameter limit 5346 REAL(wp) :: dx !< upper diameter limit 5347 REAL(wp) :: zjnuc_t !< initial nucleation rate (1/s) 5348 REAL(wp) :: zeta !< ratio of CS/GR (m) (condensation sink / growth rate) 5349 REAL(wp) :: term1 !< 5350 REAL(wp) :: term2 !< 5351 REAL(wp) :: term3 !< 5352 REAL(wp) :: term4 !< 5353 REAL(wp) :: term5 !< 5354 REAL(wp) :: z_n_nuc_tayl !< final nucleation rate (1/s) 5355 REAL(wp) :: z_gr_tot !< total growth rate (nm/h) 5356 REAL(wp) :: zm_para !< m parameter in Lehtinen et al. (2007), Eq. 6 5357 5358 z_n_nuc_tayl = 0.0_wp 5291 5359 5292 5360 DO i = 0, 29 … … 5296 5364 term1 = term1 * REAL( i, SELECTED_REAL_KIND(12,307) ) 5297 5365 END IF 5298 term2 = ( REAL( i, SELECTED_REAL_KIND(12,307) ) * ( zm_para + 1.0_wp & 5299 ) + 1.0_wp ) * term1 5300 term3 = zeta ** i 5366 term2 = ( REAL( i, SELECTED_REAL_KIND(12,307) ) * ( zm_para + 1.0_wp ) + 1.0_wp ) * term1 5367 term3 = zeta**i 5301 5368 term4 = term3 / term2 5302 term5 = REAL( i, SELECTED_REAL_KIND(12,307) ) * ( zm_para + 1.0_wp ) & 5303 + 1.0_wp 5304 zNnuc_tayl = zNnuc_tayl + term4 * ( dx ** term5 - d1 ** term5 ) 5369 term5 = REAL( i, SELECTED_REAL_KIND(12,307) ) * ( zm_para + 1.0_wp ) + 1.0_wp 5370 z_n_nuc_tayl = z_n_nuc_tayl + term4 * ( dx**term5 - d1**term5 ) 5305 5371 ENDDO 5306 zNnuc_tayl = zNnuc_tayl * zjnuc_t * EXP( -zeta * & 5307 ( d1 ** ( zm_para + 1 ) ) ) / zGRtot 5308 5309 END FUNCTION zNnuc_tayl 5310 5372 z_n_nuc_tayl = z_n_nuc_tayl * zjnuc_t * EXP( -zeta * ( d1**( zm_para + 1 ) ) ) / z_gr_tot 5373 5374 END FUNCTION z_n_nuc_tayl 5375 5311 5376 !------------------------------------------------------------------------------! 5312 5377 ! Description: … … 5318 5383 !------------------------------------------------------------------------------! 5319 5384 SUBROUTINE gpparth2o( paero, ptemp, ppres, pcs, pcw, ptstep ) 5320 5385 5321 5386 IMPLICIT NONE 5322 ! 5323 !-- Input and output variables 5324 REAL(wp), INTENT(in) :: ppres !< Air pressure (Pa) 5325 REAL(wp), INTENT(in) :: pcs !< Water vapour saturation 5326 !< concentration (kg/m3) 5327 REAL(wp), INTENT(in) :: ptemp !< Ambient temperature (K) 5328 REAL(wp), INTENT(in) :: ptstep !< timestep (s) 5329 REAL(wp), INTENT(inout) :: pcw !< Water vapour concentration 5330 !< (kg/m3) 5331 TYPE(t_section), INTENT(inout) :: paero(nbins) !< Aerosol properties 5332 !-- Local variables 5333 INTEGER(iwp) :: b !< loop index 5334 INTEGER(iwp) :: nstr 5335 REAL(wp) :: adt !< internal timestep in this subroutine 5336 REAL(wp) :: adtc(nbins) 5337 REAL(wp) :: rhoair 5338 REAL(wp) :: ttot 5339 REAL(wp) :: zact !< Water activity 5340 REAL(wp) :: zaelwc1 !< Current aerosol water content 5341 REAL(wp) :: zaelwc2 !< New aerosol water content after 5342 !< equilibrium calculation 5343 REAL(wp) :: zbeta !< Transitional correction factor 5344 REAL(wp) :: zcwc !< Current water vapour mole concentration 5345 REAL(wp) :: zcwcae(nbins) !< Current water mole concentrations 5346 !< in aerosols 5347 REAL(wp) :: zcwint !< Current and new water vapour mole concentrations 5348 REAL(wp) :: zcwintae(nbins) !< Current and new water mole concentrations 5349 !< in aerosols 5350 REAL(wp) :: zcwn !< New water vapour mole concentration 5351 REAL(wp) :: zcwnae(nbins) !< New water mole concentration in aerosols 5352 REAL(wp) :: zcwsurfae(nbins) !< Surface mole concentration 5353 REAL(wp) :: zcwtot !< Total water mole concentration 5354 REAL(wp) :: zdfh2o 5355 REAL(wp) :: zhlp1 5356 REAL(wp) :: zhlp2 5357 REAL(wp) :: zhlp3 5358 REAL(wp) :: zka(nbins) !< Activity coefficient 5359 REAL(wp) :: zkelvin(nbins) !< Kelvin effect 5360 REAL(wp) :: zknud 5361 REAL(wp) :: zmfph2o !< mean free path of H2O gas molecule 5362 REAL(wp) :: zmtae(nbins) !< Mass transfer coefficients 5363 REAL(wp) :: zrh !< Relative humidity [0-1] 5364 REAL(wp) :: zthcond 5365 REAL(wp) :: zwsatae(nbins) !< Water saturation ratio above aerosols 5387 5388 INTEGER(iwp) :: ib !< loop index 5389 INTEGER(iwp) :: nstr !< 5390 5391 REAL(wp) :: adt !< internal timestep in this subroutine 5392 REAL(wp) :: rhoair !< air density (kg/m3) 5393 REAL(wp) :: ttot !< total time (s) 5394 REAL(wp) :: zact !< Water activity 5395 REAL(wp) :: zaelwc1 !< Current aerosol water content (kg/m3) 5396 REAL(wp) :: zaelwc2 !< New aerosol water content after equilibrium calculation (kg/m3) 5397 REAL(wp) :: zbeta !< Transitional correction factor 5398 REAL(wp) :: zcwc !< Current water vapour mole concentration in aerosols (mol/m3) 5399 REAL(wp) :: zcwint !< Current and new water vapour mole concentrations (mol/m3) 5400 REAL(wp) :: zcwn !< New water vapour mole concentration (mol/m3) 5401 REAL(wp) :: zcwtot !< Total water mole concentration (mol/m3) 5402 REAL(wp) :: zdfh2o !< molecular diffusion coefficient (cm2/s) for water 5403 REAL(wp) :: zhlp1 !< intermediate variable to calculate the mass transfer coefficient 5404 REAL(wp) :: zhlp2 !< intermediate variable to calculate the mass transfer coefficient 5405 REAL(wp) :: zhlp3 !< intermediate variable to calculate the mass transfer coefficient 5406 REAL(wp) :: zknud !< Knudsen number 5407 REAL(wp) :: zmfph2o !< mean free path of H2O gas molecule 5408 REAL(wp) :: zrh !< relative humidity [0-1] 5409 REAL(wp) :: zthcond !< thermal conductivity of air (W/m/K) 5410 5411 REAL(wp), DIMENSION(nbins_aerosol) :: zcwcae !< Current water mole concentrations 5412 REAL(wp), DIMENSION(nbins_aerosol) :: zcwintae !< Current and new aerosol water mole concentration 5413 REAL(wp), DIMENSION(nbins_aerosol) :: zcwnae !< New water mole concentration in aerosols 5414 REAL(wp), DIMENSION(nbins_aerosol) :: zcwsurfae !< Surface mole concentration 5415 REAL(wp), DIMENSION(nbins_aerosol) :: zkelvin !< Kelvin effect 5416 REAL(wp), DIMENSION(nbins_aerosol) :: zmtae !< Mass transfer coefficients 5417 REAL(wp), DIMENSION(nbins_aerosol) :: zwsatae !< Water saturation ratio above aerosols 5418 5419 REAL(wp), INTENT(in) :: ppres !< Air pressure (Pa) 5420 REAL(wp), INTENT(in) :: pcs !< Water vapour saturation concentration (kg/m3) 5421 REAL(wp), INTENT(in) :: ptemp !< Ambient temperature (K) 5422 REAL(wp), INTENT(in) :: ptstep !< timestep (s) 5423 5424 REAL(wp), INTENT(inout) :: pcw !< Water vapour concentration (kg/m3) 5425 5426 TYPE(t_section), DIMENSION(nbins_aerosol), INTENT(inout) :: paero !< Aerosol properties 5366 5427 ! 5367 5428 !-- Relative humidity [0-1] 5368 5429 zrh = pcw / pcs 5430 ! 5369 5431 !-- Calculate the condensation only for 2a/2b aerosol bins 5370 nstr = in2a 5432 nstr = start_subrange_2a 5433 ! 5371 5434 !-- Save the current aerosol water content, 8 in paero is H2O 5372 zaelwc1 = SUM( paero( in1a:fn2b)%volc(8) ) * arhoh2o5435 zaelwc1 = SUM( paero(start_subrange_1a:end_subrange_2b)%volc(8) ) * arhoh2o 5373 5436 ! 5374 5437 !-- Equilibration: … … 5380 5443 ENDIF 5381 5444 ENDIF 5382 ! 5445 ! 5383 5446 !-- The new aerosol water content after equilibrium calculation 5384 zaelwc2 = SUM( paero(in1a:fn2b)%volc(8) ) * arhoh2o 5447 zaelwc2 = SUM( paero(start_subrange_1a:end_subrange_2b)%volc(8) ) * arhoh2o 5448 ! 5385 5449 !-- New water vapour mixing ratio (kg/m3) 5386 5450 pcw = pcw - ( zaelwc2 - zaelwc1 ) * ppres * amdair / ( argas * ptemp ) 5387 ! 5451 ! 5388 5452 !-- Initialise variables 5389 adtc(:) = 0.0_wp 5390 zcwc = 0.0_wp 5391 zcwcae = 0.0_wp 5392 zcwint = 0.0_wp 5393 zcwintae = 0.0_wp 5394 zcwn = 0.0_wp 5395 zcwnae = 0.0_wp 5396 zhlp1 = 0.0_wp 5397 zwsatae = 0.0_wp 5398 ! 5453 zcwsurfae(:) = 0.0_wp 5454 zhlp1 = 0.0_wp 5455 zhlp2 = 0.0_wp 5456 zhlp3 = 0.0_wp 5457 zmtae(:) = 0.0_wp 5458 zwsatae(:) = 0.0_wp 5459 ! 5399 5460 !-- Air: 5400 5461 !-- Density (kg/m3) 5401 5462 rhoair = amdair * ppres / ( argas * ptemp ) 5402 !-- Thermal conductivity of air 5463 ! 5464 !-- Thermal conductivity of air 5403 5465 zthcond = 0.023807_wp + 7.1128E-5_wp * ( ptemp - 273.16_wp ) 5404 ! 5405 !-- Water vapour: 5406 ! 5466 ! 5467 !-- Water vapour: 5407 5468 !-- Molecular diffusion coefficient (cm2/s) (eq.16.17) 5408 zdfh2o = ( 5.0_wp / ( 16.0_wp * avo * rhoair * 1.0E-3_wp * & 5409 ( 3.11E-8_wp ) ** 2.0_wp ) ) * SQRT( argas * 1.0E+7_wp * ptemp * & 5410 amdair * 1.0E+3_wp * ( amh2o + amdair ) * 1.0E+3_wp / ( 2.0_wp * & 5411 pi * amh2o * 1.0E+3_wp ) ) 5412 zdfh2o = zdfh2o * 1.0E-4 ! Unit change to m^2/s 5413 ! 5469 zdfh2o = ( 5.0_wp / ( 16.0_wp * avo * rhoair * 1.0E-3_wp * 3.11E-8_wp**2 ) ) * SQRT( argas * & 5470 1.0E+7_wp * ptemp * amdair * 1.0E+3_wp * ( amh2o + amdair ) * 1.0E+3_wp / & 5471 ( pi * amh2o * 2.0E+3_wp ) ) 5472 zdfh2o = zdfh2o * 1.0E-4 ! Unit change to m^2/s 5473 ! 5414 5474 !-- Mean free path (eq. 15.25 & 16.29) 5415 zmfph2o = 3.0_wp * zdfh2o * SQRT( pi * amh2o / ( 8.0_wp * argas * ptemp ) ) 5416 zka = 1.0_wp ! Assume activity coefficients as 1 for now. 5417 ! 5418 !-- Kelvin effect (eq. 16.33) 5419 zkelvin = 1.0_wp 5420 zkelvin(1:nbins) = EXP( 4.0_wp * surfw0 * amh2o / ( argas * ptemp * & 5421 arhoh2o * paero(1:nbins)%dwet) ) 5422 ! 5423 ! --Aerosols: 5424 zmtae(:) = 0.0_wp ! mass transfer coefficient 5425 zcwsurfae(:) = 0.0_wp ! surface mole concentrations 5426 DO b = 1, nbins 5427 IF ( paero(b)%numc > nclim .AND. zrh > 0.98_wp ) THEN 5428 ! 5475 zmfph2o = 3.0_wp * zdfh2o * SQRT( pi * amh2o / ( 8.0_wp * argas * ptemp ) ) 5476 ! 5477 !-- Kelvin effect (eq. 16.33) 5478 zkelvin(:) = EXP( 4.0_wp * surfw0 * amh2o / ( argas * ptemp * arhoh2o * paero(:)%dwet) ) 5479 5480 DO ib = 1, nbins_aerosol 5481 IF ( paero(ib)%numc > nclim .AND. zrh > 0.98_wp ) THEN 5482 ! 5429 5483 !-- Water activity 5430 zact = acth2o( paero( b) )5431 ! 5484 zact = acth2o( paero(ib) ) 5485 ! 5432 5486 !-- Saturation mole concentration over flat surface. Limit the super- 5433 !-- saturation to max 1.01 for the mass transfer. Experimental! 5434 zcwsurfae( b) = MAX( pcs, pcw / 1.01_wp ) * rhoair / amh2o5435 ! 5487 !-- saturation to max 1.01 for the mass transfer. Experimental! 5488 zcwsurfae(ib) = MAX( pcs, pcw / 1.01_wp ) * rhoair / amh2o 5489 ! 5436 5490 !-- Equilibrium saturation ratio 5437 zwsatae( b) = zact * zkelvin(b)5438 ! 5491 zwsatae(ib) = zact * zkelvin(ib) 5492 ! 5439 5493 !-- Knudsen number (eq. 16.20) 5440 zknud = 2.0_wp * zmfph2o / paero( b)%dwet5441 ! 5494 zknud = 2.0_wp * zmfph2o / paero(ib)%dwet 5495 ! 5442 5496 !-- Transitional correction factor (Fuks & Sutugin, 1971) 5443 zbeta = ( zknud + 1.0_wp ) / ( 0.377_wp * zknud + 1.0_wp + 4.0_wp / &5444 ( 3.0_wp * massacc( b) ) * ( zknud + zknud ** 2.0_wp) )5445 ! 5497 zbeta = ( zknud + 1.0_wp ) / ( 0.377_wp * zknud + 1.0_wp + 4.0_wp / & 5498 ( 3.0_wp * massacc(ib) ) * ( zknud + zknud**2 ) ) 5499 ! 5446 5500 !-- Mass transfer of H2O: Eq. 16.64 but here D^eff = zdfh2o * zbeta 5447 zhlp1 = paero( b)%numc * 2.0_wp * pi * paero(b)%dwet * zdfh2o * &5448 zbeta 5501 zhlp1 = paero(ib)%numc * 2.0_wp * pi * paero(ib)%dwet * zdfh2o * zbeta 5502 ! 5449 5503 !-- 1st term on the left side of the denominator in eq. 16.55 5450 zhlp2 = amh2o * zdfh2o * alv * zwsatae(b) * zcwsurfae(b) / & 5451 ( zthcond * ptemp ) 5452 !-- 2nd term on the left side of the denominator in eq. 16.55 5453 zhlp3 = ( (alv * amh2o ) / ( argas * ptemp ) ) - 1.0_wp 5504 zhlp2 = amh2o * zdfh2o * alv * zwsatae(ib) * zcwsurfae(ib) / ( zthcond * ptemp ) 5505 ! 5506 !-- 2nd term on the left side of the denominator in eq. 16.55 5507 zhlp3 = ( ( alv * amh2o ) / ( argas * ptemp ) ) - 1.0_wp 5508 ! 5454 5509 !-- Full eq. 16.64: Mass transfer coefficient (1/s) 5455 zmtae( b) = zhlp1 / ( zhlp2 * zhlp3 + 1.0_wp )5510 zmtae(ib) = zhlp1 / ( zhlp2 * zhlp3 + 1.0_wp ) 5456 5511 ENDIF 5457 5512 ENDDO 5458 5513 ! 5459 5514 !-- Current mole concentrations of water 5460 zcwc = pcw * rhoair / amh2o ! as vapour 5461 zcwcae(1:nbins) = paero(1:nbins)%volc(8) * arhoh2o / amh2o ! in aerosols 5462 zcwtot = zcwc + SUM( zcwcae ) ! total water concentration 5463 ttot = 0.0_wp 5464 adtc = 0.0_wp 5465 zcwintae = zcwcae 5466 ! 5515 zcwc = pcw * rhoair / amh2o ! as vapour 5516 zcwcae(:) = paero(:)%volc(8) * arhoh2o / amh2o ! in aerosols 5517 zcwtot = zcwc + SUM( zcwcae ) ! total water concentration 5518 zcwnae(:) = 0.0_wp 5519 zcwintae(:) = zcwcae(:) 5520 ! 5467 5521 !-- Substepping loop 5468 5522 zcwint = 0.0_wp 5523 ttot = 0.0_wp 5469 5524 DO WHILE ( ttot < ptstep ) 5470 5525 adt = 2.0E-2_wp ! internal timestep 5471 ! 5526 ! 5472 5527 !-- New vapour concentration: (eq. 16.71) 5473 zhlp1 = zcwc + adt * ( SUM( zmtae(nstr:nbins ) * zwsatae(nstr:nbins) *&5474 zcwsurfae(nstr:nbins ) ) ) ! numerator5475 zhlp2 = 1.0_wp + adt * ( SUM( zmtae(nstr:nbins ) ) ) ! denomin.5528 zhlp1 = zcwc + adt * ( SUM( zmtae(nstr:nbins_aerosol) * zwsatae(nstr:nbins_aerosol) * & 5529 zcwsurfae(nstr:nbins_aerosol) ) ) ! numerator 5530 zhlp2 = 1.0_wp + adt * ( SUM( zmtae(nstr:nbins_aerosol) ) ) ! denomin. 5476 5531 zcwint = zhlp1 / zhlp2 ! new vapour concentration 5477 5532 zcwint = MIN( zcwint, zcwtot ) 5478 5533 IF ( ANY( paero(:)%numc > nclim ) .AND. zrh > 0.98_wp ) THEN 5479 DO b = nstr, nbins5480 zcwintae( b) = zcwcae(b) + MIN( MAX( adt * zmtae(b) *&5481 ( zcwint - zwsatae(b) * zcwsurfae(b) ),&5482 -0.02_wp * zcwcae(b) ), 0.05_wp * zcwcae(b) )5483 zwsatae( b) = acth2o( paero(b), zcwintae(b) ) * zkelvin(b)5534 DO ib = nstr, nbins_aerosol 5535 zcwintae(ib) = zcwcae(ib) + MIN( MAX( adt * zmtae(ib) * ( zcwint - zwsatae(ib) * & 5536 zcwsurfae(ib) ), -0.02_wp * zcwcae(ib) ), & 5537 0.05_wp * zcwcae(ib) ) 5538 zwsatae(ib) = acth2o( paero(ib), zcwintae(ib) ) * zkelvin(ib) 5484 5539 ENDDO 5485 5540 ENDIF 5486 zcwintae(nstr:nbins ) = MAX( zcwintae(nstr:nbins), 0.0_wp )5487 ! 5541 zcwintae(nstr:nbins_aerosol) = MAX( zcwintae(nstr:nbins_aerosol), 0.0_wp ) 5542 ! 5488 5543 !-- Update vapour concentration for consistency 5489 zcwint = zcwtot - SUM( zcwintae(1:nbins) ) 5544 zcwint = zcwtot - SUM( zcwintae(1:nbins_aerosol) ) 5545 ! 5490 5546 !-- Update "old" values for next cycle 5491 5547 zcwcae = zcwintae 5492 5548 5493 5549 ttot = ttot + adt 5494 ENDDO ! ADT 5495 zcwn = zcwint 5496 zcwnae = zcwintae 5497 pcw = zcwn * amh2o / rhoair 5498 paero(1:nbins)%volc(8) = MAX( 0.0_wp, zcwnae(1:nbins) * amh2o / arhoh2o ) 5499 5550 5551 ENDDO ! ADT 5552 5553 zcwn = zcwint 5554 zcwnae(:) = zcwintae(:) 5555 pcw = zcwn * amh2o / rhoair 5556 paero(:)%volc(8) = MAX( 0.0_wp, zcwnae(:) * amh2o / arhoh2o ) 5557 5500 5558 END SUBROUTINE gpparth2o 5501 5559 … … 5504 5562 ! ------------ 5505 5563 !> Calculates the activity coefficient of liquid water 5506 !------------------------------------------------------------------------------! 5564 !------------------------------------------------------------------------------! 5507 5565 REAL(wp) FUNCTION acth2o( ppart, pcw ) 5508 5566 5509 5567 IMPLICIT NONE 5510 5568 5511 TYPE(t_section), INTENT(in) :: ppart !< Aerosol properties of a bin 5512 REAL(wp), INTENT(in), OPTIONAL :: pcw !< molar concentration of water 5513 !< (mol/m3) 5514 5515 REAL(wp) :: zns !< molar concentration of solutes (mol/m3) 5516 REAL(wp) :: znw !< molar concentration of water (mol/m3) 5517 5518 zns = ( 3.0_wp * ( ppart%volc(1) * arhoh2so4 / amh2so4 ) + & 5519 ( ppart%volc(2) * arhooc / amoc ) + & 5520 2.0_wp * ( ppart%volc(5) * arhoss / amss ) + & 5521 ( ppart%volc(6) * arhohno3 / amhno3 ) + & 5522 ( ppart%volc(7) * arhonh3 / amnh3 ) ) 5569 REAL(wp) :: zns !< molar concentration of solutes (mol/m3) 5570 REAL(wp) :: znw !< molar concentration of water (mol/m3) 5571 5572 REAL(wp), INTENT(in), OPTIONAL :: pcw !< molar concentration of water (mol/m3) 5573 5574 TYPE(t_section), INTENT(in) :: ppart !< Aerosol properties of a bin 5575 5576 zns = ( 3.0_wp * ( ppart%volc(1) * arhoh2so4 / amh2so4 ) + ( ppart%volc(2) * arhooc / amoc ) + & 5577 2.0_wp * ( ppart%volc(5) * arhoss / amss ) + ( ppart%volc(6) * arhohno3 / amhno3 ) + & 5578 ( ppart%volc(7) * arhonh3 / amnh3 ) ) 5579 5523 5580 IF ( PRESENT(pcw) ) THEN 5524 5581 znw = pcw … … 5526 5583 znw = ppart%volc(8) * arhoh2o / amh2o 5527 5584 ENDIF 5528 ! -- Activity = partial pressure of water vapour /5529 !-- sat. vapour pressure of water over a bulkliquid surface5585 ! 5586 !-- Activity = partial pressure of water vapour / sat. vapour pressure of water over a liquid surface 5530 5587 !-- = molality * activity coefficient (Jacobson, 2005: eq. 17.20-21) 5531 !-- Assume activity coefficient of 1 for water 5588 !-- Assume activity coefficient of 1 for water 5532 5589 acth2o = MAX( 0.1_wp, znw / MAX( EPSILON( 1.0_wp ),( znw + zns ) ) ) 5590 5533 5591 END FUNCTION acth2o 5534 5592 … … 5543 5601 !> Called from subroutine condensation. 5544 5602 !> Coded by: 5545 !> Harri Kokkola (FMI) 5603 !> Harri Kokkola (FMI) 5546 5604 !------------------------------------------------------------------------------! 5547 SUBROUTINE gpparthno3( ppres, ptemp, paero, pghno3, pgnh3, pcw, pcs, pbeta, & 5548 ptstep ) 5549 5605 SUBROUTINE gpparthno3( ppres, ptemp, paero, pghno3, pgnh3, pcw, pcs, pbeta, ptstep ) 5606 5550 5607 IMPLICIT NONE 5551 ! 5552 !-- Input and output variables 5553 REAL(wp), INTENT(in) :: pbeta(nbins) !< transitional correction factor for 5554 !< aerosols 5555 REAL(wp), INTENT(in) :: ppres !< ambient pressure (Pa) 5556 REAL(wp), INTENT(in) :: pcs !< water vapour saturation 5557 !< concentration (kg/m3) 5558 REAL(wp), INTENT(in) :: ptemp !< ambient temperature (K) 5559 REAL(wp), INTENT(in) :: ptstep !< time step (s) 5560 REAL(wp), INTENT(inout) :: pghno3 !< nitric acid concentration (#/m3) 5561 REAL(wp), INTENT(inout) :: pgnh3 !< ammonia conc. (#/m3) 5562 REAL(wp), INTENT(inout) :: pcw !< water vapour concentration (kg/m3) 5563 TYPE(t_section), INTENT(inout) :: paero(nbins) !< Aerosol properties 5564 ! 5565 !-- Local variables 5566 INTEGER(iwp) :: b !< loop index 5567 REAL(wp) :: adt !< timestep 5568 REAL(wp) :: zachhso4ae(nbins) !< Activity coefficients for HHSO4 5569 REAL(wp) :: zacnh3ae(nbins) !< Activity coefficients for NH3 5570 REAL(wp) :: zacnh4hso2ae(nbins)!< Activity coefficients for NH4HSO2 5571 REAL(wp) :: zacno3ae(nbins) !< Activity coefficients for HNO3 5572 REAL(wp) :: zcgnh3eqae(nbins) !< Equilibrium gas concentration: NH3 5573 REAL(wp) :: zcgno3eqae(nbins) !< Equilibrium gas concentration: HNO3 5574 REAL(wp) :: zcnh3c !< Current NH3 gas concentration 5575 REAL(wp) :: zcnh3int !< Intermediate NH3 gas concentration 5576 REAL(wp) :: zcnh3intae(nbins) !< Intermediate NH3 aerosol concentration 5577 REAL(wp) :: zcnh3n !< New NH3 gas concentration 5578 REAL(wp) :: zcnh3cae(nbins) !< Current NH3 in aerosols 5579 REAL(wp) :: zcnh3nae(nbins) !< New NH3 in aerosols 5580 REAL(wp) :: zcnh3tot !< Total NH3 concentration 5581 REAL(wp) :: zcno3c !< Current HNO3 gas concentration 5582 REAL(wp) :: zcno3int !< Intermediate HNO3 gas concentration 5583 REAL(wp) :: zcno3intae(nbins) !< Intermediate HNO3 aerosol concentration 5584 REAL(wp) :: zcno3n !< New HNO3 gas concentration 5585 REAL(wp) :: zcno3cae(nbins) !< Current HNO3 in aerosols 5586 REAL(wp) :: zcno3nae(nbins) !< New HNO3 in aerosols 5587 REAL(wp) :: zcno3tot !< Total HNO3 concentration 5588 REAL(wp) :: zdfvap !< Diffusion coefficient for vapors 5589 REAL(wp) :: zhlp1 !< helping variable 5590 REAL(wp) :: zhlp2 !< helping variable 5591 REAL(wp) :: zkelnh3ae(nbins) !< Kelvin effects for NH3 5592 REAL(wp) :: zkelno3ae(nbins) !< Kelvin effect for HNO3 5593 REAL(wp) :: zmolsae(nbins,7) !< Ion molalities from pdfite 5594 REAL(wp) :: zmtnh3ae(nbins) !< Mass transfer coefficients for NH3 5595 REAL(wp) :: zmtno3ae(nbins) !< Mass transfer coefficients for HNO3 5596 REAL(wp) :: zrh !< relative humidity 5597 REAL(wp) :: zsathno3ae(nbins) !< HNO3 saturation ratio 5598 REAL(wp) :: zsatnh3ae(nbins) !< NH3 saturation ratio = the partial 5599 !< pressure of a gas divided by its 5600 !< saturation vapor pressure over a surface 5601 ! 5608 5609 INTEGER(iwp) :: ib !< loop index 5610 5611 REAL(wp) :: adt !< timestep 5612 REAL(wp) :: zc_nh3_c !< Current NH3 gas concentration 5613 REAL(wp) :: zc_nh3_int !< Intermediate NH3 gas concentration 5614 REAL(wp) :: zc_nh3_n !< New NH3 gas concentration 5615 REAL(wp) :: zc_nh3_tot !< Total NH3 concentration 5616 REAL(wp) :: zc_hno3_c !< Current HNO3 gas concentration 5617 REAL(wp) :: zc_hno3_int !< Intermediate HNO3 gas concentration 5618 REAL(wp) :: zc_hno3_n !< New HNO3 gas concentration 5619 REAL(wp) :: zc_hno3_tot !< Total HNO3 concentration 5620 REAL(wp) :: zdfvap !< Diffusion coefficient for vapors 5621 REAL(wp) :: zhlp1 !< intermediate variable 5622 REAL(wp) :: zhlp2 !< intermediate variable 5623 REAL(wp) :: zrh !< relative humidity 5624 5625 REAL(wp), INTENT(in) :: ppres !< ambient pressure (Pa) 5626 REAL(wp), INTENT(in) :: pcs !< water vapour saturation 5627 !< concentration (kg/m3) 5628 REAL(wp), INTENT(in) :: ptemp !< ambient temperature (K) 5629 REAL(wp), INTENT(in) :: ptstep !< time step (s) 5630 5631 REAL(wp), INTENT(inout) :: pghno3 !< nitric acid concentration (#/m3) 5632 REAL(wp), INTENT(inout) :: pgnh3 !< ammonia conc. (#/m3) 5633 REAL(wp), INTENT(inout) :: pcw !< water vapour concentration (kg/m3) 5634 5635 REAL(wp), DIMENSION(nbins_aerosol) :: zac_hno3_ae !< Activity coefficients for HNO3 5636 REAL(wp), DIMENSION(nbins_aerosol) :: zac_hhso4_ae !< Activity coefficients for HHSO4 5637 REAL(wp), DIMENSION(nbins_aerosol) :: zac_nh3_ae !< Activity coefficients for NH3 5638 REAL(wp), DIMENSION(nbins_aerosol) :: zac_nh4hso2_ae !< Activity coefficients for NH4HSO2 5639 REAL(wp), DIMENSION(nbins_aerosol) :: zcg_hno3_eq_ae !< Equilibrium gas concentration: HNO3 5640 REAL(wp), DIMENSION(nbins_aerosol) :: zcg_nh3_eq_ae !< Equilibrium gas concentration: NH3 5641 REAL(wp), DIMENSION(nbins_aerosol) :: zc_hno3_int_ae !< Intermediate HNO3 aerosol concentration 5642 REAL(wp), DIMENSION(nbins_aerosol) :: zc_hno3_c_ae !< Current HNO3 in aerosols 5643 REAL(wp), DIMENSION(nbins_aerosol) :: zc_hno3_n_ae !< New HNO3 in aerosols 5644 REAL(wp), DIMENSION(nbins_aerosol) :: zc_nh3_int_ae !< Intermediate NH3 aerosol concentration 5645 REAL(wp), DIMENSION(nbins_aerosol) :: zc_nh3_c_ae !< Current NH3 in aerosols 5646 REAL(wp), DIMENSION(nbins_aerosol) :: zc_nh3_n_ae !< New NH3 in aerosols 5647 REAL(wp), DIMENSION(nbins_aerosol) :: zkel_hno3_ae !< Kelvin effect for HNO3 5648 REAL(wp), DIMENSION(nbins_aerosol) :: zkel_nh3_ae !< Kelvin effects for NH3 5649 REAL(wp), DIMENSION(nbins_aerosol) :: zmt_hno3_ae !< Mass transfer coefficients for HNO3 5650 REAL(wp), DIMENSION(nbins_aerosol) :: zmt_nh3_ae !< Mass transfer coefficients for NH3 5651 REAL(wp), DIMENSION(nbins_aerosol) :: zsat_hno3_ae !< HNO3 saturation ratio over a surface 5652 REAL(wp), DIMENSION(nbins_aerosol) :: zsat_nh3_ae !< NH3 saturation ratio over a surface 5653 5654 REAL(wp), DIMENSION(nbins_aerosol,maxspec) :: zion_mols !< Ion molalities from pdfite aerosols 5655 5656 REAL(wp), DIMENSION(nbins_aerosol), INTENT(in) :: pbeta !< transitional correction factor for 5657 5658 TYPE(t_section), DIMENSION(nbins_aerosol), INTENT(inout) :: paero !< Aerosol properties 5659 ! 5602 5660 !-- Initialise: 5603 adt = ptstep 5604 zachhso4ae = 0.0_wp 5605 zacnh3ae = 0.0_wp 5606 zacnh4hso2ae = 0.0_wp 5607 zacno3ae = 0.0_wp 5608 zcgnh3eqae = 0.0_wp 5609 zcgno3eqae = 0.0_wp 5610 zcnh3c = 0.0_wp 5611 zcnh3cae = 0.0_wp 5612 zcnh3int = 0.0_wp 5613 zcnh3intae = 0.0_wp 5614 zcnh3n = 0.0_wp 5615 zcnh3nae = 0.0_wp 5616 zcnh3tot = 0.0_wp 5617 zcno3c = 0.0_wp 5618 zcno3cae = 0.0_wp 5619 zcno3int = 0.0_wp 5620 zcno3intae = 0.0_wp 5621 zcno3n = 0.0_wp 5622 zcno3nae = 0.0_wp 5623 zcno3tot = 0.0_wp 5624 zhlp1 = 0.0_wp 5625 zhlp2 = 0.0_wp 5626 zkelno3ae = 1.0_wp 5627 zkelnh3ae = 1.0_wp 5628 zmolsae = 0.0_wp 5629 zmtno3ae = 0.0_wp 5630 zmtnh3ae = 0.0_wp 5631 zrh = 0.0_wp 5632 zsatnh3ae = 1.0_wp 5633 zsathno3ae = 1.0_wp 5634 ! 5635 !-- Diffusion coefficient (m2/s) 5636 zdfvap = 5.1111E-10_wp * ptemp ** 1.75_wp * ( p_0 + 1325.0_wp ) / ppres 5637 ! 5661 adt = ptstep 5662 zac_hhso4_ae = 0.0_wp 5663 zac_nh3_ae = 0.0_wp 5664 zac_nh4hso2_ae = 0.0_wp 5665 zac_hno3_ae = 0.0_wp 5666 zcg_nh3_eq_ae = 0.0_wp 5667 zcg_hno3_eq_ae = 0.0_wp 5668 zion_mols = 0.0_wp 5669 zsat_nh3_ae = 1.0_wp 5670 zsat_hno3_ae = 1.0_wp 5671 ! 5672 !-- Diffusion coefficient (m2/s) 5673 zdfvap = 5.1111E-10_wp * ptemp**1.75_wp * ( p_0 + 1325.0_wp ) / ppres 5674 ! 5638 5675 !-- Kelvin effects (Jacobson (2005), eq. 16.33) 5639 zkel no3ae(1:nbins) = EXP( 4.0_wp * surfw0 * amvhno3 / ( abo * ptemp *&5640 paero(1:nbins)%dwet ) )5641 zkel nh3ae(1:nbins) = EXP( 4.0_wp * surfw0 * amvnh3 / ( abo * ptemp *&5642 paero(1:nbins)%dwet ) )5643 ! 5676 zkel_hno3_ae(1:nbins_aerosol) = EXP( 4.0_wp * surfw0 * amvhno3 / & 5677 ( abo * ptemp * paero(1:nbins_aerosol)%dwet ) ) 5678 zkel_nh3_ae(1:nbins_aerosol) = EXP( 4.0_wp * surfw0 * amvnh3 / & 5679 ( abo * ptemp * paero(1:nbins_aerosol)%dwet ) ) 5680 ! 5644 5681 !-- Current vapour mole concentrations (mol/m3) 5645 zc no3c = pghno3 / avo! HNO35646 zc nh3c = pgnh3 / avo! NH35647 ! 5682 zc_hno3_c = pghno3 / avo ! HNO3 5683 zc_nh3_c = pgnh3 / avo ! NH3 5684 ! 5648 5685 !-- Current particle mole concentrations (mol/m3) 5649 zc no3cae(1:nbins) = paero(1:nbins)%volc(6) * arhohno3 / amhno35650 zc nh3cae(1:nbins) = paero(1:nbins)%volc(7) * arhonh3 / amnh35651 ! 5686 zc_hno3_c_ae(1:nbins_aerosol) = paero(1:nbins_aerosol)%volc(6) * arhohno3 / amhno3 5687 zc_nh3_c_ae(1:nbins_aerosol) = paero(1:nbins_aerosol)%volc(7) * arhonh3 / amnh3 5688 ! 5652 5689 !-- Total mole concentrations: gas and particle phase 5653 zc no3tot = zcno3c + SUM( zcno3cae(1:nbins) )5654 zc nh3tot = zcnh3c + SUM( zcnh3cae(1:nbins) )5655 ! 5690 zc_hno3_tot = zc_hno3_c + SUM( zc_hno3_c_ae(1:nbins_aerosol) ) 5691 zc_nh3_tot = zc_nh3_c + SUM( zc_nh3_c_ae(1:nbins_aerosol) ) 5692 ! 5656 5693 !-- Relative humidity [0-1] 5657 5694 zrh = pcw / pcs 5658 ! 5695 ! 5659 5696 !-- Mass transfer coefficients (Jacobson, Eq. 16.64) 5660 zmtno3ae(1:nbins) = 2.0_wp * pi * paero(1:nbins)%dwet * zdfvap * & 5661 paero(1:nbins)%numc * pbeta(1:nbins) 5662 zmtnh3ae(1:nbins) = 2.0_wp * pi * paero(1:nbins)%dwet * zdfvap * & 5663 paero(1:nbins)%numc * pbeta(1:nbins) 5664 5665 ! 5697 zmt_hno3_ae(:) = 2.0_wp * pi * paero(:)%dwet * zdfvap * paero(:)%numc * pbeta(:) 5698 zmt_nh3_ae(:) = 2.0_wp * pi * paero(:)%dwet * zdfvap * paero(:)%numc * pbeta(:) 5699 5700 ! 5666 5701 !-- Get the equilibrium concentrations above aerosols 5667 CALL NONHEquil( zrh, ptemp, paero, zcgno3eqae, zcgnh3eqae, zacno3ae, & 5668 zacnh3ae, zacnh4hso2ae, zachhso4ae, zmolsae ) 5669 5670 ! 5671 !-- NH4/HNO3 saturation ratios for aerosols 5672 CALL SVsat( ptemp, paero, zacno3ae, zacnh4hso2ae, zachhso4ae, zcgno3eqae, & 5673 zcno3cae, zcnh3cae, zkelno3ae, zkelnh3ae, zsathno3ae, zsatnh3ae ) 5674 ! 5675 !-- Intermediate concentrations 5676 zhlp1 = SUM( zcno3cae(1:nbins) / ( 1.0_wp + adt * zmtno3ae(1:nbins) * & 5677 zsathno3ae(1:nbins) ) ) 5678 zhlp2 = SUM( zmtno3ae(1:nbins) / ( 1.0_wp + adt * zmtno3ae(1:nbins) * & 5679 zsathno3ae(1:nbins) ) ) 5680 zcno3int = ( zcno3tot - zhlp1 ) / ( 1.0_wp + adt * zhlp2 ) 5681 5682 zhlp1 = SUM( zcnh3cae(1:nbins) / ( 1.0_wp + adt * zmtnh3ae(1:nbins) * & 5683 zsatnh3ae(1:nbins) ) ) 5684 zhlp2 = SUM( zmtnh3ae(1:nbins) / ( 1.0_wp + adt * zmtnh3ae(1:nbins) * & 5685 zsatnh3ae(1:nbins) ) ) 5686 zcnh3int = ( zcnh3tot - zhlp1 )/( 1.0_wp + adt * zhlp2 ) 5687 5688 zcno3int = MIN(zcno3int, zcno3tot) 5689 zcnh3int = MIN(zcnh3int, zcnh3tot) 5690 ! 5691 !-- Calculate the new particle concentrations 5692 zcno3intae = zcno3cae 5693 zcnh3intae = zcnh3cae 5694 DO b = 1, nbins 5695 zcno3intae(b) = ( zcno3cae(b) + adt * zmtno3ae(b) * zcno3int ) / & 5696 ( 1.0_wp + adt * zmtno3ae(b) * zsathno3ae(b) ) 5697 zcnh3intae(b) = ( zcnh3cae(b) + adt * zmtnh3ae(b) * zcnh3int ) / & 5698 ( 1.0_wp + adt * zmtnh3ae(b) * zsatnh3ae(b) ) 5702 CALL nitrate_ammonium_equilibrium( zrh, ptemp, paero, zcg_hno3_eq_ae, zcg_nh3_eq_ae, & 5703 zac_hno3_ae, zac_nh3_ae, zac_nh4hso2_ae, zac_hhso4_ae, & 5704 zion_mols ) 5705 ! 5706 !-- Calculate NH3 and HNO3 saturation ratios for aerosols 5707 CALL nitrate_ammonium_saturation( ptemp, paero, zac_hno3_ae, zac_nh4hso2_ae, zac_hhso4_ae, & 5708 zcg_hno3_eq_ae, zc_hno3_c_ae, zc_nh3_c_ae, zkel_hno3_ae, & 5709 zkel_nh3_ae, zsat_hno3_ae, zsat_nh3_ae ) 5710 ! 5711 !-- Intermediate gas concentrations of HNO3 and NH3 5712 zhlp1 = SUM( zc_hno3_c_ae(:) / ( 1.0_wp + adt * zmt_hno3_ae(:) * zsat_hno3_ae(:) ) ) 5713 zhlp2 = SUM( zmt_hno3_ae(:) / ( 1.0_wp + adt * zmt_hno3_ae(:) * zsat_hno3_ae(:) ) ) 5714 zc_hno3_int = ( zc_hno3_tot - zhlp1 ) / ( 1.0_wp + adt * zhlp2 ) 5715 5716 zhlp1 = SUM( zc_nh3_c_ae(:) / ( 1.0_wp + adt * zmt_nh3_ae(:) * zsat_nh3_ae(:) ) ) 5717 zhlp2 = SUM( zmt_nh3_ae(:) / ( 1.0_wp + adt * zmt_nh3_ae(:) * zsat_nh3_ae(:) ) ) 5718 zc_nh3_int = ( zc_nh3_tot - zhlp1 )/( 1.0_wp + adt * zhlp2 ) 5719 5720 zc_hno3_int = MIN( zc_hno3_int, zc_hno3_tot ) 5721 zc_nh3_int = MIN( zc_nh3_int, zc_nh3_tot ) 5722 ! 5723 !-- Calculate the new concentration on aerosol particles 5724 zc_hno3_int_ae = zc_hno3_c_ae 5725 zc_nh3_int_ae = zc_nh3_c_ae 5726 DO ib = 1, nbins_aerosol 5727 zc_hno3_int_ae(ib) = ( zc_hno3_c_ae(ib) + adt * zmt_hno3_ae(ib) * zc_hno3_int ) / & 5728 ( 1.0_wp + adt * zmt_hno3_ae(ib) * zsat_hno3_ae(ib) ) 5729 zc_nh3_int_ae(ib) = ( zc_nh3_c_ae(ib) + adt * zmt_nh3_ae(ib) * zc_nh3_int ) / & 5730 ( 1.0_wp + adt * zmt_nh3_ae(ib) * zsat_nh3_ae(ib) ) 5699 5731 ENDDO 5700 5732 5701 zcno3intae(1:nbins) = MAX( zcno3intae(1:nbins), 0.0_wp ) 5702 zcnh3intae(1:nbins) = MAX( zcnh3intae(1:nbins), 0.0_wp ) 5703 5704 zcno3n = zcno3int ! Final molar gas concentration of HNO3 5705 zcno3nae = zcno3intae ! Final molar particle concentration of HNO3 5706 5707 zcnh3n = zcnh3int ! Final molar gas concentration of NH3 5708 zcnh3nae = zcnh3intae ! Final molar particle concentration of NH3 5709 ! 5710 !-- Model timestep reached - update the new arrays 5711 pghno3 = zcno3n * avo 5712 pgnh3 = zcnh3n * avo 5713 5714 DO b = in1a, fn2b 5715 paero(b)%volc(6) = zcno3nae(b) * amhno3 / arhohno3 5716 paero(b)%volc(7) = zcnh3nae(b) * amnh3 / arhonh3 5733 zc_hno3_int_ae(:) = MAX( zc_hno3_int_ae(:), 0.0_wp ) 5734 zc_nh3_int_ae(:) = MAX( zc_nh3_int_ae(:), 0.0_wp ) 5735 ! 5736 !-- Final molar gas concentration and molar particle concentration of HNO3 5737 zc_hno3_n = zc_hno3_int 5738 zc_hno3_n_ae = zc_hno3_int_ae 5739 ! 5740 !-- Final molar gas concentration and molar particle concentration of NH3 5741 zc_nh3_n = zc_nh3_int 5742 zc_nh3_n_ae = zc_nh3_int_ae 5743 ! 5744 !-- Model timestep reached - update the gas concentrations 5745 pghno3 = zc_hno3_n * avo 5746 pgnh3 = zc_nh3_n * avo 5747 ! 5748 !-- Update the particle concentrations 5749 DO ib = start_subrange_1a, end_subrange_2b 5750 paero(ib)%volc(6) = zc_hno3_n_ae(ib) * amhno3 / arhohno3 5751 paero(ib)%volc(7) = zc_nh3_n_ae(ib) * amnh3 / arhonh3 5717 5752 ENDDO 5718 5719 5753 5720 5754 END SUBROUTINE gpparthno3 5721 5755 !------------------------------------------------------------------------------! … … 5724 5758 !> Calculate the equilibrium concentrations above aerosols (reference?) 5725 5759 !------------------------------------------------------------------------------! 5726 SUBROUTINE NONHEquil( prh, ptemp, ppart, pcgno3eq, pcgnh3eq, pgammano,&5727 pgammanh, pgammanh4hso2, pgammahhso4, pmols )5728 5760 SUBROUTINE nitrate_ammonium_equilibrium( prh, ptemp, ppart, pcg_hno3_eq, pcg_nh3_eq, pgamma_hno3, & 5761 pgamma_nh4, pgamma_nh4hso2, pgamma_hhso4, pmols ) 5762 5729 5763 IMPLICIT NONE 5730 5764 5765 INTEGER(iwp) :: ib !< loop index: aerosol bins 5766 5767 REAL(wp) :: zhlp !< intermediate variable 5768 REAL(wp) :: zp_hcl !< Equilibrium vapor pressures (Pa) of HCl 5769 REAL(wp) :: zp_hno3 !< Equilibrium vapor pressures (Pa) of HNO3 5770 REAL(wp) :: zp_nh3 !< Equilibrium vapor pressures (Pa) of NH3 5771 REAL(wp) :: zwatertotal !< Total water in particles (mol/m3) 5772 5731 5773 REAL(wp), INTENT(in) :: prh !< relative humidity 5732 5774 REAL(wp), INTENT(in) :: ptemp !< ambient temperature (K) 5733 5734 TYPE(t_section), INTENT(inout) :: ppart(nbins) !< Aerosol properties 5735 !-- Equilibrium molar concentration above aerosols: 5736 REAL(wp), INTENT(inout) :: pcgnh3eq(nbins) !< of NH3 5737 REAL(wp), INTENT(inout) :: pcgno3eq(nbins) !< of HNO3 5738 !< Activity coefficients: 5739 REAL(wp), INTENT(inout) :: pgammahhso4(nbins) !< HHSO4 5740 REAL(wp), INTENT(inout) :: pgammanh(nbins) !< NH3 5741 REAL(wp), INTENT(inout) :: pgammanh4hso2(nbins) !< NH4HSO2 5742 REAL(wp), INTENT(inout) :: pgammano(nbins) !< HNO3 5743 REAL(wp), INTENT(inout) :: pmols(nbins,7) !< Ion molalities 5744 5745 INTEGER(iwp) :: b 5746 5747 REAL(wp) :: zgammas(7) !< Activity coefficients 5748 REAL(wp) :: zhlp !< Dummy variable 5749 REAL(wp) :: zions(7) !< molar concentration of ion (mol/m3) 5750 REAL(wp) :: zphcl !< Equilibrium vapor pressures (Pa??) 5751 REAL(wp) :: zphno3 !< Equilibrium vapor pressures (Pa??) 5752 REAL(wp) :: zpnh3 !< Equilibrium vapor pressures (Pa??) 5753 REAL(wp) :: zwatertotal !< Total water in particles (mol/m3) ??? 5775 5776 REAL(wp), DIMENSION(maxspec) :: zgammas !< Activity coefficients 5777 REAL(wp), DIMENSION(maxspec) :: zions !< molar concentration of ion (mol/m3) 5778 5779 REAL(wp), DIMENSION(nbins_aerosol), INTENT(inout) :: pcg_nh3_eq !< equilibrium molar 5780 !< concentration: of NH3 5781 REAL(wp), DIMENSION(nbins_aerosol), INTENT(inout) :: pcg_hno3_eq !< of HNO3 5782 REAL(wp), DIMENSION(nbins_aerosol), INTENT(inout) :: pgamma_hhso4 !< activity coeff. of HHSO4 5783 REAL(wp), DIMENSION(nbins_aerosol), INTENT(inout) :: pgamma_nh4 !< activity coeff. of NH3 5784 REAL(wp), DIMENSION(nbins_aerosol), INTENT(inout) :: pgamma_nh4hso2 !< activity coeff. of NH4HSO2 5785 REAL(wp), DIMENSION(nbins_aerosol), INTENT(inout) :: pgamma_hno3 !< activity coeff. of HNO3 5786 5787 REAL(wp), DIMENSION(nbins_aerosol,maxspec), INTENT(inout) :: pmols !< Ion molalities 5788 5789 TYPE(t_section), DIMENSION(nbins_aerosol), INTENT(inout) :: ppart !< Aerosol properties 5754 5790 5755 5791 zgammas = 0.0_wp 5756 5792 zhlp = 0.0_wp 5757 5793 zions = 0.0_wp 5758 zp hcl= 0.0_wp5759 zp hno3= 0.0_wp5760 zp nh3= 0.0_wp5794 zp_hcl = 0.0_wp 5795 zp_hno3 = 0.0_wp 5796 zp_nh3 = 0.0_wp 5761 5797 zwatertotal = 0.0_wp 5762 5798 5763 DO b = 1, nbins 5764 5765 IF ( ppart(b)%numc < nclim ) CYCLE 5766 ! 5767 !-- 2*H2SO4 + CL + NO3 - Na - NH4 5768 zhlp = 2.0_wp * ppart(b)%volc(1) * arhoh2so4 / amh2so4 + & 5769 ppart(b)%volc(5) * arhoss / amss + & 5770 ppart(b)%volc(6) * arhohno3 / amhno3 - & 5771 ppart(b)%volc(5) * arhoss / amss - & 5772 ppart(b)%volc(7) * arhonh3 / amnh3 5773 5774 zhlp = MAX( zhlp, 1.0E-30_wp ) 5799 DO ib = 1, nbins_aerosol 5800 5801 IF ( ppart(ib)%numc < nclim ) CYCLE 5802 ! 5803 !-- Ion molar concentrations: 2*H2SO4 + CL + NO3 - Na - NH4 5804 zhlp = 2.0_wp * ppart(ib)%volc(1) * arhoh2so4 / amh2so4 + ppart(ib)%volc(5) * arhoss / amss & 5805 + ppart(ib)%volc(6) * arhohno3 / amhno3 - ppart(ib)%volc(5) * arhoss / amss - & 5806 ppart(ib)%volc(7) * arhonh3 / amnh3 5775 5807 5776 5808 zions(1) = zhlp ! H+ 5777 zions(2) = ppart( b)%volc(7) * arhonh3 / amnh3 ! NH4+5778 zions(3) = ppart( b)%volc(5) * arhoss / amss ! Na+5779 zions(4) = ppart( b)%volc(1) * arhoh2so4 / amh2so4 ! SO4(2-)5809 zions(2) = ppart(ib)%volc(7) * arhonh3 / amnh3 ! NH4+ 5810 zions(3) = ppart(ib)%volc(5) * arhoss / amss ! Na+ 5811 zions(4) = ppart(ib)%volc(1) * arhoh2so4 / amh2so4 ! SO4(2-) 5780 5812 zions(5) = 0.0_wp ! HSO4- 5781 zions(6) = ppart( b)%volc(6) * arhohno3 / amhno3 ! NO3-5782 zions(7) = ppart( b)%volc(5) * arhoss / amss ! Cl-5783 5784 zwatertotal = ppart( b)%volc(8) * arhoh2o / amh2o5813 zions(6) = ppart(ib)%volc(6) * arhohno3 / amhno3 ! NO3- 5814 zions(7) = ppart(ib)%volc(5) * arhoss / amss ! Cl- 5815 5816 zwatertotal = ppart(ib)%volc(8) * arhoh2o / amh2o 5785 5817 IF ( zwatertotal > 1.0E-30_wp ) THEN 5786 CALL inorganic_pdfite( prh, ptemp, zions, zwatertotal, zp hno3, zphcl,&5787 zpnh3, zgammas, pmols(b,:) )5788 ENDIF 5789 ! 5790 !-- Activity coefficients 5791 pgamma no(b) = zgammas(1)! HNO35792 pgamma nh(b) = zgammas(3) ! NH35793 pgamma nh4hso2(b) = zgammas(6)! NH4HSO25794 pgamma hhso4(b) = zgammas(7)! HHSO45818 CALL inorganic_pdfite( prh, ptemp, zions, zwatertotal, zp_hno3, zp_hcl, zp_nh3, zgammas, & 5819 pmols(ib,:) ) 5820 ENDIF 5821 ! 5822 !-- Activity coefficients 5823 pgamma_hno3(ib) = zgammas(1) ! HNO3 5824 pgamma_nh4(ib) = zgammas(3) ! NH3 5825 pgamma_nh4hso2(ib) = zgammas(6) ! NH4HSO2 5826 pgamma_hhso4(ib) = zgammas(7) ! HHSO4 5795 5827 ! 5796 5828 !-- Equilibrium molar concentrations (mol/m3) from equlibrium pressures (Pa) 5797 pcg no3eq(b) = zphno3 / ( argas * ptemp )5798 pcg nh3eq(b) = zpnh3 / ( argas * ptemp )5829 pcg_hno3_eq(ib) = zp_hno3 / ( argas * ptemp ) 5830 pcg_nh3_eq(ib) = zp_nh3 / ( argas * ptemp ) 5799 5831 5800 5832 ENDDO 5801 5833 5802 END SUBROUTINE NONHEquil5803 5834 END SUBROUTINE nitrate_ammonium_equilibrium 5835 5804 5836 !------------------------------------------------------------------------------! 5805 5837 ! Description: … … 5807 5839 !> Calculate saturation ratios of NH4 and HNO3 for aerosols 5808 5840 !------------------------------------------------------------------------------! 5809 SUBROUTINE SVsat( ptemp, ppart, pachno3, pacnh4hso2, pachhso4, pchno3eq,&5810 pchno3, pcnh3, pkelhno3, pkelnh3, psathno3, psatnh3 )5841 SUBROUTINE nitrate_ammonium_saturation( ptemp, ppart, pachno3, pacnh4hso2, pachhso4, pchno3eq, & 5842 pchno3, pc_nh3, pkelhno3, pkelnh3, psathno3, psatnh3 ) 5811 5843 5812 5844 IMPLICIT NONE 5813 5845 5846 INTEGER(iwp) :: ib !< running index for aerosol bins 5847 5848 REAL(wp) :: k_ll_h2o !< equilibrium constants of equilibrium reactions: 5849 !< H2O(aq) <--> H+ + OH- (mol/kg) 5850 REAL(wp) :: k_ll_nh3 !< NH3(aq) + H2O(aq) <--> NH4+ + OH- (mol/kg) 5851 REAL(wp) :: k_gl_nh3 !< NH3(g) <--> NH3(aq) (mol/kg/atm) 5852 REAL(wp) :: k_gl_hno3 !< HNO3(g) <--> H+ + NO3- (mol2/kg2/atm) 5853 REAL(wp) :: zmol_no3 !< molality of NO3- (mol/kg) 5854 REAL(wp) :: zmol_h !< molality of H+ (mol/kg) 5855 REAL(wp) :: zmol_so4 !< molality of SO4(2-) (mol/kg) 5856 REAL(wp) :: zmol_cl !< molality of Cl- (mol/kg) 5857 REAL(wp) :: zmol_nh4 !< molality of NH4+ (mol/kg) 5858 REAL(wp) :: zmol_na !< molality of Na+ (mol/kg) 5859 REAL(wp) :: zhlp1 !< intermediate variable 5860 REAL(wp) :: zhlp2 !< intermediate variable 5861 REAL(wp) :: zhlp3 !< intermediate variable 5862 REAL(wp) :: zxi !< particle mole concentration ratio: (NH3+SS)/H2SO4 5863 REAL(wp) :: zt0 !< reference temp 5864 5865 REAL(wp), PARAMETER :: a1 = -22.52_wp !< 5866 REAL(wp), PARAMETER :: a2 = -1.50_wp !< 5867 REAL(wp), PARAMETER :: a3 = 13.79_wp !< 5868 REAL(wp), PARAMETER :: a4 = 29.17_wp !< 5869 REAL(wp), PARAMETER :: b1 = 26.92_wp !< 5870 REAL(wp), PARAMETER :: b2 = 26.92_wp !< 5871 REAL(wp), PARAMETER :: b3 = -5.39_wp !< 5872 REAL(wp), PARAMETER :: b4 = 16.84_wp !< 5873 REAL(wp), PARAMETER :: K01 = 1.01E-14_wp !< 5874 REAL(wp), PARAMETER :: K02 = 1.81E-5_wp !< 5875 REAL(wp), PARAMETER :: K03 = 57.64_wp !< 5876 REAL(wp), PARAMETER :: K04 = 2.51E+6_wp !< 5877 5814 5878 REAL(wp), INTENT(in) :: ptemp !< ambient temperature (K) 5815 5816 TYPE(t_section), INTENT(inout) :: ppart(nbins) !< Aerosol properties 5817 !-- Activity coefficients 5818 REAL(wp), INTENT(in) :: pachhso4(nbins) !< 5819 REAL(wp), INTENT(in) :: pacnh4hso2(nbins) !< 5820 REAL(wp), INTENT(in) :: pachno3(nbins) !< 5821 REAL(wp), INTENT(in) :: pchno3eq(nbins) !< Equilibrium surface concentration 5822 !< of HNO3 5823 REAL(wp), INTENT(in) :: pchno3(nbins) !< Current particle mole 5824 !< concentration of HNO3 (mol/m3) 5825 REAL(wp), INTENT(in) :: pcnh3(nbins) !< Current particle mole 5826 !< concentration of NH3 (mol/m3) 5827 REAL(wp), INTENT(in) :: pkelhno3(nbins) !< Kelvin effect for HNO3 5828 REAL(wp), INTENT(in) :: pkelnh3(nbins) !< Kelvin effect for NH3 5829 !-- Saturation ratios 5830 REAL(wp), INTENT(out) :: psathno3(nbins) !< 5831 REAL(wp), INTENT(out) :: psatnh3(nbins) !< 5832 5833 INTEGER :: b !< running index for aerosol bins 5834 !-- Constants for calculating equilibrium constants: 5835 REAL(wp), PARAMETER :: a1 = -22.52_wp !< 5836 REAL(wp), PARAMETER :: a2 = -1.50_wp !< 5837 REAL(wp), PARAMETER :: a3 = 13.79_wp !< 5838 REAL(wp), PARAMETER :: a4 = 29.17_wp !< 5839 REAL(wp), PARAMETER :: b1 = 26.92_wp !< 5840 REAL(wp), PARAMETER :: b2 = 26.92_wp !< 5841 REAL(wp), PARAMETER :: b3 = -5.39_wp !< 5842 REAL(wp), PARAMETER :: b4 = 16.84_wp !< 5843 REAL(wp), PARAMETER :: K01 = 1.01E-14_wp !< 5844 REAL(wp), PARAMETER :: K02 = 1.81E-5_wp !< 5845 REAL(wp), PARAMETER :: K03 = 57.64_wp !< 5846 REAL(wp), PARAMETER :: K04 = 2.51E+6_wp !< 5847 !-- Equilibrium constants of equilibrium reactions 5848 REAL(wp) :: KllH2O !< H2O(aq) <--> H+ + OH- (mol/kg) 5849 REAL(wp) :: KllNH3 !< NH3(aq) + H2O(aq) <--> NH4+ + OH- (mol/kg) 5850 REAL(wp) :: KglNH3 !< NH3(g) <--> NH3(aq) (mol/kg/atm) 5851 REAL(wp) :: KglHNO3 !< HNO3(g) <--> H+ + NO3- (mol2/kg2/atm) 5852 REAL(wp) :: zmolno3 !< molality of NO3- (mol/kg) 5853 REAL(wp) :: zmolhp !< molality of H+ (mol/kg) 5854 REAL(wp) :: zmolso4 !< molality of SO4(2-) (mol/kg) 5855 REAL(wp) :: zmolcl !< molality of Cl (mol/kg) 5856 REAL(wp) :: zmolnh4 !< Molality of NH4 (mol/kg) 5857 REAL(wp) :: zmolna !< Molality of Na (mol/kg) 5858 REAL(wp) :: zhlp1 !< 5859 REAL(wp) :: zhlp2 !< 5860 REAL(wp) :: zhlp3 !< 5861 REAL(wp) :: zxi !< 5862 REAL(wp) :: zt0 !< Reference temp 5863 5864 zhlp1 = 0.0_wp 5865 zhlp2 = 0.0_wp 5866 zhlp3 = 0.0_wp 5867 zmolcl = 0.0_wp 5868 zmolhp = 0.0_wp 5869 zmolna = 0.0_wp 5870 zmolnh4 = 0.0_wp 5871 zmolno3 = 0.0_wp 5872 zmolso4 = 0.0_wp 5873 zt0 = 298.15_wp 5874 zxi = 0.0_wp 5875 ! 5876 !-- Calculates equlibrium rate constants based on Table B.7 in Jacobson (2005) 5877 !-- K^ll_H20, K^ll_NH3, K^gl_NH3, K^gl_HNO3 5879 5880 REAL(wp), DIMENSION(nbins_aerosol), INTENT(in) :: pachhso4 !< activity coeff. of HHSO4 5881 REAL(wp), DIMENSION(nbins_aerosol), INTENT(in) :: pacnh4hso2 !< activity coeff. of NH4HSO2 5882 REAL(wp), DIMENSION(nbins_aerosol), INTENT(in) :: pachno3 !< activity coeff. of HNO3 5883 REAL(wp), DIMENSION(nbins_aerosol), INTENT(in) :: pchno3eq !< eq. surface concentration: HNO3 5884 REAL(wp), DIMENSION(nbins_aerosol), INTENT(in) :: pchno3 !< current particle mole 5885 !< concentration of HNO3 (mol/m3) 5886 REAL(wp), DIMENSION(nbins_aerosol), INTENT(in) :: pc_nh3 !< of NH3 (mol/m3) 5887 REAL(wp), DIMENSION(nbins_aerosol), INTENT(in) :: pkelhno3 !< Kelvin effect for HNO3 5888 REAL(wp), DIMENSION(nbins_aerosol), INTENT(in) :: pkelnh3 !< Kelvin effect for NH3 5889 5890 REAL(wp), DIMENSION(nbins_aerosol), INTENT(out) :: psathno3 !< saturation ratio of HNO3 5891 REAL(wp), DIMENSION(nbins_aerosol), INTENT(out) :: psatnh3 !< saturation ratio of NH3 5892 5893 TYPE(t_section), DIMENSION(nbins_aerosol), INTENT(inout) :: ppart !< Aerosol properties 5894 5895 zmol_cl = 0.0_wp 5896 zmol_h = 0.0_wp 5897 zmol_na = 0.0_wp 5898 zmol_nh4 = 0.0_wp 5899 zmol_no3 = 0.0_wp 5900 zmol_so4 = 0.0_wp 5901 zt0 = 298.15_wp 5902 zxi = 0.0_wp 5903 ! 5904 !-- Calculates equlibrium rate constants based on Table B.7 in Jacobson (2005): 5905 !-- K^ll_H20, K^ll_NH3, K^gl_NH3, K^gl_HNO3 5878 5906 zhlp1 = zt0 / ptemp 5879 5907 zhlp2 = zhlp1 - 1.0_wp 5880 5908 zhlp3 = 1.0_wp + LOG( zhlp1 ) - zhlp1 5881 5909 5882 KllH2O = K01 * EXP( a1 * zhlp2 + b1 * zhlp3 ) 5883 KllNH3 = K02 * EXP( a2 * zhlp2 + b2 * zhlp3 ) 5884 KglNH3 = K03 * EXP( a3 * zhlp2 + b3 * zhlp3 ) 5885 KglHNO3 = K04 * EXP( a4 * zhlp2 + b4 * zhlp3 ) 5886 5887 DO b = 1, nbins 5888 5889 IF ( ppart(b)%numc > nclim .AND. ppart(b)%volc(8) > 1.0E-30_wp ) THEN 5890 ! 5891 !-- Molality of H+ and NO3- 5892 zhlp1 = pcnh3(b) * amnh3 + ppart(b)%volc(1) * arhoh2so4 + & 5893 ppart(b)%volc(2) * arhooc + ppart(b)%volc(5) * arhoss + & 5894 ppart(b)%volc(8) * arhoh2o 5895 zmolno3 = pchno3(b) / zhlp1 !< mol/kg 5896 ! 5897 !-- Particle mole concentration ratio: (NH3+SS)/H2SO4 5898 zxi = ( pcnh3(b) + ppart(b)%volc(5) * arhoss / amss ) / & 5899 ( ppart(b)%volc(1) * arhoh2so4 / amh2so4 ) 5900 5910 k_ll_h2o = K01 * EXP( a1 * zhlp2 + b1 * zhlp3 ) 5911 k_ll_nh3 = K02 * EXP( a2 * zhlp2 + b2 * zhlp3 ) 5912 k_gl_nh3 = K03 * EXP( a3 * zhlp2 + b3 * zhlp3 ) 5913 k_gl_hno3 = K04 * EXP( a4 * zhlp2 + b4 * zhlp3 ) 5914 5915 DO ib = 1, nbins_aerosol 5916 5917 IF ( ppart(ib)%numc > nclim .AND. ppart(ib)%volc(8) > 1.0E-30_wp ) THEN 5918 ! 5919 !-- Molality of H+ and NO3- 5920 zhlp1 = pc_nh3(ib) * amnh3 + ppart(ib)%volc(1) * arhoh2so4 + ppart(ib)%volc(2) * arhooc & 5921 + ppart(ib)%volc(5) * arhoss + ppart(ib)%volc(8) * arhoh2o 5922 zmol_no3 = pchno3(ib) / zhlp1 !< mol/kg 5923 ! 5924 !-- Particle mole concentration ratio: (NH3+SS)/H2SO4 5925 zxi = ( pc_nh3(ib) + ppart(ib)%volc(5) * arhoss / amss ) / ( ppart(ib)%volc(1) * & 5926 arhoh2so4 / amh2so4 ) 5927 5901 5928 IF ( zxi <= 2.0_wp ) THEN 5902 5929 ! 5903 5930 !-- Molality of SO4(2-) 5904 zhlp1 = pcnh3(b) * amnh3 + pchno3(b) * amhno3 + & 5905 ppart(b)%volc(2) * arhooc + ppart(b)%volc(5) * arhoss + & 5906 ppart(b)%volc(8) * arhoh2o 5907 zmolso4 = ( ppart(b)%volc(1) * arhoh2so4 / amh2so4 ) / zhlp1 5931 zhlp1 = pc_nh3(ib) * amnh3 + pchno3(ib) * amhno3 + ppart(ib)%volc(2) * arhooc + & 5932 ppart(ib)%volc(5) * arhoss + ppart(ib)%volc(8) * arhoh2o 5933 zmol_so4 = ( ppart(ib)%volc(1) * arhoh2so4 / amh2so4 ) / zhlp1 5908 5934 ! 5909 5935 !-- Molality of Cl- 5910 zhlp1 = pcnh3(b) * amnh3 + pchno3(b) * amhno3 + & 5911 ppart(b)%volc(2) * arhooc + ppart(b)%volc(1) * arhoh2so4 & 5912 + ppart(b)%volc(8) * arhoh2o 5913 zmolcl = ( ppart(b)%volc(5) * arhoss / amss ) / zhlp1 5936 zhlp1 = pc_nh3(ib) * amnh3 + pchno3(ib) * amhno3 + ppart(ib)%volc(2) * arhooc + & 5937 ppart(ib)%volc(1) * arhoh2so4 + ppart(ib)%volc(8) * arhoh2o 5938 zmol_cl = ( ppart(ib)%volc(5) * arhoss / amss ) / zhlp1 5914 5939 ! 5915 5940 !-- Molality of NH4+ 5916 zhlp1 = pchno3(b) * amhno3 + ppart(b)%volc(1) * arhoh2so4 + & 5917 ppart(b)%volc(2) * arhooc + ppart(b)%volc(5) * arhoss + & 5918 ppart(b)%volc(8) * arhoh2o 5919 zmolnh4 = pcnh3(b) / zhlp1 5920 ! 5941 zhlp1 = pchno3(ib) * amhno3 + ppart(ib)%volc(1) * arhoh2so4 + ppart(ib)%volc(2) * & 5942 arhooc + ppart(ib)%volc(5) * arhoss + ppart(ib)%volc(8) * arhoh2o 5943 zmol_nh4 = pc_nh3(ib) / zhlp1 5944 ! 5921 5945 !-- Molality of Na+ 5922 zmol na = zmolcl5946 zmol_na = zmol_cl 5923 5947 ! 5924 5948 !-- Molality of H+ 5925 zmol hp = 2.0_wp * zmolso4 + zmolno3 + zmolcl - ( zmolnh4 + zmolna )5949 zmol_h = 2.0_wp * zmol_so4 + zmol_no3 + zmol_cl - ( zmol_nh4 + zmol_na ) 5926 5950 5927 5951 ELSE 5928 5952 5929 zhlp2 = pkelhno3(b) * zmolno3 * pachno3(b) ** 2.0_wp 5930 ! 5931 !-- Mona debugging 5953 zhlp2 = pkelhno3(ib) * zmol_no3 * pachno3(ib)**2 5954 5932 5955 IF ( zhlp2 > 1.0E-30_wp ) THEN 5933 zmol hp = KglHNO3 * pchno3eq(b) / zhlp2 ! Eq. 17.385956 zmol_h = k_gl_hno3 * pchno3eq(ib) / zhlp2 ! Eq. 17.38 5934 5957 ELSE 5935 zmol hp= 0.0_wp5958 zmol_h = 0.0_wp 5936 5959 ENDIF 5937 5960 5938 5961 ENDIF 5939 5962 5940 zhlp1 = ppart( b)%volc(8) * arhoh2o * argas * ptemp * KglHNO35963 zhlp1 = ppart(ib)%volc(8) * arhoh2o * argas * ptemp * k_gl_hno3 5941 5964 ! 5942 5965 !-- Saturation ratio for NH3 and for HNO3 5943 IF ( zmolhp > 0.0_wp ) THEN 5944 zhlp2 = pkelnh3(b) / ( zhlp1 * zmolhp ) 5945 zhlp3 = KllH2O / ( KllNH3 + KglNH3 ) 5946 psatnh3(b) = zhlp2 * ( ( pacnh4hso2(b) / pachhso4(b) ) **2.0_wp ) & 5947 * zhlp3 5948 psathno3(b) = ( pkelhno3(b) * zmolhp * pachno3(b)**2.0_wp ) / zhlp1 5966 IF ( zmol_h > 0.0_wp ) THEN 5967 zhlp2 = pkelnh3(ib) / ( zhlp1 * zmol_h ) 5968 zhlp3 = k_ll_h2o / ( k_ll_nh3 + k_gl_nh3 ) 5969 psatnh3(ib) = zhlp2 * ( ( pacnh4hso2(ib) / pachhso4(ib) )**2 ) * zhlp3 5970 psathno3(ib) = ( pkelhno3(ib) * zmol_h * pachno3(ib)**2 ) / zhlp1 5949 5971 ELSE 5950 psatnh3( b) = 1.0_wp5951 psathno3( b) = 1.0_wp5972 psatnh3(ib) = 1.0_wp 5973 psathno3(ib) = 1.0_wp 5952 5974 ENDIF 5953 5975 ELSE 5954 psatnh3( b) = 1.0_wp5955 psathno3( b) = 1.0_wp5976 psatnh3(ib) = 1.0_wp 5977 psathno3(ib) = 1.0_wp 5956 5978 ENDIF 5957 5979 5958 5980 ENDDO 5959 5981 5960 END SUBROUTINE SVsat5961 5982 END SUBROUTINE nitrate_ammonium_saturation 5983 5962 5984 !------------------------------------------------------------------------------! 5963 5985 ! Description: 5964 5986 ! ------------ 5965 5987 !> Prototype module for calculating the water content of a mixed inorganic/ 5966 !> organic particle + equilibrium water vapour pressure above the solution 5967 !> (HNO3, HCL, NH3 and representative organic compounds. Efficient calculation 5968 !> of the partitioning of species between gas and aerosol. Based in a chamber 5969 !> study. 5970 ! 5971 !> Written by Dave Topping. Pure organic component properties predicted by Mark 5972 !> Barley based on VOCs predicted in MCM simulations performed by Mike Jenkin. 5973 !> Delivered by Gordon McFiggans as Deliverable D22 from WP1.4 in the EU FP6 5988 !> organic particle + equilibrium water vapour pressure above the solution 5989 !> (HNO3, HCL, NH3 and representative organic compounds. Efficient calculation 5990 !> of the partitioning of species between gas and aerosol. Based in a chamber 5991 !> study. 5992 ! 5993 !> Written by Dave Topping. Pure organic component properties predicted by Mark 5994 !> Barley based on VOCs predicted in MCM simulations performed by Mike Jenkin. 5995 !> Delivered by Gordon McFiggans as Deliverable D22 from WP1.4 in the EU FP6 5974 5996 !> EUCAARI Integrated Project. 5975 5997 ! 5976 !> Queries concerning the use of this code through Gordon McFiggans, 5998 !> REFERENCES 5999 !> Clegg et al. (1998) A Thermodynamic Model of the System H+-NH4+-Na+-SO42- -NO3--Cl--H2O at 6000 !> 298.15 K, J. Phys. Chem., 102A, 2155-2171. 6001 !> Clegg et al. (2001) Thermodynamic modelling of aqueous aerosols containing electrolytes and 6002 !> dissolved organic compounds. Journal of Aerosol Science 2001;32(6):713-738. 6003 !> Topping et al. (2005a) A curved multi-component aerosol hygroscopicity model framework: Part 1 - 6004 !> Inorganic compounds. Atmospheric Chemistry and Physics 2005;5:1205-1222. 6005 !> Topping et al. (2005b) A curved multi-component aerosol hygroscopicity model framework: Part 2 - 6006 !> Including organic compounds. Atmospheric Chemistry and Physics 2005;5:1223-1242. 6007 !> Wagman et al. (1982). The NBS tables of chemical thermodynamic properties: selected values for 6008 !> inorganic and Câ and Câ organic substances in SI units (book) 6009 !> Zaveri et al. (2005). A new method for multicomponent activity coefficients of electrolytes in 6010 !> aqueous atmospheric aerosols, JGR, 110, D02201, 2005. 6011 ! 6012 !> Queries concerning the use of this code through Gordon McFiggans, 5977 6013 !> g.mcfiggans@manchester.ac.uk, 5978 !> Ownership: D. Topping, Centre for Atmospheric Sciences, University of 6014 !> Ownership: D. Topping, Centre for Atmospheric Sciences, University of 5979 6015 !> Manchester, 2007 5980 6016 ! 5981 6017 !> Rewritten to PALM by Mona Kurppa, UHel, 2017 5982 6018 !------------------------------------------------------------------------------! 5983 SUBROUTINE inorganic_pdfite( RH, temp, ions, water_total, Press_HNO3,&5984 Press_HCL, Press_NH3,gamma_out, mols_out )5985 6019 SUBROUTINE inorganic_pdfite( rh, temp, ions, water_total, press_hno3, press_hcl, press_nh3, & 6020 gamma_out, mols_out ) 6021 5986 6022 IMPLICIT NONE 5987 5988 REAL(wp), DIMENSION(:) :: gamma_out !< Activity coefficient for calculating 5989 !< the non-ideal dissociation constants 5990 !< 1: HNO3, 2: HCL, 3: NH4+/H+ (NH3) 5991 !< 4: HHSO4**2/H2SO4, 5992 !< 5: H2SO4**3/HHSO4**2 5993 !< 6: NH4HSO2, 7: HHSO4 5994 REAL(wp), DIMENSION(:) :: ions !< ion molarities (mol/m3) 5995 !< 1: H+, 2: NH4+, 3: Na+, 4: SO4(2-), 5996 !< 5: HSO4-, 6: NO3-, 7: Cl- 5997 REAL(wp), DIMENSION(7) :: ions_mol !< ion molalities (mol/kg) 5998 !< 1: H+, 2: NH4+, 3: Na+, 4: SO4(2-), 5999 !< 5: HSO4-, 6: NO3-, 7: Cl- 6000 REAL(wp), DIMENSION(:) :: mols_out !< ion molality output (mol/kg) 6001 !< 1: H+, 2: NH4+, 3: Na+, 4: SO4(2-), 6002 !< 5: HSO4-, 6: NO3-, 7: Cl- 6023 6024 INTEGER(iwp) :: binary_case 6025 INTEGER(iwp) :: full_complexity 6026 6027 REAL(wp) :: a !< auxiliary variable 6003 6028 REAL(wp) :: act_product !< ionic activity coef. product: 6004 !< = (gamma_h2so4**3d0) / 6005 !< (gamma_hhso4**2d0) 6006 REAL(wp) :: ammonium_chloride !< 6007 REAL(wp) :: ammonium_chloride_eq_frac !< 6008 REAL(wp) :: ammonium_nitrate !< 6009 REAL(wp) :: ammonium_nitrate_eq_frac !< 6010 REAL(wp) :: ammonium_sulphate !< 6029 !< = (gamma_h2so4**3d0) / gamma_hhso4**2d0) 6030 REAL(wp) :: ammonium_chloride !< 6031 REAL(wp) :: ammonium_chloride_eq_frac !< 6032 REAL(wp) :: ammonium_nitrate !< 6033 REAL(wp) :: ammonium_nitrate_eq_frac !< 6034 REAL(wp) :: ammonium_sulphate !< 6011 6035 REAL(wp) :: ammonium_sulphate_eq_frac !< 6012 REAL(wp) :: binary_h2so4 !< binary H2SO4 activity coeff. 6036 REAL(wp) :: b !< auxiliary variable 6037 REAL(wp) :: binary_h2so4 !< binary H2SO4 activity coeff. 6013 6038 REAL(wp) :: binary_hcl !< binary HCL activity coeff. 6014 REAL(wp) :: binary_hhso4 !< binary HHSO4 activity coeff. 6039 REAL(wp) :: binary_hhso4 !< binary HHSO4 activity coeff. 6015 6040 REAL(wp) :: binary_hno3 !< binary HNO3 activity coeff. 6016 REAL(wp) :: binary_nh4hso4 !< binary NH4HSO4 activity coeff. 6041 REAL(wp) :: binary_nh4hso4 !< binary NH4HSO4 activity coeff. 6042 REAL(wp) :: c !< auxiliary variable 6017 6043 REAL(wp) :: charge_sum !< sum of ionic charges 6018 REAL(wp) :: gamma_h2so4 !< activity coefficient 6044 REAL(wp) :: gamma_h2so4 !< activity coefficient 6019 6045 REAL(wp) :: gamma_hcl !< activity coefficient 6020 REAL(wp) :: gamma_hhso4 !< activity coeffient 6046 REAL(wp) :: gamma_hhso4 !< activity coeffient 6021 6047 REAL(wp) :: gamma_hno3 !< activity coefficient 6022 6048 REAL(wp) :: gamma_nh3 !< activity coefficient … … 6024 6050 REAL(wp) :: h_out !< 6025 6051 REAL(wp) :: h_real !< new hydrogen ion conc. 6026 REAL(wp) :: H2SO4_hcl !< contribution of H2SO4 6027 REAL(wp) :: H2SO4_hno3 !< contribution of H2SO4 6028 REAL(wp) :: H2SO4_nh3 !< contribution of H2SO4 6029 REAL(wp) :: H2SO4_nh4hso4 !< contribution of H2SO4 6030 REAL(wp) :: HCL_h2so4 !< contribution of HCL 6031 REAL(wp) :: HCL_hhso4 !< contribution of HCL 6032 REAL(wp) :: HCL_hno3 !< contribution of HCL 6033 REAL(wp) :: HCL_nh3 !< contribution of HCL 6034 REAL(wp) :: HCL_nh4hso4 !< contribution of HCL 6035 REAL(wp) :: henrys_temp_dep !< temperature dependence of 6036 !< Henry's Law 6037 REAL(wp) :: HNO3_h2so4 !< contribution of HNO3 6038 REAL(wp) :: HNO3_hcl !< contribution of HNO3 6039 REAL(wp) :: HNO3_hhso4 !< contribution of HNO3 6040 REAL(wp) :: HNO3_nh3 !< contribution of HNO3 6041 REAL(wp) :: HNO3_nh4hso4 !< contribution of HNO3 6042 REAL(wp) :: hso4_out !< 6052 REAL(wp) :: h2so4_hcl !< contribution of H2SO4 6053 REAL(wp) :: h2so4_hno3 !< contribution of H2SO4 6054 REAL(wp) :: h2so4_nh3 !< contribution of H2SO4 6055 REAL(wp) :: h2so4_nh4hso4 !< contribution of H2SO4 6056 REAL(wp) :: hcl_h2so4 !< contribution of HCL 6057 REAL(wp) :: hcl_hhso4 !< contribution of HCL 6058 REAL(wp) :: hcl_hno3 !< contribution of HCL 6059 REAL(wp) :: hcl_nh4hso4 !< contribution of HCL 6060 REAL(wp) :: henrys_temp_dep !< temperature dependence of Henry's Law 6061 REAL(wp) :: hno3_h2so4 !< contribution of HNO3 6062 REAL(wp) :: hno3_hcl !< contribution of HNO3 6063 REAL(wp) :: hno3_hhso4 !< contribution of HNO3 6064 REAL(wp) :: hno3_nh3 !< contribution of HNO3 6065 REAL(wp) :: hno3_nh4hso4 !< contribution of HNO3 6066 REAL(wp) :: hso4_out !< 6043 6067 REAL(wp) :: hso4_real !< new bisulphate ion conc. 6044 6068 REAL(wp) :: hydrochloric_acid !< 6045 6069 REAL(wp) :: hydrochloric_acid_eq_frac !< 6046 REAL(wp) :: Kh !< equilibrium constant for H+ 6047 REAL(wp) :: K_hcl !< equilibrium constant of HCL 6048 REAL(wp) :: K_hno3 !< equilibrium constant of HNO3 6049 REAL(wp) :: Knh4 !< equilibrium constant for NH4+ 6050 REAL(wp) :: Kw !< equil. const. for water_surface 6051 REAL(wp) :: Ln_h2so4_act !< gamma_h2so4 = EXP(Ln_h2so4_act) 6052 REAL(wp) :: Ln_HCL_act !< gamma_hcl = EXP( Ln_HCL_act ) 6053 REAL(wp) :: Ln_hhso4_act !< gamma_hhso4 = EXP(Ln_hhso4_act) 6054 REAL(wp) :: Ln_HNO3_act !< gamma_hno3 = EXP( Ln_HNO3_act ) 6055 REAL(wp) :: Ln_NH4HSO4_act !< gamma_nh4hso4 = 6056 !< EXP( Ln_NH4HSO4_act ) 6057 REAL(wp) :: molality_ratio_nh3 !< molality ratio of NH3 6058 !< (NH4+ and H+) 6059 REAL(wp) :: Na2SO4_h2so4 !< contribution of Na2SO4 6060 REAL(wp) :: Na2SO4_hcl !< contribution of Na2SO4 6061 REAL(wp) :: Na2SO4_hhso4 !< contribution of Na2SO4 6062 REAL(wp) :: Na2SO4_hno3 !< contribution of Na2SO4 6063 REAL(wp) :: Na2SO4_nh3 !< contribution of Na2SO4 6064 REAL(wp) :: Na2SO4_nh4hso4 !< contribution of Na2SO4 6065 REAL(wp) :: NaCl_h2so4 !< contribution of NaCl 6066 REAL(wp) :: NaCl_hcl !< contribution of NaCl 6067 REAL(wp) :: NaCl_hhso4 !< contribution of NaCl 6068 REAL(wp) :: NaCl_hno3 !< contribution of NaCl 6069 REAL(wp) :: NaCl_nh3 !< contribution of NaCl 6070 REAL(wp) :: NaCl_nh4hso4 !< contribution of NaCl 6071 REAL(wp) :: NaNO3_h2so4 !< contribution of NaNO3 6072 REAL(wp) :: NaNO3_hcl !< contribution of NaNO3 6073 REAL(wp) :: NaNO3_hhso4 !< contribution of NaNO3 6074 REAL(wp) :: NaNO3_hno3 !< contribution of NaNO3 6075 REAL(wp) :: NaNO3_nh3 !< contribution of NaNO3 6076 REAL(wp) :: NaNO3_nh4hso4 !< contribution of NaNO3 6077 REAL(wp) :: NH42SO4_h2so4 !< contribution of NH42SO4 6078 REAL(wp) :: NH42SO4_hcl !< contribution of NH42SO4 6079 REAL(wp) :: NH42SO4_hhso4 !< contribution of NH42SO4 6080 REAL(wp) :: NH42SO4_hno3 !< contribution of NH42SO4 6081 REAL(wp) :: NH42SO4_nh3 !< contribution of NH42SO4 6082 REAL(wp) :: NH42SO4_nh4hso4 !< contribution of NH42SO4 6083 REAL(wp) :: NH4Cl_h2so4 !< contribution of NH4Cl 6084 REAL(wp) :: NH4Cl_hcl !< contribution of NH4Cl 6085 REAL(wp) :: NH4Cl_hhso4 !< contribution of NH4Cl 6086 REAL(wp) :: NH4Cl_hno3 !< contribution of NH4Cl 6087 REAL(wp) :: NH4Cl_nh3 !< contribution of NH4Cl 6088 REAL(wp) :: NH4Cl_nh4hso4 !< contribution of NH4Cl 6089 REAL(wp) :: NH4NO3_h2so4 !< contribution of NH4NO3 6090 REAL(wp) :: NH4NO3_hcl !< contribution of NH4NO3 6091 REAL(wp) :: NH4NO3_hhso4 !< contribution of NH4NO3 6092 REAL(wp) :: NH4NO3_hno3 !< contribution of NH4NO3 6093 REAL(wp) :: NH4NO3_nh3 !< contribution of NH4NO3 6094 REAL(wp) :: NH4NO3_nh4hso4 !< contribution of NH4NO3 6070 REAL(wp) :: k_h !< equilibrium constant for H+ 6071 REAL(wp) :: k_hcl !< equilibrium constant of HCL 6072 REAL(wp) :: k_hno3 !< equilibrium constant of HNO3 6073 REAL(wp) :: k_nh4 !< equilibrium constant for NH4+ 6074 REAL(wp) :: k_h2o !< equil. const. for water_surface 6075 REAL(wp) :: ln_h2so4_act !< gamma_h2so4 = EXP(ln_h2so4_act) 6076 REAL(wp) :: ln_HCL_act !< gamma_hcl = EXP( ln_HCL_act ) 6077 REAL(wp) :: ln_hhso4_act !< gamma_hhso4 = EXP(ln_hhso4_act) 6078 REAL(wp) :: ln_hno3_act !< gamma_hno3 = EXP( ln_hno3_act ) 6079 REAL(wp) :: ln_nh4hso4_act !< gamma_nh4hso4 = EXP( ln_nh4hso4_act ) 6080 REAL(wp) :: molality_ratio_nh3 !< molality ratio of NH3 (NH4+ and H+) 6081 REAL(wp) :: na2so4_h2so4 !< contribution of Na2SO4 6082 REAL(wp) :: na2so4_hcl !< contribution of Na2SO4 6083 REAL(wp) :: na2so4_hhso4 !< contribution of Na2SO4 6084 REAL(wp) :: na2so4_hno3 !< contribution of Na2SO4 6085 REAL(wp) :: na2so4_nh3 !< contribution of Na2SO4 6086 REAL(wp) :: na2so4_nh4hso4 !< contribution of Na2SO4 6087 REAL(wp) :: nacl_h2so4 !< contribution of NaCl 6088 REAL(wp) :: nacl_hcl !< contribution of NaCl 6089 REAL(wp) :: nacl_hhso4 !< contribution of NaCl 6090 REAL(wp) :: nacl_hno3 !< contribution of NaCl 6091 REAL(wp) :: nacl_nh3 !< contribution of NaCl 6092 REAL(wp) :: nacl_nh4hso4 !< contribution of NaCl 6093 REAL(wp) :: nano3_h2so4 !< contribution of NaNO3 6094 REAL(wp) :: nano3_hcl !< contribution of NaNO3 6095 REAL(wp) :: nano3_hhso4 !< contribution of NaNO3 6096 REAL(wp) :: nano3_hno3 !< contribution of NaNO3 6097 REAL(wp) :: nano3_nh3 !< contribution of NaNO3 6098 REAL(wp) :: nano3_nh4hso4 !< contribution of NaNO3 6099 REAL(wp) :: nh42so4_h2so4 !< contribution of NH42SO4 6100 REAL(wp) :: nh42so4_hcl !< contribution of NH42SO4 6101 REAL(wp) :: nh42so4_hhso4 !< contribution of NH42SO4 6102 REAL(wp) :: nh42so4_hno3 !< contribution of NH42SO4 6103 REAL(wp) :: nh42so4_nh3 !< contribution of NH42SO4 6104 REAL(wp) :: nh42so4_nh4hso4 !< contribution of NH42SO4 6105 REAL(wp) :: nh4cl_h2so4 !< contribution of NH4Cl 6106 REAL(wp) :: nh4cl_hcl !< contribution of NH4Cl 6107 REAL(wp) :: nh4cl_hhso4 !< contribution of NH4Cl 6108 REAL(wp) :: nh4cl_hno3 !< contribution of NH4Cl 6109 REAL(wp) :: nh4cl_nh3 !< contribution of NH4Cl 6110 REAL(wp) :: nh4cl_nh4hso4 !< contribution of NH4Cl 6111 REAL(wp) :: nh4no3_h2so4 !< contribution of NH4NO3 6112 REAL(wp) :: nh4no3_hcl !< contribution of NH4NO3 6113 REAL(wp) :: nh4no3_hhso4 !< contribution of NH4NO3 6114 REAL(wp) :: nh4no3_hno3 !< contribution of NH4NO3 6115 REAL(wp) :: nh4no3_nh3 !< contribution of NH4NO3 6116 REAL(wp) :: nh4no3_nh4hso4 !< contribution of NH4NO3 6095 6117 REAL(wp) :: nitric_acid !< 6096 6118 REAL(wp) :: nitric_acid_eq_frac !< Equivalent fractions 6097 REAL(wp) :: Press_HCL !< partial pressure of HCL 6098 REAL(wp) :: Press_HNO3 !< partial pressure of HNO3 6099 REAL(wp) :: Press_NH3 !< partial pressure of NH3 6100 REAL(wp) :: RH !< relative humidity [0-1] 6119 REAL(wp) :: press_hcl !< partial pressure of HCL 6120 REAL(wp) :: press_hno3 !< partial pressure of HNO3 6121 REAL(wp) :: press_nh3 !< partial pressure of NH3 6122 REAL(wp) :: rh !< relative humidity [0-1] 6123 REAL(wp) :: root1 !< auxiliary variable 6124 REAL(wp) :: root2 !< auxiliary variable 6125 REAL(wp) :: so4_out !< 6126 REAL(wp) :: so4_real !< new sulpate ion concentration 6127 REAL(wp) :: sodium_chloride !< 6128 REAL(wp) :: sodium_chloride_eq_frac !< 6129 REAL(wp) :: sodium_nitrate !< 6130 REAL(wp) :: sodium_nitrate_eq_frac !< 6131 REAL(wp) :: sodium_sulphate !< 6132 REAL(wp) :: sodium_sulphate_eq_frac !< 6133 REAL(wp) :: solutes !< 6134 REAL(wp) :: sulphuric_acid !< 6135 REAL(wp) :: sulphuric_acid_eq_frac !< 6101 6136 REAL(wp) :: temp !< temperature 6102 REAL(wp) :: so4_out !<6103 REAL(wp) :: so4_real !< new sulpate ion concentration6104 REAL(wp) :: sodium_chloride !<6105 REAL(wp) :: sodium_chloride_eq_frac !<6106 REAL(wp) :: sodium_nitrate !<6107 REAL(wp) :: sodium_nitrate_eq_frac !<6108 REAL(wp) :: sodium_sulphate !<6109 REAL(wp) :: sodium_sulphate_eq_frac !<6110 REAL(wp) :: solutes !<6111 REAL(wp) :: sulphuric_acid !<6112 REAL(wp) :: sulphuric_acid_eq_frac !<6113 6137 REAL(wp) :: water_total !< 6114 6115 REAL(wp) :: a !< auxiliary variable 6116 REAL(wp) :: b !< auxiliary variable 6117 REAL(wp) :: c !< auxiliary variable 6118 REAL(wp) :: root1 !< auxiliary variable 6119 REAL(wp) :: root2 !< auxiliary variable 6120 6121 INTEGER(iwp) :: binary_case 6122 INTEGER(iwp) :: full_complexity 6123 ! 6138 6139 REAL(wp), DIMENSION(:) :: gamma_out !< Activity coefficient for calculating the non-ideal 6140 !< dissociation constants 6141 !< 1: HNO3, 2: HCL, 3: NH4+/H+ (NH3), 4: HHSO4**2/H2SO4, 6142 !< 5: H2SO4**3/HHSO4**2, 6: NH4HSO2, 7: HHSO4 6143 REAL(wp), DIMENSION(:) :: ions !< ion molarities (mol/m3): 1: H+, 2: NH4+, 3: Na+, 6144 !< 4: SO4(2-), 5: HSO4-, 6: NO3-, 7: Cl- 6145 REAL(wp), DIMENSION(7) :: ions_mol !< ion molalities (mol/kg): 1: H+, 2: NH4+, 3: Na+, 6146 !< 4: SO4(2-), 5: HSO4-, 6: NO3-, 7: Cl- 6147 REAL(wp), DIMENSION(:) :: mols_out !< ion molality output (mol/kg): 1: H+, 2: NH4+, 3: Na+, 6148 !< 4: SO4(2-), 5: HSO4-, 6: NO3-, 7: Cl- 6149 ! 6124 6150 !-- Value initialisation 6125 binary_h2so4 = 0.0_wp 6126 binary_hcl = 0.0_wp 6127 binary_hhso4 = 0.0_wp 6128 binary_hno3 = 0.0_wp 6129 binary_nh4hso4 = 0.0_wp 6130 henrys_temp_dep = ( 1.0_wp / temp - 1.0_wp / 298.0_wp )6131 HCL_hno3 = 1.0_wp6132 H2SO4_hno3 = 1.0_wp6133 NH42SO4_hno3 = 1.0_wp6134 NH4NO3_hno3 = 1.0_wp6135 NH4Cl_hno3 = 1.0_wp6136 Na2SO4_hno3 = 1.0_wp6137 NaNO3_hno3 = 1.0_wp6138 NaCl_hno3 = 1.0_wp6139 HNO3_hcl = 1.0_wp6140 H2SO4_hcl = 1.0_wp6141 NH42SO4_hcl = 1.0_wp6142 NH4NO3_hcl = 1.0_wp6143 NH4Cl_hcl = 1.0_wp6144 Na2SO4_hcl = 1.0_wp6145 NaNO3_hcl = 1.0_wp6146 NaCl_hcl = 1.0_wp6147 HNO3_nh3 = 1.0_wp6148 HCL_nh3= 1.0_wp6149 H2SO4_nh3 = 1.0_wp6150 NH42SO4_nh3 = 1.0_wp6151 NH4NO3_nh3= 1.0_wp6152 NH4Cl_nh3= 1.0_wp6153 Na2SO4_nh3= 1.0_wp6154 NaNO3_nh3= 1.0_wp6155 NaCl_nh3= 1.0_wp6156 HNO3_hhso4 = 1.0_wp6157 HCL_hhso4= 1.0_wp6158 NH42SO4_hhso4= 1.0_wp6159 NH4NO3_hhso4= 1.0_wp6160 NH4Cl_hhso4= 1.0_wp6161 Na2SO4_hhso4= 1.0_wp6162 NaNO3_hhso4= 1.0_wp6163 NaCl_hhso4 = 1.0_wp6164 HNO3_h2so4= 1.0_wp6165 HCL_h2so4= 1.0_wp6166 NH42SO4_h2so4 = 1.0_wp6167 NH4NO3_h2so4= 1.0_wp6168 NH4Cl_h2so4= 1.0_wp6169 Na2SO4_h2so4= 1.0_wp6170 NaNO3_h2so4= 1.0_wp6171 NaCl_h2so4 = 1.0_wp 6151 binary_h2so4 = 0.0_wp 6152 binary_hcl = 0.0_wp 6153 binary_hhso4 = 0.0_wp 6154 binary_hno3 = 0.0_wp 6155 binary_nh4hso4 = 0.0_wp 6156 henrys_temp_dep = ( 1.0_wp / temp - 0.0033557_wp ) ! 1/T - 1/298 K 6157 hcl_hno3 = 1.0_wp 6158 h2so4_hno3 = 1.0_wp 6159 nh42so4_hno3 = 1.0_wp 6160 nh4no3_hno3 = 1.0_wp 6161 nh4cl_hno3 = 1.0_wp 6162 na2so4_hno3 = 1.0_wp 6163 nano3_hno3 = 1.0_wp 6164 nacl_hno3 = 1.0_wp 6165 hno3_hcl = 1.0_wp 6166 h2so4_hcl = 1.0_wp 6167 nh42so4_hcl = 1.0_wp 6168 nh4no3_hcl = 1.0_wp 6169 nh4cl_hcl = 1.0_wp 6170 na2so4_hcl = 1.0_wp 6171 nano3_hcl = 1.0_wp 6172 nacl_hcl = 1.0_wp 6173 hno3_nh3 = 1.0_wp 6174 h2so4_nh3 = 1.0_wp 6175 nh42so4_nh3 = 1.0_wp 6176 nh4no3_nh3 = 1.0_wp 6177 nh4cl_nh3 = 1.0_wp 6178 na2so4_nh3 = 1.0_wp 6179 nano3_nh3 = 1.0_wp 6180 nacl_nh3 = 1.0_wp 6181 hno3_hhso4 = 1.0_wp 6182 hcl_hhso4 = 1.0_wp 6183 nh42so4_hhso4 = 1.0_wp 6184 nh4no3_hhso4 = 1.0_wp 6185 nh4cl_hhso4 = 1.0_wp 6186 na2so4_hhso4 = 1.0_wp 6187 nano3_hhso4 = 1.0_wp 6188 nacl_hhso4 = 1.0_wp 6189 hno3_h2so4 = 1.0_wp 6190 hcl_h2so4 = 1.0_wp 6191 nh42so4_h2so4 = 1.0_wp 6192 nh4no3_h2so4 = 1.0_wp 6193 nh4cl_h2so4 = 1.0_wp 6194 na2so4_h2so4 = 1.0_wp 6195 nano3_h2so4 = 1.0_wp 6196 nacl_h2so4 = 1.0_wp 6197 ! 6172 6198 !-- New NH3 variables 6173 HNO3_nh4hso4 = 1.0_wp6174 HCL_nh4hso4 = 1.0_wp6175 H2SO4_nh4hso4 = 1.0_wp6176 NH42SO4_nh4hso4 = 1.0_wp6177 NH4NO3_nh4hso4 = 1.0_wp6178 NH4Cl_nh4hso4 = 1.0_wp6179 Na2SO4_nh4hso4 = 1.0_wp6180 NaNO3_nh4hso4 = 1.0_wp6181 NaCl_nh4hso4 = 1.0_wp6199 hno3_nh4hso4 = 1.0_wp 6200 hcl_nh4hso4 = 1.0_wp 6201 h2so4_nh4hso4 = 1.0_wp 6202 nh42so4_nh4hso4 = 1.0_wp 6203 nh4no3_nh4hso4 = 1.0_wp 6204 nh4cl_nh4hso4 = 1.0_wp 6205 na2so4_nh4hso4 = 1.0_wp 6206 nano3_nh4hso4 = 1.0_wp 6207 nacl_nh4hso4 = 1.0_wp 6182 6208 ! 6183 6209 !-- Juha Tonttila added 6184 6210 mols_out = 0.0_wp 6185 Press_HNO3 = 0.0_wp 6186 Press_HCL = 0.0_wp 6187 Press_NH3 = 0.0_wp !< Initialising vapour pressure over the 6188 !< multicomponent particle 6189 gamma_out = 1.0_wp !< i.e. don't alter the ideal mixing ratios if 6190 !< there's nothing there. 6191 ! 6211 press_hno3 = 0.0_wp !< Initialising vapour pressures over the 6212 press_hcl = 0.0_wp !< multicomponent particle 6213 press_nh3 = 0.0_wp 6214 gamma_out = 1.0_wp !< i.e. don't alter the ideal mixing ratios if there's nothing there. 6215 ! 6192 6216 !-- 1) - COMPOSITION DEFINITIONS 6193 6217 ! 6194 6218 !-- a) Inorganic ion pairing: 6195 !-- In order to calculate the water content, which is also used in 6196 !-- calculating vapour pressures, one needs to pair the anions and cations 6197 !-- for use in the ZSR mixing rule. The equation provided by Clegg et al. 6198 !-- (2001) is used for ion pairing. The solutes chosen comprise of 9 6199 !-- inorganic salts and acids which provide a pairing between each anion and 6200 !-- cation: (NH4)2SO4, NH4NO3, NH4Cl, Na2SO4, NaNO3, NaCl, H2SO4, HNO3, HCL. 6201 !-- The organic compound is treated as a seperate solute. 6219 !-- In order to calculate the water content, which is also used in calculating vapour pressures, one 6220 !-- needs to pair the anions and cations for use in the ZSR mixing rule. The equation provided by 6221 !-- Clegg et al. (2001) is used for ion pairing. The solutes chosen comprise of 9 inorganic salts 6222 !-- and acids which provide a pairing between each anion and cation: (NH4)2SO4, NH4NO3, NH4Cl, 6223 !-- Na2SO4, NaNO3, NaCl, H2SO4, HNO3, HCL. The organic compound is treated as a seperate solute. 6202 6224 !-- Ions: 1: H+, 2: NH4+, 3: Na+, 4: SO4(2-), 5: HSO4-, 6: NO3-, 7: Cl- 6203 6225 ! 6204 charge_sum = ions(1) + ions(2) + ions(3) + 2.0_wp * ions(4) + ions(5) + & 6205 ions(6) + ions(7) 6206 nitric_acid = 0.0_wp ! HNO3 6207 nitric_acid = ( 2.0_wp * ions(1) * ions(6) * & 6208 ( ( 1.0_wp / 1.0_wp ) ** 0.5_wp ) ) / ( charge_sum ) 6209 hydrochloric_acid = 0.0_wp ! HCL 6210 hydrochloric_acid = ( 2.0_wp * ions(1) * ions(7) * & 6211 ( ( 1.0_wp / 1.0_wp ) ** 0.5_wp ) ) / ( charge_sum ) 6212 sulphuric_acid = 0.0_wp ! H2SO4 6213 sulphuric_acid = ( 2.0_wp * ions(1) * ions(4) * & 6214 ( ( 2.0_wp / 2.0_wp ) ** 0.5_wp ) ) / ( charge_sum ) 6215 ammonium_sulphate = 0.0_wp ! (NH4)2SO4 6216 ammonium_sulphate = ( 2.0_wp * ions(2) * ions(4) * & 6217 ( ( 2.0_wp / 2.0_wp ) ** 0.5_wp ) ) / ( charge_sum ) 6218 ammonium_nitrate = 0.0_wp ! NH4NO3 6219 ammonium_nitrate = ( 2.0_wp * ions(2) * ions(6) * & 6220 ( ( 1.0_wp / 1.0_wp ) ** 0.5_wp ) ) / ( charge_sum ) 6221 ammonium_chloride = 0.0_wp ! NH4Cl 6222 ammonium_chloride = ( 2.0_wp * ions(2) * ions(7) * & 6223 ( ( 1.0_wp / 1.0_wp ) ** 0.5_wp ) ) / ( charge_sum ) 6224 sodium_sulphate = 0.0_wp ! Na2SO4 6225 sodium_sulphate = ( 2.0_wp * ions(3) * ions(4) * & 6226 ( ( 2.0_wp / 2.0_wp ) ** 0.5_wp ) ) / ( charge_sum ) 6227 sodium_nitrate = 0.0_wp ! NaNO3 6228 sodium_nitrate = ( 2.0_wp * ions(3) *ions(6) * & 6229 ( ( 1.0_wp / 1.0_wp ) ** 0.5_wp ) ) / ( charge_sum ) 6230 sodium_chloride = 0.0_wp ! NaCl 6231 sodium_chloride = ( 2.0_wp * ions(3) * ions(7) * & 6232 ( ( 1.0_wp / 1.0_wp ) ** 0.5_wp ) ) / ( charge_sum ) 6226 charge_sum = ions(1) + ions(2) + ions(3) + 2.0_wp * ions(4) + ions(5) + ions(6) + ions(7) 6227 nitric_acid = ( 2.0_wp * ions(1) * ions(6) ) / charge_sum 6228 hydrochloric_acid = ( 2.0_wp * ions(1) * ions(7) ) / charge_sum 6229 sulphuric_acid = ( 2.0_wp * ions(1) * ions(4) ) / charge_sum 6230 ammonium_sulphate = ( 2.0_wp * ions(2) * ions(4) ) / charge_sum 6231 ammonium_nitrate = ( 2.0_wp * ions(2) * ions(6) ) / charge_sum 6232 ammonium_chloride = ( 2.0_wp * ions(2) * ions(7) ) / charge_sum 6233 sodium_sulphate = ( 2.0_wp * ions(3) * ions(4) ) / charge_sum 6234 sodium_nitrate = ( 2.0_wp * ions(3) * ions(6) ) / charge_sum 6235 sodium_chloride = ( 2.0_wp * ions(3) * ions(7) ) / charge_sum 6233 6236 solutes = 0.0_wp 6234 solutes = 3.0_wp * sulphuric_acid + 2.0_wp * hydrochloric_acid + & 6235 2.0_wp * nitric_acid + 3.0_wp * ammonium_sulphate + & 6236 2.0_wp * ammonium_nitrate + 2.0_wp * ammonium_chloride + & 6237 3.0_wp * sodium_sulphate + 2.0_wp * sodium_nitrate + & 6238 2.0_wp * sodium_chloride 6239 6240 ! 6237 solutes = 3.0_wp * sulphuric_acid + 2.0_wp * hydrochloric_acid + 2.0_wp * nitric_acid + & 6238 3.0_wp * ammonium_sulphate + 2.0_wp * ammonium_nitrate + 2.0_wp * ammonium_chloride +& 6239 3.0_wp * sodium_sulphate + 2.0_wp * sodium_nitrate + 2.0_wp * sodium_chloride 6240 ! 6241 6241 !-- b) Inorganic equivalent fractions: 6242 !-- These values are calculated so that activity coefficients can be 6243 !-- expressed by a linear additive rule, thus allowing more efficient6244 !-- calculations and future expansion (see more detailed description below)6245 nitric_acid_eq_frac = 2.0_wp * nitric_acid / ( solutes )6246 hydrochloric_acid_eq_frac = 2.0_wp * hydrochloric_acid / ( solutes )6247 sulphuric_acid_eq_frac = 3.0_wp * sulphuric_acid / ( solutes )6248 ammonium_sulphate_eq_frac = 3.0_wp * ammonium_sulphate / ( solutes )6249 ammonium_nitrate_eq_frac = 2.0_wp * ammonium_nitrate / ( solutes )6250 ammonium_chloride_eq_frac = 2.0_wp * ammonium_chloride / ( solutes )6251 sodium_sulphate_eq_frac = 3.0_wp * sodium_sulphate / ( solutes )6252 sodium_nitrate_eq_frac = 2.0_wp * sodium_nitrate / ( solutes )6253 sodium_chloride_eq_frac = 2.0_wp * sodium_chloride / ( solutes )6242 !-- These values are calculated so that activity coefficients can be expressed by a linear additive 6243 !-- rule, thus allowing more efficient calculations and future expansion (see more detailed 6244 !-- description below) 6245 nitric_acid_eq_frac = 2.0_wp * nitric_acid / solutes 6246 hydrochloric_acid_eq_frac = 2.0_wp * hydrochloric_acid / solutes 6247 sulphuric_acid_eq_frac = 3.0_wp * sulphuric_acid / solutes 6248 ammonium_sulphate_eq_frac = 3.0_wp * ammonium_sulphate / solutes 6249 ammonium_nitrate_eq_frac = 2.0_wp * ammonium_nitrate / solutes 6250 ammonium_chloride_eq_frac = 2.0_wp * ammonium_chloride / solutes 6251 sodium_sulphate_eq_frac = 3.0_wp * sodium_sulphate / solutes 6252 sodium_nitrate_eq_frac = 2.0_wp * sodium_nitrate / solutes 6253 sodium_chloride_eq_frac = 2.0_wp * sodium_chloride / solutes 6254 6254 ! 6255 6255 !-- Inorganic ion molalities 6256 ions_mol(:) = 0.0_wp6257 6256 ions_mol(1) = ions(1) / ( water_total * 18.01528E-3_wp ) ! H+ 6258 6257 ions_mol(2) = ions(2) / ( water_total * 18.01528E-3_wp ) ! NH4+ … … 6263 6262 ions_mol(7) = ions(7) / ( water_total * 18.01528E-3_wp ) ! Cl- 6264 6263 6265 !-- 6266 !-- At this point we may need to introduce a method for prescribing H+ when 6267 !-- there is no 'real' value for H+..i.e. in the sulphate poor domain6268 !-- This will give a value for solve quadratic proposed byZaveri et al. 20056264 !-- *** 6265 !-- At this point we may need to introduce a method for prescribing H+ when there is no 'real' value 6266 !-- for H+..i.e. in the sulphate poor domain. This will give a value for solve quadratic proposed by 6267 !-- Zaveri et al. 2005 6269 6268 ! 6270 6269 !-- 2) - WATER CALCULATION 6271 6270 ! 6272 !-- a) The water content is calculated using the ZSR rule with solute 6273 !-- concentrations calculated using 1a above. Whilst the usual approximation of 6274 !-- ZSR relies on binary data consisting of 5th or higher order polynomials, in 6275 !-- this code 4 different RH regimes are used, each housing cubic equations for 6276 !-- the water associated with each solute listed above. Binary water contents 6277 !-- for inorganic components were calculated using AIM online (Clegg et al 6278 !-- 1998). The water associated with the organic compound is calculated assuming 6279 !-- ideality and that aw = RH. 6280 ! 6281 !-- b) Molality of each inorganic ion and organic solute (initial input) is 6282 !-- calculated for use in vapour pressure calculation. 6271 !-- a) The water content is calculated using the ZSR rule with solute concentrations calculated 6272 !-- using 1a above. Whilst the usual approximation of ZSR relies on binary data consisting of 5th or 6273 !-- higher order polynomials, in this code 4 different RH regimes are used, each housing cubic 6274 !-- equations for the water associated with each solute listed above. Binary water contents for 6275 !-- inorganic components were calculated using AIM online (Clegg et al 1998). The water associated 6276 !-- with the organic compound is calculated assuming ideality and that aw = RH. 6277 ! 6278 !-- b) Molality of each inorganic ion and organic solute (initial input) is calculated for use in 6279 !-- vapour pressure calculation. 6283 6280 ! 6284 6281 !-- 3) - BISULPHATE ION DISSOCIATION CALCULATION 6285 6282 ! 6286 !-- The dissociation of the bisulphate ion is calculated explicitly. A solution 6287 !-- to the equilibrium equation between the bisulphate ion, hydrogen ion and 6288 !-- sulphate ion is found using tabulated equilibrium constants (referenced). It 6289 !-- is necessary to calculate the activity coefficients of HHSO4 and H2SO4 in a 6290 !-- non-iterative manner. These are calculated using the same format as 6291 !-- described in 4) below, where both activity coefficients were fit to the 6292 !-- output from ADDEM (Topping et al 2005a,b) covering an extensive composition 6293 !-- space, providing the activity coefficients and bisulphate ion dissociation 6294 !-- as a function of equivalent mole fractions and relative humidity. 6295 ! 6296 !-- NOTE: the flags "binary_case" and "full_complexity" are not used in this 6297 !-- prototype. They are used for simplification of the fit expressions when 6298 !-- using limited composition regions. This section of code calculates the 6299 !-- bisulphate ion concentration 6283 !-- The dissociation of the bisulphate ion is calculated explicitly. A solution to the equilibrium 6284 !-- equation between the bisulphate ion, hydrogen ion and sulphate ion is found using tabulated 6285 !-- equilibrium constants (referenced). It is necessary to calculate the activity coefficients of 6286 !-- HHSO4 and H2SO4 in a non-iterative manner. These are calculated using the same format as 6287 !-- described in 4) below, where both activity coefficients were fit to the output from ADDEM 6288 !-- (Topping et al 2005a,b) covering an extensive composition space, providing the activity 6289 !-- coefficients and bisulphate ion dissociation as a function of equivalent mole fractions and 6290 !-- relative humidity. 6291 ! 6292 !-- NOTE: the flags "binary_case" and "full_complexity" are not used in this prototype. They are 6293 !-- used for simplification of the fit expressions when using limited composition regions. This 6294 !-- section of code calculates the bisulphate ion concentration. 6300 6295 ! 6301 6296 IF ( ions(1) > 0.0_wp .AND. ions(4) > 0.0_wp ) THEN 6302 ! 6297 ! 6303 6298 !-- HHSO4: 6304 6299 binary_case = 1 6305 IF ( RH > 0.1_wp .AND. RH < 0.9_wp ) THEN 6306 binary_hhso4 = - 4.9521_wp * ( RH**3 ) + 9.2881_wp * ( RH**2 ) - & 6307 10.777_wp * RH + 6.0534_wp 6308 ELSEIF ( RH >= 0.9_wp .AND. RH < 0.955_wp ) THEN 6309 binary_hhso4 = - 6.3777_wp * RH + 5.962_wp 6310 ELSEIF ( RH >= 0.955_wp .AND. RH < 0.99_wp ) THEN 6311 binary_hhso4 = 2367.2_wp * ( RH**3 ) - 6849.7_wp * ( RH**2 ) + & 6312 6600.9_wp * RH - 2118.7_wp 6313 ELSEIF ( RH >= 0.99_wp .AND. RH < 0.9999_wp ) THEN 6314 binary_hhso4 = 3E-7_wp * ( RH**5 ) - 2E-5_wp * ( RH**4 ) + & 6315 0.0004_wp * ( RH**3 ) - 0.0035_wp * ( RH**2 ) + & 6316 0.0123_wp * RH - 0.3025_wp 6317 ENDIF 6318 6300 IF ( rh > 0.1_wp .AND. rh < 0.9_wp ) THEN 6301 binary_hhso4 = -4.9521_wp * rh**3 + 9.2881_wp * rh**2 - 10.777_wp * rh + 6.0534_wp 6302 ELSEIF ( rh >= 0.9_wp .AND. rh < 0.955_wp ) THEN 6303 binary_hhso4 = -6.3777_wp * rh + 5.962_wp 6304 ELSEIF ( rh >= 0.955_wp .AND. rh < 0.99_wp ) THEN 6305 binary_hhso4 = 2367.2_wp * rh**3 - 6849.7_wp * rh**2 + 6600.9_wp * rh - 2118.7_wp 6306 ELSEIF ( rh >= 0.99_wp .AND. rh < 0.9999_wp ) THEN 6307 binary_hhso4 = 3E-7_wp * rh**5 - 2E-5_wp * rh**4 + 0.0004_wp * rh**3 - 0.0035_wp * rh**2 & 6308 + 0.0123_wp * rh - 0.3025_wp 6309 ENDIF 6310 6319 6311 IF ( nitric_acid > 0.0_wp ) THEN 6320 HNO3_hhso4 = - 4.2204_wp * ( RH**4 ) + 12.193_wp * ( RH**3 ) -&6321 12.481_wp * ( RH**2 ) + 6.459_wp * RH- 1.9004_wp6322 ENDIF 6323 6312 hno3_hhso4 = -4.2204_wp * rh**4 + 12.193_wp * rh**3 - 12.481_wp * rh**2 + 6.459_wp * rh & 6313 - 1.9004_wp 6314 ENDIF 6315 6324 6316 IF ( hydrochloric_acid > 0.0_wp ) THEN 6325 HCL_hhso4 = - 54.845_wp * ( RH**7 ) + 209.54_wp * ( RH**6 ) - & 6326 336.59_wp * ( RH**5 ) + 294.21_wp * ( RH**4 ) - & 6327 150.07_wp * ( RH**3 ) + 43.767_wp * ( RH**2 ) - & 6328 6.5495_wp * RH + 0.60048_wp 6329 ENDIF 6330 6317 hcl_hhso4 = -54.845_wp * rh**7 + 209.54_wp * rh**6 - 336.59_wp * rh**5 + 294.21_wp * & 6318 rh**4 - 150.07_wp * rh**3 + 43.767_wp * rh**2 - 6.5495_wp * rh + 0.60048_wp 6319 ENDIF 6320 6331 6321 IF ( ammonium_sulphate > 0.0_wp ) THEN 6332 NH42SO4_hhso4 = 16.768_wp * ( RH**3 ) - 28.75_wp * ( RH**2 ) + & 6333 20.011_wp * RH - 8.3206_wp 6334 ENDIF 6335 6322 nh42so4_hhso4 = 16.768_wp * rh**3 - 28.75_wp * rh**2 + 20.011_wp * rh - 8.3206_wp 6323 ENDIF 6324 6336 6325 IF ( ammonium_nitrate > 0.0_wp ) THEN 6337 NH4NO3_hhso4 = - 17.184_wp * ( RH**4 ) + 56.834_wp * ( RH**3 ) -&6338 65.765_wp * ( RH**2 ) + 35.321_wp * RH- 9.252_wp6339 ENDIF 6340 6326 nh4no3_hhso4 = -17.184_wp * rh**4 + 56.834_wp * rh**3 - 65.765_wp * rh**2 + & 6327 35.321_wp * rh - 9.252_wp 6328 ENDIF 6329 6341 6330 IF (ammonium_chloride > 0.0_wp ) THEN 6342 IF ( RH < 0.2_wp .AND. RH >= 0.1_wp ) THEN 6343 NH4Cl_hhso4 = 3.2809_wp * RH - 2.0637_wp 6344 ELSEIF ( RH >= 0.2_wp .AND. RH < 0.99_wp ) THEN 6345 NH4Cl_hhso4 = - 1.2981_wp * ( RH**3 ) + 4.7461_wp * ( RH**2 ) - & 6346 2.3269_wp * RH - 1.1259_wp 6331 IF ( rh < 0.2_wp .AND. rh >= 0.1_wp ) THEN 6332 nh4cl_hhso4 = 3.2809_wp * rh - 2.0637_wp 6333 ELSEIF ( rh >= 0.2_wp .AND. rh < 0.99_wp ) THEN 6334 nh4cl_hhso4 = -1.2981_wp * rh**3 + 4.7461_wp * rh**2 - 2.3269_wp * rh - 1.1259_wp 6347 6335 ENDIF 6348 6336 ENDIF 6349 6337 6350 6338 IF ( sodium_sulphate > 0.0_wp ) THEN 6351 Na2SO4_hhso4 = 118.87_wp * ( RH**6 ) - 358.63_wp * ( RH**5 ) + & 6352 435.85_wp * ( RH**4 ) - 272.88_wp * ( RH**3 ) + & 6353 94.411_wp * ( RH**2 ) - 18.21_wp * RH + 0.45935_wp 6354 ENDIF 6355 6339 na2so4_hhso4 = 118.87_wp * rh**6 - 358.63_wp * rh**5 + 435.85_wp * rh**4 - 272.88_wp * & 6340 rh**3 + 94.411_wp * rh**2 - 18.21_wp * rh + 0.45935_wp 6341 ENDIF 6342 6356 6343 IF ( sodium_nitrate > 0.0_wp ) THEN 6357 IF ( RH < 0.2_wp .AND. RH >= 0.1_wp ) THEN 6358 NaNO3_hhso4 = 4.8456_wp * RH - 2.5773_wp 6359 ELSEIF ( RH >= 0.2_wp .AND. RH < 0.99_wp ) THEN 6360 NaNO3_hhso4 = 0.5964_wp * ( RH**3 ) - 0.38967_wp * ( RH**2 ) + & 6361 1.7918_wp * RH - 1.9691_wp 6344 IF ( rh < 0.2_wp .AND. rh >= 0.1_wp ) THEN 6345 nano3_hhso4 = 4.8456_wp * rh - 2.5773_wp 6346 ELSEIF ( rh >= 0.2_wp .AND. rh < 0.99_wp ) THEN 6347 nano3_hhso4 = 0.5964_wp * rh**3 - 0.38967_wp * rh**2 + 1.7918_wp * rh - 1.9691_wp 6362 6348 ENDIF 6363 6349 ENDIF 6364 6350 6365 6351 IF ( sodium_chloride > 0.0_wp ) THEN 6366 IF ( RH< 0.2_wp ) THEN6367 NaCl_hhso4 = 0.51995_wp * RH- 1.3981_wp6368 ELSEIF ( RH >= 0.2_wp .AND. RH< 0.99_wp ) THEN6369 NaCl_hhso4 = 1.6539_wp * RH- 1.6101_wp6352 IF ( rh < 0.2_wp ) THEN 6353 nacl_hhso4 = 0.51995_wp * rh - 1.3981_wp 6354 ELSEIF ( rh >= 0.2_wp .AND. rh < 0.99_wp ) THEN 6355 nacl_hhso4 = 1.6539_wp * rh - 1.6101_wp 6370 6356 ENDIF 6371 6357 ENDIF 6372 6373 Ln_hhso4_act = binary_hhso4 + & 6374 nitric_acid_eq_frac * HNO3_hhso4 + & 6375 hydrochloric_acid_eq_frac * HCL_hhso4 + & 6376 ammonium_sulphate_eq_frac * NH42SO4_hhso4 + & 6377 ammonium_nitrate_eq_frac * NH4NO3_hhso4 + & 6378 ammonium_chloride_eq_frac * NH4Cl_hhso4 + & 6379 sodium_sulphate_eq_frac * Na2SO4_hhso4 + & 6380 sodium_nitrate_eq_frac * NaNO3_hhso4 + & 6381 sodium_chloride_eq_frac * NaCl_hhso4 6382 gamma_hhso4 = EXP( Ln_hhso4_act ) ! molal activity coefficient of HHSO4 6358 6359 ln_hhso4_act = binary_hhso4 + nitric_acid_eq_frac * hno3_hhso4 + & 6360 hydrochloric_acid_eq_frac * hcl_hhso4 + & 6361 ammonium_sulphate_eq_frac * nh42so4_hhso4 + & 6362 ammonium_nitrate_eq_frac * nh4no3_hhso4 + & 6363 ammonium_chloride_eq_frac * nh4cl_hhso4 + & 6364 sodium_sulphate_eq_frac * na2so4_hhso4 + & 6365 sodium_nitrate_eq_frac * nano3_hhso4 + sodium_chloride_eq_frac * nacl_hhso4 6366 6367 gamma_hhso4 = EXP( ln_hhso4_act ) ! molal activity coefficient of HHSO4 6383 6368 6384 6369 !-- H2SO4 (sulphuric acid): 6385 IF ( RH >= 0.1_wp .AND. RH < 0.9_wp ) THEN 6386 binary_h2so4 = 2.4493_wp * ( RH**2 ) - 6.2326_wp * RH + 2.1763_wp 6387 ELSEIF ( RH >= 0.9_wp .AND. RH < 0.98 ) THEN 6388 binary_h2so4 = 914.68_wp * ( RH**3 ) - 2502.3_wp * ( RH**2 ) + & 6389 2281.9_wp * RH - 695.11_wp 6390 ELSEIF ( RH >= 0.98 .AND. RH < 0.9999 ) THEN 6391 binary_h2so4 = 3E-8_wp * ( RH**4 ) - 5E-6_wp * ( RH**3 ) + & 6392 0.0003_wp * ( RH**2 ) - 0.0022_wp * RH - 1.1305_wp 6393 ENDIF 6394 6370 IF ( rh >= 0.1_wp .AND. rh < 0.9_wp ) THEN 6371 binary_h2so4 = 2.4493_wp * rh**2 - 6.2326_wp * rh + 2.1763_wp 6372 ELSEIF ( rh >= 0.9_wp .AND. rh < 0.98 ) THEN 6373 binary_h2so4 = 914.68_wp * rh**3 - 2502.3_wp * rh**2 + 2281.9_wp * rh - 695.11_wp 6374 ELSEIF ( rh >= 0.98 .AND. rh < 0.9999 ) THEN 6375 binary_h2so4 = 3.0E-8_wp * rh**4 - 5E-6_wp * rh**3 + 0.0003_wp * rh**2 - 0.0022_wp * & 6376 rh - 1.1305_wp 6377 ENDIF 6378 6395 6379 IF ( nitric_acid > 0.0_wp ) THEN 6396 HNO3_h2so4 = - 16.382_wp * ( RH**5 ) + 46.677_wp * ( RH**4 ) - & 6397 54.149_wp * ( RH**3 ) + 34.36_wp * ( RH**2 ) - & 6398 12.54_wp * RH + 2.1368_wp 6399 ENDIF 6400 6380 hno3_h2so4 = - 16.382_wp * rh**5 + 46.677_wp * rh**4 - 54.149_wp * rh**3 + 34.36_wp * & 6381 rh**2 - 12.54_wp * rh + 2.1368_wp 6382 ENDIF 6383 6401 6384 IF ( hydrochloric_acid > 0.0_wp ) THEN 6402 HCL_h2so4 = - 14.409_wp * ( RH**5 ) + 42.804_wp * ( RH**4 ) - & 6403 47.24_wp * ( RH**3 ) + 24.668_wp * ( RH**2 ) - & 6404 5.8015_wp * RH + 0.084627_wp 6405 ENDIF 6406 6385 hcl_h2so4 = - 14.409_wp * rh**5 + 42.804_wp * rh**4 - 47.24_wp * rh**3 + 24.668_wp * & 6386 rh**2 - 5.8015_wp * rh + 0.084627_wp 6387 ENDIF 6388 6407 6389 IF ( ammonium_sulphate > 0.0_wp ) THEN 6408 NH42SO4_h2so4 = 66.71_wp * ( RH**5 ) - 187.5_wp * ( RH**4 ) + & 6409 210.57_wp * ( RH**3 ) - 121.04_wp * ( RH**2 ) + & 6410 39.182_wp * RH - 8.0606_wp 6411 ENDIF 6412 6390 nh42so4_h2so4 = 66.71_wp * rh**5 - 187.5_wp * rh**4 + 210.57_wp * rh**3 - 121.04_wp * & 6391 rh**2 + 39.182_wp * rh - 8.0606_wp 6392 ENDIF 6393 6413 6394 IF ( ammonium_nitrate > 0.0_wp ) THEN 6414 NH4NO3_h2so4 = - 22.532_wp * ( RH**4 ) + 66.615_wp * ( RH**3 ) -&6415 74.647_wp * ( RH**2 ) + 37.638_wp * RH - 6.9711_wp6416 ENDIF 6417 6395 nh4no3_h2so4 = - 22.532_wp * rh**4 + 66.615_wp * rh**3 - 74.647_wp * rh**2 + 37.638_wp * & 6396 rh - 6.9711_wp 6397 ENDIF 6398 6418 6399 IF ( ammonium_chloride > 0.0_wp ) THEN 6419 IF ( RH >= 0.1_wp .AND. RH < 0.2_wp ) THEN 6420 NH4Cl_h2so4 = - 0.32089_wp * RH + 0.57738_wp 6421 ELSEIF ( RH >= 0.2_wp .AND. RH < 0.9_wp ) THEN 6422 NH4Cl_h2so4 = 18.089_wp * ( RH**5 ) - 51.083_wp * ( RH**4 ) + & 6423 50.32_wp * ( RH**3 ) - 17.012_wp * ( RH**2 ) - & 6424 0.93435_wp * RH + 1.0548_wp 6425 ELSEIF ( RH >= 0.9_wp .AND. RH < 0.99_wp ) THEN 6426 NH4Cl_h2so4 = - 1.5749_wp * RH + 1.7002_wp 6400 IF ( rh >= 0.1_wp .AND. rh < 0.2_wp ) THEN 6401 nh4cl_h2so4 = - 0.32089_wp * rh + 0.57738_wp 6402 ELSEIF ( rh >= 0.2_wp .AND. rh < 0.9_wp ) THEN 6403 nh4cl_h2so4 = 18.089_wp * rh**5 - 51.083_wp * rh**4 + 50.32_wp * rh**3 - 17.012_wp * & 6404 rh**2 - 0.93435_wp * rh + 1.0548_wp 6405 ELSEIF ( rh >= 0.9_wp .AND. rh < 0.99_wp ) THEN 6406 nh4cl_h2so4 = - 1.5749_wp * rh + 1.7002_wp 6427 6407 ENDIF 6428 6408 ENDIF 6429 6409 6430 6410 IF ( sodium_sulphate > 0.0_wp ) THEN 6431 Na2SO4_h2so4 = 29.843_wp * ( RH**4 ) - 69.417_wp * ( RH**3 ) +&6432 61.507_wp * ( RH**2 ) - 29.874_wp * RH+ 7.7556_wp6433 ENDIF 6434 6411 na2so4_h2so4 = 29.843_wp * rh**4 - 69.417_wp * rh**3 + 61.507_wp * rh**2 - 29.874_wp * & 6412 rh + 7.7556_wp 6413 ENDIF 6414 6435 6415 IF ( sodium_nitrate > 0.0_wp ) THEN 6436 NaNO3_h2so4 = - 122.37_wp * ( RH**6 ) + 427.43_wp * ( RH**5 ) - & 6437 604.68_wp * ( RH**4 ) + 443.08_wp * ( RH**3 ) - & 6438 178.61_wp * ( RH**2 ) + 37.242_wp * RH - 1.9564_wp 6439 ENDIF 6440 6416 nano3_h2so4 = - 122.37_wp * rh**6 + 427.43_wp * rh**5 - 604.68_wp * rh**4 + 443.08_wp * & 6417 rh**3 - 178.61_wp * rh**2 + 37.242_wp * rh - 1.9564_wp 6418 ENDIF 6419 6441 6420 IF ( sodium_chloride > 0.0_wp ) THEN 6442 NaCl_h2so4 = - 40.288_wp * ( RH**5 ) + 115.61_wp * ( RH**4 ) - & 6443 129.99_wp * ( RH**3 ) + 72.652_wp * ( RH**2 ) - & 6444 22.124_wp * RH + 4.2676_wp 6445 ENDIF 6446 6447 Ln_h2so4_act = binary_h2so4 + & 6448 nitric_acid_eq_frac * HNO3_h2so4 + & 6449 hydrochloric_acid_eq_frac * HCL_h2so4 + & 6450 ammonium_sulphate_eq_frac * NH42SO4_h2so4 + & 6451 ammonium_nitrate_eq_frac * NH4NO3_h2so4 + & 6452 ammonium_chloride_eq_frac * NH4Cl_h2so4 + & 6453 sodium_sulphate_eq_frac * Na2SO4_h2so4 + & 6454 sodium_nitrate_eq_frac * NaNO3_h2so4 + & 6455 sodium_chloride_eq_frac * NaCl_h2so4 6456 6457 gamma_h2so4 = EXP( Ln_h2so4_act ) ! molal activity coefficient 6458 ! 6421 nacl_h2so4 = - 40.288_wp * rh**5 + 115.61_wp * rh**4 - 129.99_wp * rh**3 + 72.652_wp * & 6422 rh**2 - 22.124_wp * rh + 4.2676_wp 6423 ENDIF 6424 6425 ln_h2so4_act = binary_h2so4 + nitric_acid_eq_frac * hno3_h2so4 + & 6426 hydrochloric_acid_eq_frac * hcl_h2so4 + & 6427 ammonium_sulphate_eq_frac * nh42so4_h2so4 + & 6428 ammonium_nitrate_eq_frac * nh4no3_h2so4 + & 6429 ammonium_chloride_eq_frac * nh4cl_h2so4 + & 6430 sodium_sulphate_eq_frac * na2so4_h2so4 + & 6431 sodium_nitrate_eq_frac * nano3_h2so4 + sodium_chloride_eq_frac * nacl_h2so4 6432 6433 gamma_h2so4 = EXP( ln_h2so4_act ) ! molal activity coefficient 6434 ! 6459 6435 !-- Export activity coefficients 6460 6436 IF ( gamma_h2so4 > 1.0E-10_wp ) THEN 6461 gamma_out(4) = ( gamma_hhso4**2.0_wp )/ gamma_h2so46437 gamma_out(4) = gamma_hhso4**2 / gamma_h2so4 6462 6438 ENDIF 6463 6439 IF ( gamma_hhso4 > 1.0E-10_wp ) THEN 6464 gamma_out(5) = ( gamma_h2so4**3.0_wp ) / ( gamma_hhso4**2.0_wp )6440 gamma_out(5) = gamma_h2so4**3 / gamma_hhso4**2 6465 6441 ENDIF 6466 6442 ! 6467 6443 !-- Ionic activity coefficient product 6468 act_product = ( gamma_h2so4**3.0_wp ) / ( gamma_hhso4**2.0_wp )6444 act_product = gamma_h2so4**3 / gamma_hhso4**2 6469 6445 ! 6470 6446 !-- Solve the quadratic equation (i.e. x in ax**2 + bx + c = 0) 6471 6447 a = 1.0_wp 6472 b = - 1.0_wp * ( ions(4) + ions(1) + ( ( water_total * 18.0E-3_wp ) /&6473 ( 99.0_wp * act_product ) ) )6448 b = -1.0_wp * ( ions(4) + ions(1) + ( ( water_total * 18.0E-3_wp ) / & 6449 ( 99.0_wp * act_product ) ) ) 6474 6450 c = ions(4) * ions(1) 6475 root1 = ( ( -1.0_wp * b ) + ( ( ( b**2 ) - 4.0_wp * a * c )**0.5_wp & 6476 ) ) / ( 2 * a ) 6477 root2 = ( ( -1.0_wp * b ) - ( ( ( b**2 ) - 4.0_wp * a * c) **0.5_wp & 6478 ) ) / ( 2 * a ) 6451 root1 = ( ( -1.0_wp * b ) + ( ( ( b**2 ) - 4.0_wp * a * c )**0.5_wp ) ) / ( 2.0_wp * a ) 6452 root2 = ( ( -1.0_wp * b ) - ( ( ( b**2 ) - 4.0_wp * a * c) **0.5_wp ) ) / ( 2.0_wp * a ) 6479 6453 6480 6454 IF ( root1 > ions(1) .OR. root1 < 0.0_wp ) THEN … … 6485 6459 root2 = 0.0_wp 6486 6460 ENDIF 6487 ! 6461 ! 6488 6462 !-- Calculate the new hydrogen ion, bisulphate ion and sulphate ion 6489 6463 !-- concentration 6490 hso4_real = 0.0_wp6491 6464 h_real = ions(1) 6492 6465 so4_real = ions(4) 6493 IF ( root1 == 0.0_wp ) THEN 6494 hso4_real = root2 6495 ELSEIF ( root2 == 0.0_wp ) THEN 6496 hso4_real = root1 6497 ENDIF 6466 hso4_real = MAX( root1, root2 ) 6498 6467 h_real = ions(1) - hso4_real 6499 6468 so4_real = ions(4) - hso4_real … … 6507 6476 hso4_out = hso4_real 6508 6477 so4_out = so4_real 6509 6510 ELSE IF ( ions(1) == 0.0_wp .OR. ions(4) == 0.0_wp ) THEN6478 6479 ELSE 6511 6480 h_out = ions(1) 6512 6481 hso4_out = 0.0_wp … … 6517 6486 !-- 4) ACTIVITY COEFFICIENTS -for vapour pressures of HNO3,HCL and NH3 6518 6487 ! 6519 !-- This section evaluates activity coefficients and vapour pressures using the 6520 !-- water content calculated above) for each inorganic condensing species: 6521 !-- a - HNO3, b - NH3, c - HCL. 6522 !-- The following procedure is used: 6523 !-- Zaveri et al (2005) found that one could express the variation of activity 6524 !-- coefficients linearly in log-space if equivalent mole fractions were used. 6525 !-- So, by a taylor series expansion LOG( activity coefficient ) = 6526 !-- LOG( binary activity coefficient at a given RH ) + 6527 !-- (equivalent mole fraction compound A) * 6528 !-- ('interaction' parameter between A and condensing species) + 6529 !-- equivalent mole fraction compound B) * 6530 !-- ('interaction' parameter between B and condensing species). 6531 !-- Here, the interaction parameters have been fit to ADDEM by searching the 6532 !-- whole compositon space and fit usign the Levenberg-Marquardt non-linear 6533 !-- least squares algorithm. 6534 ! 6535 !-- They are given as a function of RH and vary with complexity ranging from 6536 !-- linear to 5th order polynomial expressions, the binary activity coefficients 6537 !-- were calculated using AIM online. 6538 !-- NOTE: for NH3, no binary activity coefficient was used and the data were fit 6539 !-- to the ratio of the activity coefficients for the ammonium and hydrogen 6540 !-- ions. Once the activity coefficients are obtained the vapour pressure can be 6541 !-- easily calculated using tabulated equilibrium constants (referenced). This 6542 !-- procedure differs from that of Zaveri et al (2005) in that it is not assumed 6543 !-- one can carry behaviour from binary mixtures in multicomponent systems. To 6544 !-- this end we have fit the 'interaction' parameters explicitly to a general 6545 !-- inorganic equilibrium model (ADDEM - Topping et al. 2005a,b). Such 6546 !-- parameters take into account bisulphate ion dissociation and water content. 6547 !-- This also allows us to consider one regime for all composition space, rather 6548 !-- than defining sulphate rich and sulphate poor regimes 6549 !-- NOTE: The flags "binary_case" and "full_complexity" are not used in this 6550 !-- prototype. They are used for simplification of the fit expressions when 6551 !-- using limited composition regions. 6488 !-- This section evaluates activity coefficients and vapour pressures using the water content 6489 !-- calculated above) for each inorganic condensing species: a - HNO3, b - NH3, c - HCL. 6490 !-- The following procedure is used: Zaveri et al (2005) found that one could express the variation 6491 !-- of activity coefficients linearly in log-space if equivalent mole fractions were used. 6492 !-- So, by a taylor series expansion LOG( activity coefficient ) = 6493 !-- LOG( binary activity coefficient at a given RH ) + 6494 !-- (equivalent mole fraction compound A) * 6495 !-- ('interaction' parameter between A and condensing species) + 6496 !-- equivalent mole fraction compound B) * 6497 !-- ('interaction' parameter between B and condensing species). 6498 !-- Here, the interaction parameters have been fit to ADDEM by searching the whole compositon space 6499 !-- and fit usign the Levenberg-Marquardt non-linear least squares algorithm. 6500 ! 6501 !-- They are given as a function of RH and vary with complexity ranging from linear to 5th order 6502 !-- polynomial expressions, the binary activity coefficients were calculated using AIM online. 6503 !-- NOTE: for NH3, no binary activity coefficient was used and the data were fit to the ratio of the 6504 !-- activity coefficients for the ammonium and hydrogen ions. Once the activity coefficients are 6505 !-- obtained the vapour pressure can be easily calculated using tabulated equilibrium constants 6506 !-- (referenced). This procedure differs from that of Zaveri et al (2005) in that it is not assumed 6507 !-- one can carry behaviour from binary mixtures in multicomponent systems. To this end we have fit 6508 !-- the 'interaction' parameters explicitly to a general inorganic equilibrium model 6509 !-- (ADDEM - Topping et al. 2005a,b). Such parameters take into account bisulphate ion dissociation 6510 !-- and water content. This also allows us to consider one regime for all composition space, rather 6511 !-- than defining sulphate rich and sulphate poor regimes. 6512 !-- NOTE: The flags "binary_case" and "full_complexity" are not used in this prototype. They are 6513 !-- used for simplification of the fit expressions when using limited composition regions. 6552 6514 ! 6553 6515 !-- a) - ACTIVITY COEFF/VAPOUR PRESSURE - HNO3 6554 6516 IF ( ions(1) > 0.0_wp .AND. ions(6) > 0.0_wp ) THEN 6555 6517 binary_case = 1 6556 IF ( RH > 0.1_wp .AND. RH< 0.98_wp ) THEN6518 IF ( rh > 0.1_wp .AND. rh < 0.98_wp ) THEN 6557 6519 IF ( binary_case == 1 ) THEN 6558 binary_hno3 = 1.8514_wp * ( RH**3 ) - 4.6991_wp * ( RH**2 ) + & 6559 1.5514_wp * RH + 0.90236_wp 6520 binary_hno3 = 1.8514_wp * rh**3 - 4.6991_wp * rh**2 + 1.5514_wp * rh + 0.90236_wp 6560 6521 ELSEIF ( binary_case == 2 ) THEN 6561 binary_hno3 = - 1.1751_wp * ( RH**2 ) - 0.53794_wp * RH + & 6562 1.2808_wp 6522 binary_hno3 = - 1.1751_wp * ( rh**2 ) - 0.53794_wp * rh + 1.2808_wp 6563 6523 ENDIF 6564 ELSEIF ( RH >= 0.98_wp .AND. RH < 0.9999_wp ) THEN 6565 binary_hno3 = 1244.69635941351_wp * ( RH**3 ) - & 6566 2613.93941099991_wp * ( RH**2 ) + & 6567 1525.0684974546_wp * RH -155.946764059316_wp 6568 ENDIF 6569 ! 6524 ELSEIF ( rh >= 0.98_wp .AND. rh < 0.9999_wp ) THEN 6525 binary_hno3 = 1244.69635941351_wp * rh**3 - 2613.93941099991_wp * rh**2 + & 6526 1525.0684974546_wp * rh -155.946764059316_wp 6527 ENDIF 6528 ! 6570 6529 !-- Contributions from other solutes 6571 6530 full_complexity = 1 6572 6531 IF ( hydrochloric_acid > 0.0_wp ) THEN ! HCL 6573 IF ( full_complexity == 1 .OR. RH< 0.4_wp ) THEN6574 HCL_hno3 = 16.051_wp * ( RH**4 ) - 44.357_wp * ( RH**3 ) +&6575 45.141_wp * ( RH**2 ) - 21.638_wp * RH+ 4.8182_wp6576 ELSEIF ( full_complexity == 0 .AND. RH> 0.4_wp ) THEN6577 HCL_hno3 = - 1.5833_wp * RH+ 1.5569_wp6532 IF ( full_complexity == 1 .OR. rh < 0.4_wp ) THEN 6533 hcl_hno3 = 16.051_wp * rh**4 - 44.357_wp * rh**3 + 45.141_wp * rh**2 - 21.638_wp * & 6534 rh + 4.8182_wp 6535 ELSEIF ( full_complexity == 0 .AND. rh > 0.4_wp ) THEN 6536 hcl_hno3 = - 1.5833_wp * rh + 1.5569_wp 6578 6537 ENDIF 6579 6538 ENDIF 6580 6539 6581 6540 IF ( sulphuric_acid > 0.0_wp ) THEN ! H2SO4 6582 IF ( full_complexity == 1 .OR. RH < 0.4_wp ) THEN 6583 H2SO4_hno3 = - 3.0849_wp * ( RH**3 ) + 5.9609_wp * ( RH**2 ) - & 6584 4.468_wp * RH + 1.5658_wp 6585 ELSEIF ( full_complexity == 0 .AND. RH > 0.4_wp ) THEN 6586 H2SO4_hno3 = - 0.93473_wp * RH + 0.9363_wp 6541 IF ( full_complexity == 1 .OR. rh < 0.4_wp ) THEN 6542 h2so4_hno3 = - 3.0849_wp * rh**3 + 5.9609_wp * rh**2 - 4.468_wp * rh + 1.5658_wp 6543 ELSEIF ( full_complexity == 0 .AND. rh > 0.4_wp ) THEN 6544 h2so4_hno3 = - 0.93473_wp * rh + 0.9363_wp 6587 6545 ENDIF 6588 6546 ENDIF 6589 6547 6590 6548 IF ( ammonium_sulphate > 0.0_wp ) THEN ! NH42SO4 6591 NH42SO4_hno3 = 16.821_wp * ( RH**3 ) - 28.391_wp * ( RH**2 ) + & 6592 18.133_wp * RH - 6.7356_wp 6593 ENDIF 6594 6549 nh42so4_hno3 = 16.821_wp * rh**3 - 28.391_wp * rh**2 + 18.133_wp * rh - 6.7356_wp 6550 ENDIF 6551 6595 6552 IF ( ammonium_nitrate > 0.0_wp ) THEN ! NH4NO3 6596 NH4NO3_hno3 = 11.01_wp * ( RH**3 ) - 21.578_wp * ( RH**2 ) + & 6597 14.808_wp * RH - 4.2593_wp 6598 ENDIF 6599 6553 nh4no3_hno3 = 11.01_wp * rh**3 - 21.578_wp * rh**2 + 14.808_wp * rh - 4.2593_wp 6554 ENDIF 6555 6600 6556 IF ( ammonium_chloride > 0.0_wp ) THEN ! NH4Cl 6601 IF ( full_complexity == 1 .OR. RH <= 0.4_wp ) THEN 6602 NH4Cl_hno3 = - 1.176_wp * ( RH**3 ) + 5.0828_wp * ( RH**2 ) - & 6603 3.8792_wp * RH - 0.05518_wp 6604 ELSEIF ( full_complexity == 0 .AND. RH > 0.4_wp ) THEN 6605 NH4Cl_hno3 = 2.6219_wp * ( RH**2 ) - 2.2609_wp * RH - 0.38436_wp 6557 IF ( full_complexity == 1 .OR. rh <= 0.4_wp ) THEN 6558 nh4cl_hno3 = - 1.176_wp * rh**3 + 5.0828_wp * rh**2 - 3.8792_wp * rh - 0.05518_wp 6559 ELSEIF ( full_complexity == 0 .AND. rh > 0.4_wp ) THEN 6560 nh4cl_hno3 = 2.6219_wp * rh**2 - 2.2609_wp * rh - 0.38436_wp 6606 6561 ENDIF 6607 6562 ENDIF 6608 6563 6609 6564 IF ( sodium_sulphate > 0.0_wp ) THEN ! Na2SO4 6610 Na2SO4_hno3 = 35.504_wp * ( RH**4 ) - 80.101_wp * ( RH**3 ) +&6611 67.326_wp * ( RH**2 ) - 28.461_wp * RH+ 5.6016_wp6612 ENDIF 6613 6565 na2so4_hno3 = 35.504_wp * rh**4 - 80.101_wp * rh**3 + 67.326_wp * rh**2 - 28.461_wp * & 6566 rh + 5.6016_wp 6567 ENDIF 6568 6614 6569 IF ( sodium_nitrate > 0.0_wp ) THEN ! NaNO3 6615 IF ( full_complexity == 1 .OR. RH <= 0.4_wp ) THEN 6616 NaNO3_hno3 = 23.659_wp * ( RH**5 ) - 66.917_wp * ( RH**4 ) + & 6617 74.686_wp * ( RH**3 ) - 40.795_wp * ( RH**2 ) + & 6618 10.831_wp * RH - 1.4701_wp 6619 ELSEIF ( full_complexity == 0 .AND. RH > 0.4_wp ) THEN 6620 NaNO3_hno3 = 14.749_wp * ( RH**4 ) - 35.237_wp * ( RH**3 ) + & 6621 31.196_wp * ( RH**2 ) - 12.076_wp * RH + 1.3605_wp 6570 IF ( full_complexity == 1 .OR. rh <= 0.4_wp ) THEN 6571 nano3_hno3 = 23.659_wp * rh**5 - 66.917_wp * rh**4 + 74.686_wp * rh**3 - 40.795_wp * & 6572 rh**2 + 10.831_wp * rh - 1.4701_wp 6573 ELSEIF ( full_complexity == 0 .AND. rh > 0.4_wp ) THEN 6574 nano3_hno3 = 14.749_wp * rh**4 - 35.237_wp * rh**3 + 31.196_wp * rh**2 - 12.076_wp * & 6575 rh + 1.3605_wp 6622 6576 ENDIF 6623 6577 ENDIF 6624 6578 6625 6579 IF ( sodium_chloride > 0.0_wp ) THEN ! NaCl 6626 IF ( full_complexity == 1 .OR. RH <= 0.4_wp ) THEN 6627 NaCl_hno3 = 13.682_wp * ( RH**4 ) - 35.122_wp * ( RH**3 ) + & 6628 33.397_wp * ( RH**2 ) - 14.586_wp * RH + 2.6276_wp 6629 ELSEIF ( full_complexity == 0 .AND. RH > 0.4_wp ) THEN 6630 NaCl_hno3 = 1.1882_wp * ( RH**3 ) - 1.1037_wp * ( RH**2 ) - & 6631 0.7642_wp * RH + 0.6671_wp 6580 IF ( full_complexity == 1 .OR. rh <= 0.4_wp ) THEN 6581 nacl_hno3 = 13.682_wp * rh**4 - 35.122_wp * rh**3 + 33.397_wp * rh**2 - 14.586_wp * & 6582 rh + 2.6276_wp 6583 ELSEIF ( full_complexity == 0 .AND. rh > 0.4_wp ) THEN 6584 nacl_hno3 = 1.1882_wp * rh**3 - 1.1037_wp * rh**2 - 0.7642_wp * rh + 0.6671_wp 6632 6585 ENDIF 6633 6586 ENDIF 6634 6635 Ln_HNO3_act = binary_hno3 + & 6636 hydrochloric_acid_eq_frac * HCL_hno3 + & 6637 sulphuric_acid_eq_frac * H2SO4_hno3 + & 6638 ammonium_sulphate_eq_frac * NH42SO4_hno3 + & 6639 ammonium_nitrate_eq_frac * NH4NO3_hno3 + & 6640 ammonium_chloride_eq_frac * NH4Cl_hno3 + & 6641 sodium_sulphate_eq_frac * Na2SO4_hno3 + & 6642 sodium_nitrate_eq_frac * NaNO3_hno3 + & 6643 sodium_chloride_eq_frac * NaCl_hno3 6644 6645 gamma_hno3 = EXP( Ln_HNO3_act ) ! Molal activity coefficient of HNO3 6587 6588 ln_hno3_act = binary_hno3 + hydrochloric_acid_eq_frac * hcl_hno3 + & 6589 sulphuric_acid_eq_frac * h2so4_hno3 + & 6590 ammonium_sulphate_eq_frac * nh42so4_hno3 + & 6591 ammonium_nitrate_eq_frac * nh4no3_hno3 + & 6592 ammonium_chloride_eq_frac * nh4cl_hno3 + & 6593 sodium_sulphate_eq_frac * na2so4_hno3 + & 6594 sodium_nitrate_eq_frac * nano3_hno3 + sodium_chloride_eq_frac * nacl_hno3 6595 6596 gamma_hno3 = EXP( ln_hno3_act ) ! Molal activity coefficient of HNO3 6646 6597 gamma_out(1) = gamma_hno3 6647 6598 ! 6648 6599 !-- Partial pressure calculation 6649 !-- K_hno3 = 2.51 * ( 10**6 ) 6650 !-- K_hno3 = 2.628145923d6 !< calculated by AIM online (Clegg et al 1998) 6651 !-- after Chameides (1984) (and NIST database) 6652 K_hno3 = 2.6E6_wp * EXP( 8700.0_wp * henrys_temp_dep) 6653 Press_HNO3 = ( ions_mol(1) * ions_mol(6) * ( gamma_hno3**2 ) ) / & 6654 K_hno3 6600 !-- k_hno3 = 2.51 * ( 10**6 ) 6601 !-- k_hno3 = 2.628145923d6 !< calculated by AIM online (Clegg et al 1998) after Chameides (1984) 6602 k_hno3 = 2.6E6_wp * EXP( 8700.0_wp * henrys_temp_dep ) 6603 press_hno3 = ( ions_mol(1) * ions_mol(6) * ( gamma_hno3**2 ) ) / k_hno3 6655 6604 ENDIF 6656 ! 6605 ! 6657 6606 !-- b) - ACTIVITY COEFF/VAPOUR PRESSURE - NH3 6658 6607 !-- Follow the two solute approach of Zaveri et al. (2005) 6659 IF ( ions(2) > 0.0_wp .AND. ions_mol(1) > 0.0_wp ) THEN 6608 IF ( ions(2) > 0.0_wp .AND. ions_mol(1) > 0.0_wp ) THEN 6609 ! 6660 6610 !-- NH4HSO4: 6661 binary_nh4hso4 = 56.907_wp * ( RH**6 ) - 155.32_wp * ( RH**5 ) + & 6662 142.94_wp * ( RH**4 ) - 32.298_wp * ( RH**3 ) - & 6663 27.936_wp * ( RH**2 ) + 19.502_wp * RH - 4.2618_wp 6611 binary_nh4hso4 = 56.907_wp * rh**6 - 155.32_wp * rh**5 + 142.94_wp * rh**4 - 32.298_wp * & 6612 rh**3 - 27.936_wp * rh**2 + 19.502_wp * rh - 4.2618_wp 6664 6613 IF ( nitric_acid > 0.0_wp) THEN ! HNO3 6665 HNO3_nh4hso4 = 104.8369_wp * ( RH**8 ) - 288.8923_wp * ( RH**7 ) + & 6666 129.3445_wp * ( RH**6 ) + 373.0471_wp * ( RH**5 ) - & 6667 571.0385_wp * ( RH**4 ) + 326.3528_wp * ( RH**3 ) - & 6668 74.169_wp * ( RH**2 ) - 2.4999_wp * RH + 3.17_wp 6669 ENDIF 6670 6671 IF ( hydrochloric_acid > 0.0_wp) THEN ! HCL 6672 HCL_nh4hso4 = - 7.9133_wp * ( RH**8 ) + 126.6648_wp * ( RH**7 ) - & 6673 460.7425_wp * ( RH**6 ) + 731.606_wp * ( RH**5 ) - & 6674 582.7467_wp * ( RH**4 ) + 216.7197_wp * ( RH**3 ) - & 6675 11.3934_wp * ( RH**2 ) - 17.7728_wp * RH + 5.75_wp 6676 ENDIF 6677 6614 hno3_nh4hso4 = 104.8369_wp * rh**8 - 288.8923_wp * rh**7 + 129.3445_wp * rh**6 + & 6615 373.0471_wp * rh**5 - 571.0385_wp * rh**4 + 326.3528_wp * rh**3 - & 6616 74.169_wp * rh**2 - 2.4999_wp * rh + 3.17_wp 6617 ENDIF 6618 6619 IF ( hydrochloric_acid > 0.0_wp) THEN ! HCL 6620 hcl_nh4hso4 = - 7.9133_wp * rh**8 + 126.6648_wp * rh**7 - 460.7425_wp * rh**6 + & 6621 731.606_wp * rh**5 - 582.7467_wp * rh**4 + 216.7197_wp * rh**3 - & 6622 11.3934_wp * rh**2 - 17.7728_wp * rh + 5.75_wp 6623 ENDIF 6624 6678 6625 IF ( sulphuric_acid > 0.0_wp) THEN ! H2SO4 6679 H2SO4_nh4hso4 = 195.981_wp * ( RH**8 ) - 779.2067_wp * ( RH**7 ) + & 6680 1226.3647_wp * ( RH**6 ) - 964.0261_wp * ( RH**5 ) + & 6681 391.7911_wp * ( RH**4 ) - 84.1409_wp * ( RH**3 ) + & 6682 20.0602_wp * ( RH**2 ) - 10.2663_wp * RH + 3.5817_wp 6683 ENDIF 6684 6626 h2so4_nh4hso4 = 195.981_wp * rh**8 - 779.2067_wp * rh**7 + 1226.3647_wp * rh**6 - & 6627 964.0261_wp * rh**5 + 391.7911_wp * rh**4 - 84.1409_wp * rh**3 + & 6628 20.0602_wp * rh**2 - 10.2663_wp * rh + 3.5817_wp 6629 ENDIF 6630 6685 6631 IF ( ammonium_sulphate > 0.0_wp) THEN ! NH42SO4 6686 NH42SO4_nh4hso4 = 617.777_wp * ( RH**8 ) - 2547.427_wp * ( RH**7 ) & 6687 + 4361.6009_wp * ( RH**6 ) - 4003.162_wp * ( RH**5 ) & 6688 + 2117.8281_wp * ( RH**4 ) - 640.0678_wp * ( RH**3 ) & 6689 + 98.0902_wp * ( RH**2 ) - 2.2615_wp * RH - 2.3811_wp 6690 ENDIF 6691 6632 nh42so4_nh4hso4 = 617.777_wp * rh**8 - 2547.427_wp * rh**7 + 4361.6009_wp * rh**6 - & 6633 4003.162_wp * rh**5 + 2117.8281_wp * rh**4 - 640.0678_wp * rh**3 + & 6634 98.0902_wp * rh**2 - 2.2615_wp * rh - 2.3811_wp 6635 ENDIF 6636 6692 6637 IF ( ammonium_nitrate > 0.0_wp) THEN ! NH4NO3 6693 NH4NO3_nh4hso4 = - 104.4504_wp * ( RH**8 ) + 539.5921_wp * & 6694 ( RH**7 ) - 1157.0498_wp * ( RH**6 ) + 1322.4507_wp * & 6695 ( RH**5 ) - 852.2475_wp * ( RH**4 ) + 298.3734_wp * & 6696 ( RH**3 ) - 47.0309_wp * ( RH**2 ) + 1.297_wp * RH - & 6697 0.8029_wp 6698 ENDIF 6699 6638 nh4no3_nh4hso4 = - 104.4504_wp * rh**8 + 539.5921_wp * rh**7 - 1157.0498_wp * rh**6 + & 6639 1322.4507_wp * rh**5 - 852.2475_wp * rh**4 + 298.3734_wp * rh**3 - & 6640 47.0309_wp * rh**2 + 1.297_wp * rh - 0.8029_wp 6641 ENDIF 6642 6700 6643 IF ( ammonium_chloride > 0.0_wp) THEN ! NH4Cl 6701 NH4Cl_nh4hso4 = 258.1792_wp * ( RH**8 ) - 1019.3777_wp * & 6702 ( RH**7 ) + 1592.8918_wp * ( RH**6 ) - 1221.0726_wp * & 6703 ( RH**5 ) + 442.2548_wp * ( RH**4 ) - 43.6278_wp * & 6704 ( RH**3 ) - 7.5282_wp * ( RH**2 ) - 3.8459_wp * RH + 2.2728_wp 6705 ENDIF 6706 6644 nh4cl_nh4hso4 = 258.1792_wp * rh**8 - 1019.3777_wp * rh**7 + 1592.8918_wp * rh**6 - & 6645 1221.0726_wp * rh**5 + 442.2548_wp * rh**4 - 43.6278_wp * rh**3 - & 6646 7.5282_wp * rh**2 - 3.8459_wp * rh + 2.2728_wp 6647 ENDIF 6648 6707 6649 IF ( sodium_sulphate > 0.0_wp) THEN ! Na2SO4 6708 Na2SO4_nh4hso4 = 225.4238_wp * ( RH**8 ) - 732.4113_wp * & 6709 ( RH**7 ) + 843.7291_wp * ( RH**6 ) - 322.7328_wp * & 6710 ( RH**5 ) - 88.6252_wp * ( RH**4 ) + 72.4434_wp * & 6711 ( RH**3 ) + 22.9252_wp * ( RH**2 ) - 25.3954_wp * RH + & 6712 4.6971_wp 6713 ENDIF 6714 6650 na2so4_nh4hso4 = 225.4238_wp * rh**8 - 732.4113_wp * rh**7 + 843.7291_wp * rh**6 - & 6651 322.7328_wp * rh**5 - 88.6252_wp * rh**4 + 72.4434_wp * rh**3 + & 6652 22.9252_wp * rh**2 - 25.3954_wp * rh + 4.6971_wp 6653 ENDIF 6654 6715 6655 IF ( sodium_nitrate > 0.0_wp) THEN ! NaNO3 6716 NaNO3_nh4hso4 = 96.1348_wp * ( RH**8 ) - 341.6738_wp * ( RH**7 ) + & 6717 406.5314_wp * ( RH**6 ) - 98.5777_wp * ( RH**5 ) - & 6718 172.8286_wp * ( RH**4 ) + 149.3151_wp * ( RH**3 ) - & 6719 38.9998_wp * ( RH**2 ) - 0.2251 * RH + 0.4953_wp 6720 ENDIF 6721 6656 nano3_nh4hso4 = 96.1348_wp * rh**8 - 341.6738_wp * rh**7 + 406.5314_wp * rh**6 - & 6657 98.5777_wp * rh**5 - 172.8286_wp * rh**4 + 149.3151_wp * rh**3 - & 6658 38.9998_wp * rh**2 - 0.2251_wp * rh + 0.4953_wp 6659 ENDIF 6660 6722 6661 IF ( sodium_chloride > 0.0_wp) THEN ! NaCl 6723 NaCl_nh4hso4 = 91.7856_wp * ( RH**8 ) - 316.6773_wp * ( RH**7 ) + & 6724 358.2703_wp * ( RH**6 ) - 68.9142 * ( RH**5 ) - & 6725 156.5031_wp * ( RH**4 ) + 116.9592_wp * ( RH**3 ) - & 6726 22.5271_wp * ( RH**2 ) - 3.7716_wp * RH + 1.56_wp 6727 ENDIF 6728 6729 Ln_NH4HSO4_act = binary_nh4hso4 + & 6730 nitric_acid_eq_frac * HNO3_nh4hso4 + & 6731 hydrochloric_acid_eq_frac * HCL_nh4hso4 + & 6732 sulphuric_acid_eq_frac * H2SO4_nh4hso4 + & 6733 ammonium_sulphate_eq_frac * NH42SO4_nh4hso4 + & 6734 ammonium_nitrate_eq_frac * NH4NO3_nh4hso4 + & 6735 ammonium_chloride_eq_frac * NH4Cl_nh4hso4 + & 6736 sodium_sulphate_eq_frac * Na2SO4_nh4hso4 + & 6737 sodium_nitrate_eq_frac * NaNO3_nh4hso4 + & 6738 sodium_chloride_eq_frac * NaCl_nh4hso4 6739 6740 gamma_nh4hso4 = EXP( Ln_NH4HSO4_act ) ! molal act. coefficient of NH4HSO4 6662 nacl_nh4hso4 = 91.7856_wp * rh**8 - 316.6773_wp * rh**7 + 358.2703_wp * rh**6 - & 6663 68.9142_wp * rh**5 - 156.5031_wp * rh**4 + 116.9592_wp * rh**3 - & 6664 22.5271_wp * rh**2 - 3.7716_wp * rh + 1.56_wp 6665 ENDIF 6666 6667 ln_nh4hso4_act = binary_nh4hso4 + nitric_acid_eq_frac * hno3_nh4hso4 + & 6668 hydrochloric_acid_eq_frac * hcl_nh4hso4 + & 6669 sulphuric_acid_eq_frac * h2so4_nh4hso4 + & 6670 ammonium_sulphate_eq_frac * nh42so4_nh4hso4 + & 6671 ammonium_nitrate_eq_frac * nh4no3_nh4hso4 + & 6672 ammonium_chloride_eq_frac * nh4cl_nh4hso4 + & 6673 sodium_sulphate_eq_frac * na2so4_nh4hso4 + & 6674 sodium_nitrate_eq_frac * nano3_nh4hso4 + & 6675 sodium_chloride_eq_frac * nacl_nh4hso4 6676 6677 gamma_nh4hso4 = EXP( ln_nh4hso4_act ) ! molal act. coefficient of NH4HSO4 6678 ! 6741 6679 !-- Molal activity coefficient of NO3- 6742 6680 gamma_out(6) = gamma_nh4hso4 6743 !-- Molal activity coefficient of NH4+ 6744 gamma_nh3 = ( gamma_nh4hso4**2 ) / ( gamma_hhso4**2 ) 6681 ! 6682 !-- Molal activity coefficient of NH4+ 6683 gamma_nh3 = gamma_nh4hso4**2 / gamma_hhso4**2 6745 6684 gamma_out(3) = gamma_nh3 6746 ! 6747 !-- This actually represents the ratio of the ammonium to hydrogen ion 6748 !-- activity coefficients (see Zaveri paper) - multiply this by the ratio 6749 !-- of the ammonium to hydrogen ion molality and the ratio of appropriate 6750 !-- equilibrium constants 6685 ! 6686 !-- This actually represents the ratio of the ammonium to hydrogen ion activity coefficients 6687 !-- (see Zaveri paper) - multiply this by the ratio of the ammonium to hydrogen ion molality and 6688 !-- the ratio of appropriate equilibrium constants 6751 6689 ! 6752 6690 !-- Equilibrium constants 6753 !-- Kh = 57.64d0 ! Zaveri et al. (2005) 6754 Kh = 5.8E1_wp * EXP( 4085.0_wp * henrys_temp_dep ) ! after Chameides 6755 ! ! (1984) (and NIST database) 6756 !-- Knh4 = 1.81E-5_wp ! Zaveri et al. (2005) 6757 Knh4 = 1.7E-5_wp * EXP( -4325.0_wp * henrys_temp_dep ) ! Chameides 6758 ! (1984) 6759 !-- Kw = 1.01E-14_wp ! Zaveri et al (2005) 6760 Kw = 1.E-14_wp * EXP( -6716.0_wp * henrys_temp_dep ) ! Chameides 6761 ! (1984) 6691 !-- k_h = 57.64d0 ! Zaveri et al. (2005) 6692 k_h = 5.8E1_wp * EXP( 4085.0_wp * henrys_temp_dep ) ! after Chameides (1984) 6693 !-- k_nh4 = 1.81E-5_wp ! Zaveri et al. (2005) 6694 k_nh4 = 1.7E-5_wp * EXP( -4325.0_wp * henrys_temp_dep ) ! Chameides (1984) 6695 !-- k_h2o = 1.01E-14_wp ! Zaveri et al (2005) 6696 k_h2o = 1.E-14_wp * EXP( -6716.0_wp * henrys_temp_dep ) ! Chameides (1984) 6762 6697 ! 6763 6698 molality_ratio_nh3 = ions_mol(2) / ions_mol(1) 6764 !-- Partial pressure calculation 6765 Press_NH3 = molality_ratio_nh3 * gamma_nh3 * ( Kw / ( Kh * Knh4 ) ) 6766 6699 ! 6700 !-- Partial pressure calculation 6701 press_nh3 = molality_ratio_nh3 * gamma_nh3 * ( k_h2o / ( k_h * k_nh4 ) ) 6702 6767 6703 ENDIF 6768 ! 6704 ! 6769 6705 !-- c) - ACTIVITY COEFF/VAPOUR PRESSURE - HCL 6770 6706 IF ( ions(1) > 0.0_wp .AND. ions(7) > 0.0_wp ) THEN 6771 6707 binary_case = 1 6772 IF ( RH > 0.1_wp .AND. RH< 0.98 ) THEN6708 IF ( rh > 0.1_wp .AND. rh < 0.98 ) THEN 6773 6709 IF ( binary_case == 1 ) THEN 6774 binary_hcl = - 5.0179_wp * ( RH**3 ) + 9.8816_wp * ( RH**2 ) - & 6775 10.789_wp * RH + 5.4737_wp 6710 binary_hcl = - 5.0179_wp * rh**3 + 9.8816_wp * rh**2 - 10.789_wp * rh + 5.4737_wp 6776 6711 ELSEIF ( binary_case == 2 ) THEN 6777 binary_hcl = - 4.6221_wp * RH+ 4.2633_wp6712 binary_hcl = - 4.6221_wp * rh + 4.2633_wp 6778 6713 ENDIF 6779 ELSEIF ( RH >= 0.98_wp .AND. RH< 0.9999_wp ) THEN6780 binary_hcl = 775.6111008626_wp * ( RH**3 ) - 2146.01320888771_wp *&6781 ( RH**2 ) + 1969.01979670259_wp * RH- 598.878230033926_wp6714 ELSEIF ( rh >= 0.98_wp .AND. rh < 0.9999_wp ) THEN 6715 binary_hcl = 775.6111008626_wp * rh**3 - 2146.01320888771_wp * rh**2 + & 6716 1969.01979670259_wp * rh - 598.878230033926_wp 6782 6717 ENDIF 6783 6718 ENDIF 6784 6719 6785 6720 IF ( nitric_acid > 0.0_wp ) THEN ! HNO3 6786 IF ( full_complexity == 1 .OR. RH<= 0.4_wp ) THEN6787 HNO3_hcl = 9.6256_wp * ( RH**4 ) - 26.507_wp * ( RH**3 ) +&6788 2 7.622_wp * ( RH**2 ) - 12.958_wp * RH + 2.2193_wp6789 ELSEIF ( full_complexity == 0 .AND. RH> 0.4_wp ) THEN6790 HNO3_hcl = 1.3242_wp * ( RH**2 ) - 1.8827_wp * RH+ 0.55706_wp6721 IF ( full_complexity == 1 .OR. rh <= 0.4_wp ) THEN 6722 hno3_hcl = 9.6256_wp * rh**4 - 26.507_wp * rh**3 + 27.622_wp * rh**2 - 12.958_wp * rh + & 6723 2.2193_wp 6724 ELSEIF ( full_complexity == 0 .AND. rh > 0.4_wp ) THEN 6725 hno3_hcl = 1.3242_wp * rh**2 - 1.8827_wp * rh + 0.55706_wp 6791 6726 ENDIF 6792 6727 ENDIF 6793 6728 6794 6729 IF ( sulphuric_acid > 0.0_wp ) THEN ! H2SO4 6795 IF ( full_complexity == 1 .OR. RH <= 0.4 ) THEN 6796 H2SO4_hcl = 1.4406_wp * ( RH**3 ) - 2.7132_wp * ( RH**2 ) + & 6797 1.014_wp * RH + 0.25226_wp 6798 ELSEIF ( full_complexity == 0 .AND. RH > 0.4_wp ) THEN 6799 H2SO4_hcl = 0.30993_wp * ( RH**2 ) - 0.99171_wp * RH + 0.66913_wp 6730 IF ( full_complexity == 1 .OR. rh <= 0.4 ) THEN 6731 h2so4_hcl = 1.4406_wp * rh**3 - 2.7132_wp * rh**2 + 1.014_wp * rh + 0.25226_wp 6732 ELSEIF ( full_complexity == 0 .AND. rh > 0.4_wp ) THEN 6733 h2so4_hcl = 0.30993_wp * rh**2 - 0.99171_wp * rh + 0.66913_wp 6800 6734 ENDIF 6801 6735 ENDIF 6802 6736 6803 6737 IF ( ammonium_sulphate > 0.0_wp ) THEN ! NH42SO4 6804 NH42SO4_hcl = 22.071_wp * ( RH**3 ) - 40.678_wp * ( RH**2 ) + & 6805 27.893_wp * RH - 9.4338_wp 6738 nh42so4_hcl = 22.071_wp * rh**3 - 40.678_wp * rh**2 + 27.893_wp * rh - 9.4338_wp 6806 6739 ENDIF 6807 6740 6808 6741 IF ( ammonium_nitrate > 0.0_wp ) THEN ! NH4NO3 6809 NH4NO3_hcl = 19.935_wp * ( RH**3 ) - 42.335_wp * ( RH**2 ) + & 6810 31.275_wp * RH - 8.8675_wp 6742 nh4no3_hcl = 19.935_wp * rh**3 - 42.335_wp * rh**2 + 31.275_wp * rh - 8.8675_wp 6811 6743 ENDIF 6812 6744 6813 6745 IF ( ammonium_chloride > 0.0_wp ) THEN ! NH4Cl 6814 IF ( full_complexity == 1 .OR. RH <= 0.4_wp ) THEN 6815 NH4Cl_hcl = 2.8048_wp * ( RH**3 ) - 4.3182_wp * ( RH**2 ) + & 6816 3.1971_wp * RH - 1.6824_wp 6817 ELSEIF ( full_complexity == 0 .AND. RH > 0.4_wp ) THEN 6818 NH4Cl_hcl = 1.2304_wp * ( RH**2 ) - 0.18262_wp * RH - 1.0643_wp 6746 IF ( full_complexity == 1 .OR. rh <= 0.4_wp ) THEN 6747 nh4cl_hcl = 2.8048_wp * rh**3 - 4.3182_wp * rh**2 + 3.1971_wp * rh - 1.6824_wp 6748 ELSEIF ( full_complexity == 0 .AND. rh > 0.4_wp ) THEN 6749 nh4cl_hcl = 1.2304_wp * rh**2 - 0.18262_wp * rh - 1.0643_wp 6819 6750 ENDIF 6820 6751 ENDIF 6821 6752 6822 6753 IF ( sodium_sulphate > 0.0_wp ) THEN ! Na2SO4 6823 Na2SO4_hcl = 36.104_wp * ( RH**4 ) - 78.658_wp * ( RH**3 ) +&6824 63.441_wp * ( RH**2 ) - 26.727_wp * RH +5.7007_wp6754 na2so4_hcl = 36.104_wp * rh**4 - 78.658_wp * rh**3 + 63.441_wp * rh**2 - 26.727_wp * rh + & 6755 5.7007_wp 6825 6756 ENDIF 6826 6757 6827 6758 IF ( sodium_nitrate > 0.0_wp ) THEN ! NaNO3 6828 IF ( full_complexity == 1 .OR. RH <= 0.4_wp ) THEN 6829 NaNO3_hcl = 54.471_wp * ( RH**5 ) - 159.42_wp * ( RH**4 ) + & 6830 180.25_wp * ( RH**3 ) - 98.176_wp * ( RH**2 ) + & 6831 25.309_wp * RH - 2.4275_wp 6832 ELSEIF ( full_complexity == 0 .AND. RH > 0.4_wp ) THEN 6833 NaNO3_hcl = 21.632_wp * ( RH**4 ) - 53.088_wp * ( RH**3 ) + & 6834 47.285_wp * ( RH**2 ) - 18.519_wp * RH + 2.6846_wp 6759 IF ( full_complexity == 1 .OR. rh <= 0.4_wp ) THEN 6760 nano3_hcl = 54.471_wp * rh**5 - 159.42_wp * rh**4 + 180.25_wp * rh**3 - 98.176_wp * rh**2& 6761 + 25.309_wp * rh - 2.4275_wp 6762 ELSEIF ( full_complexity == 0 .AND. rh > 0.4_wp ) THEN 6763 nano3_hcl = 21.632_wp * rh**4 - 53.088_wp * rh**3 + 47.285_wp * rh**2 - 18.519_wp * rh & 6764 + 2.6846_wp 6835 6765 ENDIF 6836 6766 ENDIF 6837 6767 6838 6768 IF ( sodium_chloride > 0.0_wp ) THEN ! NaCl 6839 IF ( full_complexity == 1 .OR. RH <= 0.4_wp ) THEN 6840 NaCl_hcl = 5.4138_wp * ( RH**4 ) - 12.079_wp * ( RH**3 ) + & 6841 9.627_wp * ( RH**2 ) - 3.3164_wp * RH + 0.35224_wp 6842 ELSEIF ( full_complexity == 0 .AND. RH > 0.4_wp ) THEN 6843 NaCl_hcl = 2.432_wp * ( RH**3 ) - 4.3453_wp * ( RH**2 ) + & 6844 2.3834_wp * RH - 0.4762_wp 6769 IF ( full_complexity == 1 .OR. rh <= 0.4_wp ) THEN 6770 nacl_hcl = 5.4138_wp * rh**4 - 12.079_wp * rh**3 + 9.627_wp * rh**2 - 3.3164_wp * rh + & 6771 0.35224_wp 6772 ELSEIF ( full_complexity == 0 .AND. rh > 0.4_wp ) THEN 6773 nacl_hcl = 2.432_wp * rh**3 - 4.3453_wp * rh**2 + 2.3834_wp * rh - 0.4762_wp 6845 6774 ENDIF 6846 6775 ENDIF 6847 6848 Ln_HCL_act = binary_hcl + & 6849 nitric_acid_eq_frac * HNO3_hcl + & 6850 sulphuric_acid_eq_frac * H2SO4_hcl + & 6851 ammonium_sulphate_eq_frac * NH42SO4_hcl + & 6852 ammonium_nitrate_eq_frac * NH4NO3_hcl + & 6853 ammonium_chloride_eq_frac * NH4Cl_hcl + & 6854 sodium_sulphate_eq_frac * Na2SO4_hcl + & 6855 sodium_nitrate_eq_frac * NaNO3_hcl + & 6856 sodium_chloride_eq_frac * NaCl_hcl 6857 6858 gamma_hcl = EXP( Ln_HCL_act ) ! Molal activity coefficient 6776 6777 ln_HCL_act = binary_hcl + nitric_acid_eq_frac * hno3_hcl + sulphuric_acid_eq_frac * h2so4_hcl +& 6778 ammonium_sulphate_eq_frac * nh42so4_hcl + ammonium_nitrate_eq_frac * nh4no3_hcl + & 6779 ammonium_chloride_eq_frac * nh4cl_hcl + sodium_sulphate_eq_frac * na2so4_hcl + & 6780 sodium_nitrate_eq_frac * nano3_hcl + sodium_chloride_eq_frac * nacl_hcl 6781 6782 gamma_hcl = EXP( ln_HCL_act ) ! Molal activity coefficient 6859 6783 gamma_out(2) = gamma_hcl 6860 ! 6784 ! 6861 6785 !-- Equilibrium constant after Wagman et al. (1982) (and NIST database) 6862 K_hcl = 2E6_wp * EXP( 9000.0_wp * henrys_temp_dep )6863 6864 Press_HCL = ( ions_mol(1) * ions_mol(7) * ( gamma_hcl**2 ) ) / K_hcl6786 k_hcl = 2E6_wp * EXP( 9000.0_wp * henrys_temp_dep ) 6787 6788 press_hcl = ( ions_mol(1) * ions_mol(7) * gamma_hcl**2 ) / k_hcl 6865 6789 ! 6866 6790 !-- 5) Ion molility output 6867 6791 mols_out = ions_mol 6868 ! 6869 !-- REFERENCES 6870 !-- Clegg et al. (1998) A Thermodynamic Model of the System 6871 !-- H+-NH4+-Na+-SO42- -NO3--Cl--H2O at 298.15 K, J. Phys. Chem., 102A, 6872 !-- 2155-2171. 6873 !-- Clegg et al. (2001) Thermodynamic modelling of aqueous aerosols containing 6874 !-- electrolytes and dissolved organic compounds. Journal of Aerosol Science 6875 !-- 2001;32(6):713-738. 6876 !-- Topping et al. (2005a) A curved multi-component aerosol hygroscopicity model 6877 !-- framework: Part 1 - Inorganic compounds. Atmospheric Chemistry and 6878 !-- Physics 2005;5:1205-1222. 6879 !-- Topping et al. (2005b) A curved multi-component aerosol hygroscopicity model 6880 !-- framework: Part 2 - Including organic compounds. Atmospheric Chemistry 6881 !-- and Physics 2005;5:1223-1242. 6882 !-- Wagman et al. (1982). The NBS tables of chemical thermodynamic properties: 6883 !-- selected values for inorganic and Câ and Câ organic substances in SI 6884 !-- units (book) 6885 !-- Zaveri et al. (2005). A new method for multicomponent activity coefficients 6886 !-- of electrolytes in aqueous atmospheric aerosols, JGR, 110, D02201, 2005. 6792 6887 6793 END SUBROUTINE inorganic_pdfite 6888 6794 6889 6795 !------------------------------------------------------------------------------! 6890 6796 ! Description: … … 6899 6805 ! 6900 6806 !> Moving-centre method minimises numerical diffusion. 6901 !------------------------------------------------------------------------------! 6807 !------------------------------------------------------------------------------! 6902 6808 SUBROUTINE distr_update( paero ) 6903 6809 6904 6810 IMPLICIT NONE 6905 6811 6906 !-- Input and output variables 6907 TYPE(t_section), INTENT(inout) :: paero(fn2b) !< Aerosols particle 6908 !< size distribution and properties 6909 !-- Local variables 6910 INTEGER(iwp) :: b !< loop index 6911 INTEGER(iwp) :: mm !< loop index 6912 INTEGER(iwp) :: counti 6913 LOGICAL :: within_bins !< logical (particle belongs to the bin?) 6914 REAL(wp) :: znfrac !< number fraction to be moved to the larger bin 6915 REAL(wp) :: zvfrac !< volume fraction to be moved to the larger bin 6916 REAL(wp) :: zVexc !< Volume in the grown bin which exceeds the bin 6917 !< upper limit 6918 REAL(wp) :: zVihi !< particle volume at the high end of the bin 6919 REAL(wp) :: zVilo !< particle volume at the low end of the bin 6920 REAL(wp) :: zvpart !< particle volume (m3) 6921 REAL(wp) :: zVrat !< volume ratio of a size bin 6922 6923 zvpart = 0.0_wp 6924 zvfrac = 0.0_wp 6925 6812 INTEGER(iwp) :: ib !< loop index 6813 INTEGER(iwp) :: mm !< loop index 6814 INTEGER(iwp) :: counti !< number of while loops 6815 6816 LOGICAL :: within_bins !< logical (particle belongs to the bin?) 6817 6818 REAL(wp) :: znfrac !< number fraction to be moved to the larger bin 6819 REAL(wp) :: zvfrac !< volume fraction to be moved to the larger bin 6820 REAL(wp) :: zVexc !< Volume in the grown bin which exceeds the bin upper limit 6821 REAL(wp) :: zVihi !< particle volume at the high end of the bin 6822 REAL(wp) :: zVilo !< particle volume at the low end of the bin 6823 REAL(wp) :: zvpart !< particle volume (m3) 6824 REAL(wp) :: zVrat !< volume ratio of a size bin 6825 6826 TYPE(t_section), DIMENSION(nbins_aerosol), INTENT(inout) :: paero !< aerosol properties 6827 6828 zvpart = 0.0_wp 6829 zvfrac = 0.0_wp 6926 6830 within_bins = .FALSE. 6927 6928 6831 ! 6929 6832 !-- Check if the volume of the bin is within bin limits after update … … 6931 6834 DO WHILE ( .NOT. within_bins ) 6932 6835 within_bins = .TRUE. 6933 6934 DO b = fn2b-1, in1a, -1 6836 ! 6837 !-- Loop from larger to smaller size bins 6838 DO ib = end_subrange_2b-1, start_subrange_1a, -1 6935 6839 mm = 0 6936 IF ( paero(b)%numc > nclim ) THEN 6937 6840 IF ( paero(ib)%numc > nclim ) THEN 6938 6841 zvpart = 0.0_wp 6939 6842 zvfrac = 0.0_wp 6940 6843 6941 IF ( b == fn2a ) CYCLE6844 IF ( ib == end_subrange_2a ) CYCLE 6942 6845 ! 6943 6846 !-- Dry volume 6944 zvpart = SUM( paero( b)%volc(1:7) ) / paero(b)%numc6847 zvpart = SUM( paero(ib)%volc(1:7) ) / paero(ib)%numc 6945 6848 ! 6946 6849 !-- Smallest bin cannot decrease 6947 IF ( paero( b)%vlolim > zvpart .AND. b == in1a ) CYCLE6850 IF ( paero(ib)%vlolim > zvpart .AND. ib == start_subrange_1a ) CYCLE 6948 6851 ! 6949 6852 !-- Decreasing bins 6950 IF ( paero( b)%vlolim > zvpart ) THEN6951 mm = b - 16952 IF ( b == in2b ) mm = fn1a ! 2b goes to 1a6953 6954 paero(mm)%numc = paero(mm)%numc + paero( b)%numc6955 paero( b)%numc = 0.0_wp6956 paero(mm)%volc(:) = paero(mm)%volc(:) + paero( b)%volc(:)6957 paero( b)%volc(:) = 0.0_wp6853 IF ( paero(ib)%vlolim > zvpart ) THEN 6854 mm = ib - 1 6855 IF ( ib == start_subrange_2b ) mm = end_subrange_1a ! 2b goes to 1a 6856 6857 paero(mm)%numc = paero(mm)%numc + paero(ib)%numc 6858 paero(ib)%numc = 0.0_wp 6859 paero(mm)%volc(:) = paero(mm)%volc(:) + paero(ib)%volc(:) 6860 paero(ib)%volc(:) = 0.0_wp 6958 6861 CYCLE 6959 6862 ENDIF 6960 6863 ! 6961 !-- If size bin has not grown, cycle 6962 !-- Changed by Mona: compare to the arithmetic mean volume, as done 6963 !-- originally. Now particle volume is derived from the geometric mean 6964 !-- diameter, not arithmetic (see SUBROUTINE set_sizebins). 6965 IF ( zvpart <= api6 * ( ( aero(b)%vhilim + aero(b)%vlolim ) / & 6966 ( 2.0_wp * api6 ) ) ) CYCLE 6967 IF ( ABS( zvpart - api6 * paero(b)%dmid ** 3.0_wp ) < & 6968 1.0E-35_wp ) CYCLE ! Mona: to avoid precision problems 6969 ! 6864 !-- If size bin has not grown, cycle. 6865 !-- Changed by Mona: compare to the arithmetic mean volume, as done originally. Now 6866 !-- particle volume is derived from the geometric mean diameter, not arithmetic (see 6867 !-- SUBROUTINE set_sizebins). 6868 IF ( zvpart <= api6 * ( ( aero(ib)%vhilim + aero(ib)%vlolim ) / ( 2.0_wp * api6 ) ) ) & 6869 CYCLE 6870 ! 6871 !-- Avoid precision problems 6872 IF ( ABS( zvpart - api6 * paero(ib)%dmid**3 ) < 1.0E-35_wp ) CYCLE 6873 ! 6970 6874 !-- Volume ratio of the size bin 6971 zVrat = paero(b)%vhilim / paero(b)%vlolim 6875 zVrat = paero(ib)%vhilim / paero(ib)%vlolim 6876 ! 6972 6877 !-- Particle volume at the low end of the bin 6973 6878 zVilo = 2.0_wp * zvpart / ( 1.0_wp + zVrat ) 6879 ! 6974 6880 !-- Particle volume at the high end of the bin 6975 6881 zVihi = zVrat * zVilo 6882 ! 6976 6883 !-- Volume in the grown bin which exceeds the bin upper limit 6977 zVexc = 0.5_wp * ( zVihi + paero(b)%vhilim ) 6884 zVexc = 0.5_wp * ( zVihi + paero(ib)%vhilim ) 6885 ! 6978 6886 !-- Number fraction to be moved to the larger bin 6979 znfrac = MIN( 1.0_wp, ( zVihi - paero( b)%vhilim) / &6980 ( zVihi - zVilo ) ) 6887 znfrac = MIN( 1.0_wp, ( zVihi - paero(ib)%vhilim) / ( zVihi - zVilo ) ) 6888 ! 6981 6889 !-- Volume fraction to be moved to the larger bin 6982 6890 zvfrac = MIN( 0.99_wp, znfrac * zVexc / zvpart ) 6983 6891 IF ( zvfrac < 0.0_wp ) THEN 6984 6892 message_string = 'Error: zvfrac < 0' 6985 CALL message( 'salsa_mod: distr_update', 'SA0050', & 6986 1, 2, 0, 6, 0 ) 6893 CALL message( 'salsa_mod: distr_update', 'PA0624', 1, 2, 0, 6, 0 ) 6987 6894 ENDIF 6988 6895 ! 6989 6896 !-- Update bin 6990 mm = b + 1 6897 mm = ib + 1 6898 ! 6991 6899 !-- Volume (cm3/cm3) 6992 paero(mm)%volc(:) = paero(mm)%volc(:) + znfrac * paero(b)%numc * & 6993 zVexc * paero(b)%volc(:) / & 6994 SUM( paero(b)%volc(1:7) ) 6995 paero(b)%volc(:) = paero(b)%volc(:) - znfrac * paero(b)%numc * & 6996 zVexc * paero(b)%volc(:) / & 6997 SUM( paero(b)%volc(1:7) ) 6900 paero(mm)%volc(:) = paero(mm)%volc(:) + znfrac * paero(ib)%numc * zVexc * & 6901 paero(ib)%volc(:) / SUM( paero(ib)%volc(:) ) 6902 paero(ib)%volc(:) = paero(ib)%volc(:) - znfrac * paero(ib)%numc * zVexc * & 6903 paero(ib)%volc(:) / SUM( paero(ib)%volc(:) ) 6998 6904 6999 6905 !-- Number concentration (#/m3) 7000 paero(mm)%numc = paero(mm)%numc + znfrac * paero( b)%numc7001 paero( b)%numc = paero(b)%numc * ( 1.0_wp - znfrac )6906 paero(mm)%numc = paero(mm)%numc + znfrac * paero(ib)%numc 6907 paero(ib)%numc = paero(ib)%numc * ( 1.0_wp - znfrac ) 7002 6908 7003 6909 ENDIF ! nclim 7004 7005 IF ( paero(b)%numc > nclim ) THEN 7006 zvpart = SUM( paero(b)%volc(1:7) ) / paero(b)%numc 7007 within_bins = ( paero(b)%vlolim < zvpart .AND. & 7008 zvpart < paero(b)%vhilim ) 6910 6911 IF ( paero(ib)%numc > nclim ) THEN 6912 zvpart = SUM( paero(ib)%volc(:) ) / paero(ib)%numc 6913 within_bins = ( paero(ib)%vlolim < zvpart .AND. zvpart < paero(ib)%vhilim ) 7009 6914 ENDIF 7010 6915 7011 ENDDO ! - b6916 ENDDO ! - ib 7012 6917 7013 6918 counti = counti + 1 7014 6919 IF ( counti > 100 ) THEN 7015 6920 message_string = 'Error: Aerosol bin update not converged' 7016 CALL message( 'salsa_mod: distr_update', ' SA0051', 1, 2, 0, 6, 0 )7017 ENDIF 6921 CALL message( 'salsa_mod: distr_update', 'PA0625', 1, 2, 0, 6, 0 ) 6922 ENDIF 7018 6923 7019 6924 ENDDO ! - within bins 7020 6925 7021 6926 END SUBROUTINE distr_update 7022 6927 7023 6928 !------------------------------------------------------------------------------! 7024 6929 ! Description: … … 7030 6935 !------------------------------------------------------------------------------! 7031 6936 SUBROUTINE salsa_diagnostics( i, j ) 7032 6937 7033 6938 USE cpulog, & 7034 6939 ONLY: cpu_log, log_point_s 7035 6940 7036 6941 IMPLICIT NONE 7037 6942 6943 INTEGER(iwp) :: ib !< 6944 INTEGER(iwp) :: ic !< 6945 INTEGER(iwp) :: icc !< 6946 INTEGER(iwp) :: ig !< 6947 INTEGER(iwp) :: k !< 6948 7038 6949 INTEGER(iwp), INTENT(in) :: i !< 7039 INTEGER(iwp), INTENT(in) :: j !< 7040 7041 INTEGER(iwp) :: b !< 7042 INTEGER(iwp) :: c !< 7043 INTEGER(iwp) :: gt !< 7044 INTEGER(iwp) :: k !< 7045 INTEGER(iwp) :: nc !< 7046 REAL(wp), DIMENSION(nzb:nzt+1) :: flag !< flag to mask topography 7047 REAL(wp), DIMENSION(nzb:nzt+1) :: flag_zddry !< flag to mask zddry 7048 REAL(wp), DIMENSION(nzb:nzt+1) :: in_adn !< air density (kg/m3) 7049 REAL(wp), DIMENSION(nzb:nzt+1) :: in_p !< pressure 7050 REAL(wp), DIMENSION(nzb:nzt+1) :: in_t !< temperature (K) 7051 REAL(wp), DIMENSION(nzb:nzt+1) :: mcsum !< sum of mass concentration 7052 REAL(wp), DIMENSION(nzb:nzt+1) :: ppm_to_nconc !< Conversion factor 7053 !< from ppm to #/m3 7054 REAL(wp), DIMENSION(nzb:nzt+1) :: zddry !< 7055 REAL(wp), DIMENSION(nzb:nzt+1) :: zvol !< 7056 6950 INTEGER(iwp), INTENT(in) :: j !< 6951 6952 REAL(wp), DIMENSION(nzb:nzt+1) :: flag !< flag to mask topography 6953 REAL(wp), DIMENSION(nzb:nzt+1) :: flag_zddry !< flag to mask zddry 6954 REAL(wp), DIMENSION(nzb:nzt+1) :: in_adn !< air density (kg/m3) 6955 REAL(wp), DIMENSION(nzb:nzt+1) :: in_p !< pressure 6956 REAL(wp), DIMENSION(nzb:nzt+1) :: in_t !< temperature (K) 6957 REAL(wp), DIMENSION(nzb:nzt+1) :: mcsum !< sum of mass concentration 6958 REAL(wp), DIMENSION(nzb:nzt+1) :: ppm_to_nconc !< Conversion factor: ppm to #/m3 6959 REAL(wp), DIMENSION(nzb:nzt+1) :: zddry !< particle dry diameter 6960 REAL(wp), DIMENSION(nzb:nzt+1) :: zvol !< particle volume 6961 7057 6962 flag_zddry = 0.0_wp 7058 6963 in_adn = 0.0_wp … … 7062 6967 zddry = 0.0_wp 7063 6968 zvol = 0.0_wp 7064 6969 7065 6970 CALL cpu_log( log_point_s(94), 'salsa diagnostics ', 'start' ) 7066 7067 ! 6971 ! 7068 6972 !-- Calculate thermodynamic quantities needed in SALSA 7069 CALL salsa_thrm_ij( i, j, p_ij=in_p, temp_ij=in_t, adn_ij=in_adn ) 6973 CALL salsa_thrm_ij( i, j, p_ij=in_p, temp_ij=in_t, adn_ij=in_adn ) 7070 6974 ! 7071 6975 !-- Calculate conversion factors for gas concentrations … … 7073 6977 ! 7074 6978 !-- Predetermine flag to mask topography 7075 flag = MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(:,j,i), 0 ) ) 7076 7077 DO b = 1, nbins ! aerosol size bins 7078 ! 7079 !-- Remove negative values 7080 aerosol_number(b)%conc(:,j,i) = MAX( nclim, & 7081 aerosol_number(b)%conc(:,j,i) ) * flag 7082 mcsum = 0.0_wp ! total mass concentration 7083 DO c = 1, ncc_tot 7084 ! 7085 !-- Remove negative concentrations 7086 aerosol_mass((c-1)*nbins+b)%conc(:,j,i) = MAX( mclim, & 7087 aerosol_mass((c-1)*nbins+b)%conc(:,j,i) ) & 7088 * flag 7089 mcsum = mcsum + aerosol_mass((c-1)*nbins+b)%conc(:,j,i) * flag 7090 ENDDO 7091 ! 7092 !-- Check that number and mass concentration match qualitatively 7093 IF ( ANY ( aerosol_number(b)%conc(:,j,i) > nclim .AND. & 7094 mcsum <= 0.0_wp ) ) & 7095 THEN 6979 flag = MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(:,j,i), 0 ) ) 6980 6981 DO ib = 1, nbins_aerosol ! aerosol size bins 6982 ! 6983 !-- Remove negative values 6984 aerosol_number(ib)%conc(:,j,i) = MAX( nclim, aerosol_number(ib)%conc(:,j,i) ) * flag 6985 ! 6986 !-- Calculate total mass concentration per bin 6987 mcsum = 0.0_wp 6988 DO ic = 1, ncomponents_mass 6989 icc = ( ic - 1 ) * nbins_aerosol + ib 6990 mcsum = mcsum + aerosol_mass(icc)%conc(:,j,i) * flag 6991 ENDDO 6992 ! 6993 !-- Check that number and mass concentration match qualitatively 6994 IF ( ANY ( aerosol_number(ib)%conc(:,j,i) > nclim .AND. mcsum <= 0.0_wp ) ) THEN 7096 6995 DO k = nzb+1, nzt 7097 IF ( aerosol_number(b)%conc(k,j,i) > nclim .AND. & 7098 mcsum(k) <= 0.0_wp ) & 7099 THEN 7100 aerosol_number(b)%conc(k,j,i) = nclim * flag(k) 7101 DO c = 1, ncc_tot 7102 aerosol_mass((c-1)*nbins+b)%conc(k,j,i) = mclim * flag(k) 6996 IF ( aerosol_number(ib)%conc(k,j,i) > nclim .AND. mcsum(k) <= 0.0_wp ) THEN 6997 aerosol_number(ib)%conc(k,j,i) = nclim * flag(k) 6998 DO ic = 1, ncomponents_mass 6999 icc = ( ic - 1 ) * nbins_aerosol + ib 7000 aerosol_mass(icc)%conc(k,j,i) = mclim * flag(k) 7103 7001 ENDDO 7104 7002 ENDIF 7105 7003 ENDDO 7106 7004 ENDIF 7107 ! 7005 ! 7108 7006 !-- Update aerosol particle radius 7109 CALL bin_mixrat( 'dry', b, i, j, zvol )7007 CALL bin_mixrat( 'dry', ib, i, j, zvol ) 7110 7008 zvol = zvol / arhoh2so4 ! Why on sulphate? 7111 ! 7112 !-- Particles smaller then 0.1 nm diameter are set to zero 7113 zddry = ( zvol / MAX( nclim, aerosol_number(b)%conc(:,j,i) ) / api6 )** & 7114 ( 1.0_wp / 3.0_wp ) 7115 flag_zddry = MERGE( 1.0_wp, 0.0_wp, ( zddry < 1.0E-10_wp .AND. & 7116 aerosol_number(b)%conc(:,j,i) > nclim ) ) 7117 ! 7009 ! 7010 !-- Particles smaller then 0.1 nm diameter are set to zero 7011 zddry = ( zvol / MAX( nclim, aerosol_number(ib)%conc(:,j,i) ) / api6 )**0.33333333_wp 7012 flag_zddry = MERGE( 1.0_wp, 0.0_wp, ( zddry < 1.0E-10_wp .AND. & 7013 aerosol_number(ib)%conc(:,j,i) > nclim ) ) 7014 ! 7118 7015 !-- Volatile species to the gas phase 7119 IF ( is_used( prtcl, 'SO4' ) .AND. lscndgas ) THEN 7120 nc = get_index( prtcl, 'SO4' ) 7121 c = ( nc - 1 ) * nbins + b 7016 IF ( index_so4 > 0 .AND. lscndgas ) THEN 7017 ic = ( index_so4 - 1 ) * nbins_aerosol + ib 7122 7018 IF ( salsa_gases_from_chem ) THEN 7123 chem_species( gas_index_chem(1) )%conc(:,j,i) = &7124 chem_species( gas_index_chem(1) )%conc(:,j,i) +&7125 aerosol_mass(c)%conc(:,j,i) * avo * flag *&7126 flag_zddry / ( amh2so4 * ppm_to_nconc )7019 ig = gas_index_chem(1) 7020 chem_species(ig)%conc(:,j,i) = chem_species(ig)%conc(:,j,i) + & 7021 aerosol_mass(ic)%conc(:,j,i) * avo * flag_zddry / & 7022 ( amh2so4 * ppm_to_nconc ) * flag 7127 7023 ELSE 7128 salsa_gas(1)%conc(:,j,i) = salsa_gas(1)%conc(:,j,i) + & 7129 aerosol_mass(c)%conc(:,j,i) / amh2so4 *& 7130 avo * flag * flag_zddry 7024 salsa_gas(1)%conc(:,j,i) = salsa_gas(1)%conc(:,j,i) + aerosol_mass(ic)%conc(:,j,i) / & 7025 amh2so4 * avo * flag_zddry * flag 7131 7026 ENDIF 7132 7027 ENDIF 7133 IF ( is_used( prtcl, 'OC' ) .AND. lscndgas ) THEN 7134 nc = get_index( prtcl, 'OC' ) 7135 c = ( nc - 1 ) * nbins + b 7028 IF ( index_oc > 0 .AND. lscndgas ) THEN 7029 ic = ( index_oc - 1 ) * nbins_aerosol + ib 7136 7030 IF ( salsa_gases_from_chem ) THEN 7137 chem_species( gas_index_chem(5) )%conc(:,j,i) = & 7138 chem_species( gas_index_chem(5) )%conc(:,j,i) + & 7139 aerosol_mass(c)%conc(:,j,i) * avo * flag * & 7140 flag_zddry / ( amoc * ppm_to_nconc ) 7141 ELSE 7142 salsa_gas(5)%conc(:,j,i) = salsa_gas(5)%conc(:,j,i) + & 7143 aerosol_mass(c)%conc(:,j,i) / amoc * & 7144 avo * flag * flag_zddry 7031 ig = gas_index_chem(5) 7032 chem_species(ig)%conc(:,j,i) = chem_species(ig)%conc(:,j,i) + & 7033 aerosol_mass(ic)%conc(:,j,i) * avo * flag_zddry / & 7034 ( amoc * ppm_to_nconc ) * flag 7035 ELSE 7036 salsa_gas(5)%conc(:,j,i) = salsa_gas(5)%conc(:,j,i) + aerosol_mass(ic)%conc(:,j,i) / & 7037 amoc * avo * flag_zddry * flag 7145 7038 ENDIF 7146 7039 ENDIF 7147 IF ( is_used( prtcl, 'NO' ) .AND. lscndgas ) THEN 7148 nc = get_index( prtcl, 'NO' ) 7149 c = ( nc - 1 ) * nbins + b 7040 IF ( index_no > 0 .AND. lscndgas ) THEN 7041 ic = ( index_no - 1 ) * nbins_aerosol + ib 7150 7042 IF ( salsa_gases_from_chem ) THEN 7151 chem_species( gas_index_chem(2) )%conc(:,j,i) = &7152 chem_species( gas_index_chem(2) )%conc(:,j,i) +&7153 aerosol_mass(c)%conc(:,j,i) * avo * flag *&7154 flag_zddry / ( amhno3 * ppm_to_nconc )7043 ig = gas_index_chem(2) 7044 chem_species(ig)%conc(:,j,i) = chem_species(ig)%conc(:,j,i) + & 7045 aerosol_mass(ic)%conc(:,j,i) * avo * flag_zddry / & 7046 ( amhno3 * ppm_to_nconc ) *flag 7155 7047 ELSE 7156 salsa_gas(2)%conc(:,j,i) = salsa_gas(2)%conc(:,j,i) + & 7157 aerosol_mass(c)%conc(:,j,i) / amhno3 * & 7158 avo * flag * flag_zddry 7048 salsa_gas(2)%conc(:,j,i) = salsa_gas(2)%conc(:,j,i) + aerosol_mass(ic)%conc(:,j,i) / & 7049 amhno3 * avo * flag_zddry * flag 7159 7050 ENDIF 7160 7051 ENDIF 7161 IF ( is_used( prtcl, 'NH' ) .AND. lscndgas ) THEN 7162 nc = get_index( prtcl, 'NH' ) 7163 c = ( nc - 1 ) * nbins + b 7052 IF ( index_nh > 0 .AND. lscndgas ) THEN 7053 ic = ( index_nh - 1 ) * nbins_aerosol + ib 7164 7054 IF ( salsa_gases_from_chem ) THEN 7165 chem_species( gas_index_chem(3) )%conc(:,j,i) = &7166 chem_species( gas_index_chem(3) )%conc(:,j,i) +&7167 aerosol_mass(c)%conc(:,j,i) * avo * flag *&7168 flag_zddry / ( amnh3 * ppm_to_nconc )7055 ig = gas_index_chem(3) 7056 chem_species(ig)%conc(:,j,i) = chem_species(ig)%conc(:,j,i) + & 7057 aerosol_mass(ic)%conc(:,j,i) * avo * flag_zddry / & 7058 ( amnh3 * ppm_to_nconc ) *flag 7169 7059 ELSE 7170 salsa_gas(3)%conc(:,j,i) = salsa_gas(3)%conc(:,j,i) + & 7171 aerosol_mass(c)%conc(:,j,i) / amnh3 * & 7172 avo * flag * flag_zddry 7060 salsa_gas(3)%conc(:,j,i) = salsa_gas(3)%conc(:,j,i) + aerosol_mass(ic)%conc(:,j,i) / & 7061 amnh3 * avo * flag_zddry *flag 7173 7062 ENDIF 7174 7063 ENDIF 7175 ! 7064 ! 7176 7065 !-- Mass and number to zero (insoluble species and water are lost) 7177 DO c = 1, ncc_tot7178 aerosol_mass((c-1)*nbins+b)%conc(:,j,i) = MERGE( mclim * flag, &7179 aerosol_mass((c-1)*nbins+b)%conc(:,j,i),&7180 flag_zddry > 0.0_wp )7066 DO ic = 1, ncomponents_mass 7067 icc = ( ic - 1 ) * nbins_aerosol + ib 7068 aerosol_mass(icc)%conc(:,j,i) = MERGE( mclim * flag, aerosol_mass(icc)%conc(:,j,i), & 7069 flag_zddry > 0.0_wp ) 7181 7070 ENDDO 7182 aerosol_number(b)%conc(:,j,i) = MERGE( nclim * flag, & 7183 aerosol_number(b)%conc(:,j,i), & 7184 flag_zddry > 0.0_wp ) 7185 Ra_dry(:,j,i,b) = MAX( 1.0E-10_wp, 0.5_wp * zddry ) 7186 7071 aerosol_number(ib)%conc(:,j,i) = MERGE( nclim, aerosol_number(ib)%conc(:,j,i), & 7072 flag_zddry > 0.0_wp ) 7073 ra_dry(:,j,i,ib) = MAX( 1.0E-10_wp, 0.5_wp * zddry ) 7074 7187 7075 ENDDO 7188 7076 IF ( .NOT. salsa_gases_from_chem ) THEN 7189 DO gt = 1, ngast 7190 salsa_gas(gt)%conc(:,j,i) = MAX( nclim, salsa_gas(gt)%conc(:,j,i) ) & 7191 * flag 7077 DO ig = 1, ngases_salsa 7078 salsa_gas(ig)%conc(:,j,i) = MAX( nclim, salsa_gas(ig)%conc(:,j,i) ) * flag 7192 7079 ENDDO 7193 7080 ENDIF 7194 7081 7195 7082 CALL cpu_log( log_point_s(94), 'salsa diagnostics ', 'stop' ) 7196 7083 7197 7084 END SUBROUTINE salsa_diagnostics 7198 7085 7199 7200 ! 7086 ! 7201 7087 !------------------------------------------------------------------------------! 7202 7088 ! Description: 7203 7089 ! ------------ 7204 !> Calculate the tendencies for aerosol number and mass concentrations. 7090 !> Calculate the prognostic equation for aerosol number and mass, and gas 7091 !> concentrations. Cache-optimized. 7092 !------------------------------------------------------------------------------! 7093 SUBROUTINE salsa_prognostic_equations_ij( i, j, i_omp_start, tn ) 7094 7095 USE control_parameters, & 7096 ONLY: time_since_reference_point 7097 7098 USE salsa_util_mod, & 7099 ONLY: sums_salsa_ws_l 7100 7101 IMPLICIT NONE 7102 7103 INTEGER(iwp) :: i !< 7104 INTEGER(iwp) :: i_omp_start !< 7105 INTEGER(iwp) :: ib !< loop index for aerosol number bin OR gas index 7106 INTEGER(iwp) :: ic !< loop index for aerosol mass bin 7107 INTEGER(iwp) :: icc !< (c-1)*nbins_aerosol+b 7108 INTEGER(iwp) :: ig !< loop index for salsa gases 7109 INTEGER(iwp) :: j !< 7110 INTEGER(iwp) :: tn !< 7111 7112 LOGICAL :: sedim !< calculate sedimentation only for aerosols (number and mass) 7113 7114 IF ( time_since_reference_point >= skip_time_do_salsa ) THEN 7115 ! 7116 !-- Aerosol number 7117 DO ib = 1, nbins_aerosol 7118 sums_salsa_ws_l = aerosol_number(ib)%sums_ws_l 7119 CALL salsa_tendency( 'aerosol_number', aerosol_number(ib)%conc_p, aerosol_number(ib)%conc,& 7120 aerosol_number(ib)%tconc_m, i, j, i_omp_start, tn, ib, ib, & 7121 aerosol_number(ib)%flux_s, aerosol_number(ib)%diss_s, & 7122 aerosol_number(ib)%flux_l, aerosol_number(ib)%diss_l, & 7123 aerosol_number(ib)%init, sedim ) 7124 aerosol_number(ib)%sums_ws_l = sums_salsa_ws_l 7125 ! 7126 !-- Aerosol mass 7127 DO ic = 1, ncomponents_mass 7128 icc = ( ic - 1 ) * nbins_aerosol + ib 7129 sums_salsa_ws_l = aerosol_mass(icc)%sums_ws_l 7130 CALL salsa_tendency( 'aerosol_mass', aerosol_mass(icc)%conc_p, aerosol_mass(icc)%conc,& 7131 aerosol_mass(icc)%tconc_m, i, j, i_omp_start, tn, ib, ic, & 7132 aerosol_mass(icc)%flux_s, aerosol_mass(icc)%diss_s, & 7133 aerosol_mass(icc)%flux_l, aerosol_mass(icc)%diss_l, & 7134 aerosol_mass(icc)%init, sedim ) 7135 aerosol_mass(icc)%sums_ws_l = sums_salsa_ws_l 7136 7137 ENDDO ! ic 7138 ENDDO ! ib 7139 ! 7140 !-- Gases 7141 IF ( .NOT. salsa_gases_from_chem ) THEN 7142 7143 DO ig = 1, ngases_salsa 7144 sums_salsa_ws_l = salsa_gas(ig)%sums_ws_l 7145 CALL salsa_tendency( 'salsa_gas', salsa_gas(ig)%conc_p, salsa_gas(ig)%conc, & 7146 salsa_gas(ig)%tconc_m, i, j, i_omp_start, tn, ig, ig, & 7147 salsa_gas(ig)%flux_s, salsa_gas(ig)%diss_s, salsa_gas(ig)%flux_l,& 7148 salsa_gas(ig)%diss_l, salsa_gas(ig)%init, sedim ) 7149 salsa_gas(ig)%sums_ws_l = sums_salsa_ws_l 7150 7151 ENDDO ! ig 7152 7153 ENDIF 7154 7155 ENDIF 7156 7157 END SUBROUTINE salsa_prognostic_equations_ij 7158 ! 7159 !------------------------------------------------------------------------------! 7160 ! Description: 7161 ! ------------ 7162 !> Calculate the prognostic equation for aerosol number and mass, and gas 7163 !> concentrations. Cache-optimized. 7164 !------------------------------------------------------------------------------! 7165 SUBROUTINE salsa_prognostic_equations() 7166 7167 USE control_parameters, & 7168 ONLY: time_since_reference_point 7169 7170 USE salsa_util_mod, & 7171 ONLY: sums_salsa_ws_l 7172 7173 IMPLICIT NONE 7174 7175 INTEGER(iwp) :: ib !< loop index for aerosol number bin OR gas index 7176 INTEGER(iwp) :: ic !< loop index for aerosol mass bin 7177 INTEGER(iwp) :: icc !< (c-1)*nbins_aerosol+b 7178 INTEGER(iwp) :: ig !< loop index for salsa gases 7179 7180 LOGICAL :: sedim !< calculate sedimentation only for aerosols (number and mass) 7181 7182 IF ( time_since_reference_point >= skip_time_do_salsa ) THEN 7183 ! 7184 !-- Aerosol number 7185 DO ib = 1, nbins_aerosol 7186 sums_salsa_ws_l = aerosol_number(ib)%sums_ws_l 7187 CALL salsa_tendency( 'aerosol_number', aerosol_number(ib)%conc_p, aerosol_number(ib)%conc,& 7188 aerosol_number(ib)%tconc_m, ib, ib, aerosol_number(ib)%init, sedim ) 7189 aerosol_number(ib)%sums_ws_l = sums_salsa_ws_l 7190 ! 7191 !-- Aerosol mass 7192 DO ic = 1, ncomponents_mass 7193 icc = ( ic - 1 ) * nbins_aerosol + ib 7194 sums_salsa_ws_l = aerosol_mass(icc)%sums_ws_l 7195 CALL salsa_tendency( 'aerosol_mass', aerosol_mass(icc)%conc_p, aerosol_mass(icc)%conc,& 7196 aerosol_mass(icc)%tconc_m, ib, ic, aerosol_mass(icc)%init, sedim ) 7197 aerosol_mass(icc)%sums_ws_l = sums_salsa_ws_l 7198 7199 ENDDO ! ic 7200 ENDDO ! ib 7201 ! 7202 !-- Gases 7203 IF ( .NOT. salsa_gases_from_chem ) THEN 7204 7205 DO ig = 1, ngases_salsa 7206 sums_salsa_ws_l = salsa_gas(ig)%sums_ws_l 7207 CALL salsa_tendency( 'salsa_gas', salsa_gas(ig)%conc_p, salsa_gas(ig)%conc, & 7208 salsa_gas(ig)%tconc_m, ig, ig, salsa_gas(ig)%init, sedim ) 7209 salsa_gas(ig)%sums_ws_l = sums_salsa_ws_l 7210 7211 ENDDO ! ig 7212 7213 ENDIF 7214 7215 ENDIF 7216 7217 END SUBROUTINE salsa_prognostic_equations 7218 ! 7219 !------------------------------------------------------------------------------! 7220 ! Description: 7221 ! ------------ 7222 !> Tendencies for aerosol number and mass and gas concentrations. 7205 7223 !> Cache-optimized. 7206 !------------------------------------------------------------------------------! 7207 SUBROUTINE salsa_tendency_ij( id, rs_p, rs, trs_m, i, j, i_omp_start, tn, b, & 7208 c, flux_s, diss_s, flux_l, diss_l, rs_init ) 7209 7210 USE advec_ws, & 7211 ONLY: advec_s_ws 7212 USE advec_s_pw_mod, & 7224 !------------------------------------------------------------------------------! 7225 SUBROUTINE salsa_tendency_ij( id, rs_p, rs, trs_m, i, j, i_omp_start, tn, ib, ic, flux_s, diss_s, & 7226 flux_l, diss_l, rs_init, do_sedimentation ) 7227 7228 USE advec_ws, & 7229 ONLY: advec_s_ws 7230 7231 USE advec_s_pw_mod, & 7213 7232 ONLY: advec_s_pw 7214 USE advec_s_up_mod, & 7233 7234 USE advec_s_up_mod, & 7215 7235 ONLY: advec_s_up 7216 USE arrays_3d, & 7236 7237 USE arrays_3d, & 7217 7238 ONLY: ddzu, rdf_sc, tend 7218 USE diffusion_s_mod, & 7239 7240 USE diffusion_s_mod, & 7219 7241 ONLY: diffusion_s 7220 USE indices, & 7242 7243 USE indices, & 7221 7244 ONLY: wall_flags_0 7222 USE pegrid, & 7245 7246 USE pegrid, & 7223 7247 ONLY: threads_per_task 7224 USE surface_mod, & 7225 ONLY : surf_def_h, surf_def_v, surf_lsm_h, surf_lsm_v, surf_usm_h,&7226 7227 7248 7249 USE surface_mod, & 7250 ONLY : surf_def_h, surf_def_v, surf_lsm_h, surf_lsm_v, surf_usm_h, surf_usm_v 7251 7228 7252 IMPLICIT NONE 7229 7230 CHARACTER (LEN = *) :: id 7231 INTEGER(iwp) :: b !< bin index in derived type aerosol_size_bin 7232 INTEGER(iwp) :: c !< bin index in derived type aerosol_size_bin 7233 INTEGER(iwp) :: i !< 7234 INTEGER(iwp) :: i_omp_start !< 7235 INTEGER(iwp) :: j !< 7236 INTEGER(iwp) :: k !< 7237 INTEGER(iwp) :: nc !< (c-1)*nbins+b 7238 INTEGER(iwp) :: tn !< 7253 7254 CHARACTER(LEN = *) :: id !< 7255 7256 INTEGER(iwp) :: i !< 7257 INTEGER(iwp) :: i_omp_start !< 7258 INTEGER(iwp) :: ib !< loop index for aerosol number bin OR gas index 7259 INTEGER(iwp) :: ic !< loop index for aerosol mass bin 7260 INTEGER(iwp) :: icc !< (c-1)*nbins_aerosol+b 7261 INTEGER(iwp) :: j !< 7262 INTEGER(iwp) :: k !< 7263 INTEGER(iwp) :: tn !< 7264 7265 LOGICAL :: do_sedimentation !< 7266 7267 REAL(wp), DIMENSION(nzb:nzt+1) :: rs_init !< 7268 7269 REAL(wp), DIMENSION(nzb+1:nzt,0:threads_per_task-1) :: diss_s !< 7270 REAL(wp), DIMENSION(nzb+1:nzt,0:threads_per_task-1) :: flux_s !< 7271 7239 7272 REAL(wp), DIMENSION(nzb+1:nzt,nys:nyn,0:threads_per_task-1) :: diss_l !< 7240 REAL(wp), DIMENSION(nzb+1:nzt,0:threads_per_task-1) :: diss_s !<7241 7273 REAL(wp), DIMENSION(nzb+1:nzt,nys:nyn,0:threads_per_task-1) :: flux_l !< 7242 REAL(wp), DIMENSION(nzb+1:nzt,0:threads_per_task-1) :: flux_s !< 7243 REAL(wp), DIMENSION(nzb:nzt+1) :: rs_init !< 7244 REAL(wp), DIMENSION(:,:,:), POINTER :: rs_p !< 7245 REAL(wp), DIMENSION(:,:,:), POINTER :: rs !< 7246 REAL(wp), DIMENSION(:,:,:), POINTER :: trs_m !< 7247 7248 nc = (c-1)*nbins+b 7274 7275 REAL(wp), DIMENSION(:,:,:), POINTER :: rs_p !< 7276 REAL(wp), DIMENSION(:,:,:), POINTER :: rs !< 7277 REAL(wp), DIMENSION(:,:,:), POINTER :: trs_m !< 7278 7279 icc = ( ic - 1 ) * nbins_aerosol + ib 7249 7280 ! 7250 7281 !-- Tendency-terms for reactive scalar 7251 7282 tend(:,j,i) = 0.0_wp 7252 7253 IF ( id == 'aerosol_number' .AND. lod_aero == 3 ) THEN 7254 tend(:,j,i) = tend(:,j,i) + aerosol_number(b)%source(:,j,i) 7255 ELSEIF ( id == 'aerosol_mass' .AND. lod_aero == 3 ) THEN 7256 tend(:,j,i) = tend(:,j,i) + aerosol_mass(nc)%source(:,j,i) 7257 ENDIF 7258 ! 7283 ! 7259 7284 !-- Advection terms 7260 7285 IF ( timestep_scheme(1:5) == 'runge' ) THEN 7261 7286 IF ( ws_scheme_sca ) THEN 7262 CALL advec_s_ws( i, j, rs, id, flux_s, diss_s, flux_l, diss_l, & 7263 i_omp_start, tn ) 7287 CALL advec_s_ws( i, j, rs, id, flux_s, diss_s, flux_l, diss_l, i_omp_start, tn ) 7264 7288 ELSE 7265 7289 CALL advec_s_pw( i, j, rs ) … … 7269 7293 ENDIF 7270 7294 ! 7271 !-- Diffusion terms 7272 IF ( id == 'aerosol_number' ) THEN 7273 CALL diffusion_s( i, j, rs, surf_def_h(0)%answs(:,b), & 7274 surf_def_h(1)%answs(:,b), surf_def_h(2)%answs(:,b), & 7275 surf_lsm_h%answs(:,b), surf_usm_h%answs(:,b), & 7276 surf_def_v(0)%answs(:,b), surf_def_v(1)%answs(:,b), & 7277 surf_def_v(2)%answs(:,b), surf_def_v(3)%answs(:,b), & 7278 surf_lsm_v(0)%answs(:,b), surf_lsm_v(1)%answs(:,b), & 7279 surf_lsm_v(2)%answs(:,b), surf_lsm_v(3)%answs(:,b), & 7280 surf_usm_v(0)%answs(:,b), surf_usm_v(1)%answs(:,b), & 7281 surf_usm_v(2)%answs(:,b), surf_usm_v(3)%answs(:,b) ) 7282 ! 7283 !-- Sedimentation for aerosol number and mass 7284 IF ( lsdepo ) THEN 7285 tend(nzb+1:nzt,j,i) = tend(nzb+1:nzt,j,i) - MAX( 0.0_wp, & 7286 ( rs(nzb+2:nzt+1,j,i) * sedim_vd(nzb+2:nzt+1,j,i,b) - & 7287 rs(nzb+1:nzt,j,i) * sedim_vd(nzb+1:nzt,j,i,b) ) * & 7288 ddzu(nzb+1:nzt) ) * MERGE( 1.0_wp, 0.0_wp, & 7289 BTEST( wall_flags_0(nzb:nzt-1,j,i), 0 ) ) 7290 ENDIF 7291 7292 ELSEIF ( id == 'aerosol_mass' ) THEN 7293 CALL diffusion_s( i, j, rs, surf_def_h(0)%amsws(:,nc), & 7294 surf_def_h(1)%amsws(:,nc), surf_def_h(2)%amsws(:,nc), & 7295 surf_lsm_h%amsws(:,nc), surf_usm_h%amsws(:,nc), & 7296 surf_def_v(0)%amsws(:,nc), surf_def_v(1)%amsws(:,nc), & 7297 surf_def_v(2)%amsws(:,nc), surf_def_v(3)%amsws(:,nc), & 7298 surf_lsm_v(0)%amsws(:,nc), surf_lsm_v(1)%amsws(:,nc), & 7299 surf_lsm_v(2)%amsws(:,nc), surf_lsm_v(3)%amsws(:,nc), & 7300 surf_usm_v(0)%amsws(:,nc), surf_usm_v(1)%amsws(:,nc), & 7301 surf_usm_v(2)%amsws(:,nc), surf_usm_v(3)%amsws(:,nc) ) 7302 ! 7303 !-- Sedimentation for aerosol number and mass 7304 IF ( lsdepo ) THEN 7305 tend(nzb+1:nzt,j,i) = tend(nzb+1:nzt,j,i) - MAX( 0.0_wp, & 7306 ( rs(nzb+2:nzt+1,j,i) * sedim_vd(nzb+2:nzt+1,j,i,b) - & 7307 rs(nzb+1:nzt,j,i) * sedim_vd(nzb+1:nzt,j,i,b) ) * & 7308 ddzu(nzb+1:nzt) ) * MERGE( 1.0_wp, 0.0_wp, & 7309 BTEST( wall_flags_0(nzb:nzt-1,j,i), 0 ) ) 7310 ENDIF 7311 ELSEIF ( id == 'salsa_gas' ) THEN 7312 CALL diffusion_s( i, j, rs, surf_def_h(0)%gtsws(:,b), & 7313 surf_def_h(1)%gtsws(:,b), surf_def_h(2)%gtsws(:,b), & 7314 surf_lsm_h%gtsws(:,b), surf_usm_h%gtsws(:,b), & 7315 surf_def_v(0)%gtsws(:,b), surf_def_v(1)%gtsws(:,b), & 7316 surf_def_v(2)%gtsws(:,b), surf_def_v(3)%gtsws(:,b), & 7317 surf_lsm_v(0)%gtsws(:,b), surf_lsm_v(1)%gtsws(:,b), & 7318 surf_lsm_v(2)%gtsws(:,b), surf_lsm_v(3)%gtsws(:,b), & 7319 surf_usm_v(0)%gtsws(:,b), surf_usm_v(1)%gtsws(:,b), & 7320 surf_usm_v(2)%gtsws(:,b), surf_usm_v(3)%gtsws(:,b) ) 7295 !-- Diffusion terms 7296 SELECT CASE ( id ) 7297 CASE ( 'aerosol_number' ) 7298 CALL diffusion_s( i, j, rs, surf_def_h(0)%answs(:,ib), & 7299 surf_def_h(1)%answs(:,ib), surf_def_h(2)%answs(:,ib), & 7300 surf_lsm_h%answs(:,ib), surf_usm_h%answs(:,ib), & 7301 surf_def_v(0)%answs(:,ib), surf_def_v(1)%answs(:,ib), & 7302 surf_def_v(2)%answs(:,ib), surf_def_v(3)%answs(:,ib), & 7303 surf_lsm_v(0)%answs(:,ib), surf_lsm_v(1)%answs(:,ib), & 7304 surf_lsm_v(2)%answs(:,ib), surf_lsm_v(3)%answs(:,ib), & 7305 surf_usm_v(0)%answs(:,ib), surf_usm_v(1)%answs(:,ib), & 7306 surf_usm_v(2)%answs(:,ib), surf_usm_v(3)%answs(:,ib) ) 7307 CASE ( 'aerosol_mass' ) 7308 CALL diffusion_s( i, j, rs, surf_def_h(0)%amsws(:,icc), & 7309 surf_def_h(1)%amsws(:,icc), surf_def_h(2)%amsws(:,icc), & 7310 surf_lsm_h%amsws(:,icc), surf_usm_h%amsws(:,icc), & 7311 surf_def_v(0)%amsws(:,icc), surf_def_v(1)%amsws(:,icc), & 7312 surf_def_v(2)%amsws(:,icc), surf_def_v(3)%amsws(:,icc), & 7313 surf_lsm_v(0)%amsws(:,icc), surf_lsm_v(1)%amsws(:,icc), & 7314 surf_lsm_v(2)%amsws(:,icc), surf_lsm_v(3)%amsws(:,icc), & 7315 surf_usm_v(0)%amsws(:,icc), surf_usm_v(1)%amsws(:,icc), & 7316 surf_usm_v(2)%amsws(:,icc), surf_usm_v(3)%amsws(:,icc) ) 7317 CASE ( 'salsa_gas' ) 7318 CALL diffusion_s( i, j, rs, surf_def_h(0)%gtsws(:,ib), & 7319 surf_def_h(1)%gtsws(:,ib), surf_def_h(2)%gtsws(:,ib), & 7320 surf_lsm_h%gtsws(:,ib), surf_usm_h%gtsws(:,ib), & 7321 surf_def_v(0)%gtsws(:,ib), surf_def_v(1)%gtsws(:,ib), & 7322 surf_def_v(2)%gtsws(:,ib), surf_def_v(3)%gtsws(:,ib), & 7323 surf_lsm_v(0)%gtsws(:,ib), surf_lsm_v(1)%gtsws(:,ib), & 7324 surf_lsm_v(2)%gtsws(:,ib), surf_lsm_v(3)%gtsws(:,ib), & 7325 surf_usm_v(0)%gtsws(:,ib), surf_usm_v(1)%gtsws(:,ib), & 7326 surf_usm_v(2)%gtsws(:,ib), surf_usm_v(3)%gtsws(:,ib) ) 7327 END SELECT 7328 ! 7329 !-- Sedimentation for aerosol number and mass 7330 IF ( lsdepo .AND. do_sedimentation ) THEN 7331 tend(nzb+1:nzt,j,i) = tend(nzb+1:nzt,j,i) - MAX( 0.0_wp, & 7332 ( rs(nzb+2:nzt+1,j,i) * sedim_vd(nzb+2:nzt+1,j,i,ib) - & 7333 rs(nzb+1:nzt,j,i) * sedim_vd(nzb+1:nzt,j,i,ib) ) * ddzu(nzb+1:nzt) )& 7334 * MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(nzb:nzt-1,j,i), 0 ) ) 7321 7335 ENDIF 7322 7336 ! 7323 7337 !-- Prognostic equation for a scalar 7324 7338 DO k = nzb+1, nzt 7325 rs_p(k,j,i) = rs(k,j,i) + ( dt_3d * ( tsc(2) * tend(k,j,i) + & 7326 tsc(3) * trs_m(k,j,i) ) & 7327 - tsc(5) * rdf_sc(k) & 7328 * ( rs(k,j,i) - rs_init(k) ) ) & 7329 * MERGE( 1.0_wp, 0.0_wp, & 7330 BTEST( wall_flags_0(k,j,i), 0 ) ) 7331 IF ( rs_p(k,j,i) < 0.0_wp ) rs_p(k,j,i) = 0.1_wp * rs(k,j,i) 7339 rs_p(k,j,i) = rs(k,j,i) + ( dt_3d * ( tsc(2) * tend(k,j,i) + tsc(3) * trs_m(k,j,i) ) & 7340 - tsc(5) * rdf_sc(k) * ( rs(k,j,i) - rs_init(k) ) ) & 7341 * MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(k,j,i), 0 ) ) 7342 IF ( rs_p(k,j,i) < 0.0_wp ) rs_p(k,j,i) = 0.1_wp * rs(k,j,i) 7332 7343 ENDDO 7333 7334 7344 ! 7335 7345 !-- Calculate tendencies for the next Runge-Kutta step … … 7339 7349 trs_m(k,j,i) = tend(k,j,i) 7340 7350 ENDDO 7341 ELSEIF ( intermediate_timestep_count < & 7342 intermediate_timestep_count_max ) THEN 7351 ELSEIF ( intermediate_timestep_count < intermediate_timestep_count_max ) THEN 7343 7352 DO k = nzb+1, nzt 7344 7353 trs_m(k,j,i) = -9.5625_wp * tend(k,j,i) + 5.3125_wp * trs_m(k,j,i) … … 7346 7355 ENDIF 7347 7356 ENDIF 7348 7357 7349 7358 END SUBROUTINE salsa_tendency_ij 7350 7351 ! 7359 ! 7352 7360 !------------------------------------------------------------------------------! 7353 7361 ! Description: 7354 7362 ! ------------ 7355 !> Calculate the tendencies for aerosol number and mass concentrations. 7363 !> Calculate the tendencies for aerosol number and mass concentrations. 7356 7364 !> Vector-optimized. 7357 !------------------------------------------------------------------------------! 7358 SUBROUTINE salsa_tendency( id, rs_p, rs, trs_m, b, c, rs_init)7359 7360 USE advec_ws, &7361 ONLY: advec_s_ws 7362 USE advec_s_pw_mod, &7365 !------------------------------------------------------------------------------! 7366 SUBROUTINE salsa_tendency( id, rs_p, rs, trs_m, ib, ic, rs_init, do_sedimentation ) 7367 7368 USE advec_ws, & 7369 ONLY: advec_s_ws 7370 USE advec_s_pw_mod, & 7363 7371 ONLY: advec_s_pw 7364 USE advec_s_up_mod, &7372 USE advec_s_up_mod, & 7365 7373 ONLY: advec_s_up 7366 USE arrays_3d, &7367 ONLY: ddzu, hyp, pt,rdf_sc, tend7368 USE diffusion_s_mod, &7374 USE arrays_3d, & 7375 ONLY: ddzu, rdf_sc, tend 7376 USE diffusion_s_mod, & 7369 7377 ONLY: diffusion_s 7370 USE indices, &7378 USE indices, & 7371 7379 ONLY: wall_flags_0 7372 USE surface_mod, & 7373 ONLY : surf_def_h, surf_def_v, surf_lsm_h, surf_lsm_v, surf_usm_h, & 7374 surf_usm_v 7375 7380 USE surface_mod, & 7381 ONLY : surf_def_h, surf_def_v, surf_lsm_h, surf_lsm_v, surf_usm_h, surf_usm_v 7382 7376 7383 IMPLICIT NONE 7377 7378 CHARACTER (LEN = *) :: id 7379 INTEGER(iwp) :: b !< bin index in derived type aerosol_size_bin 7380 INTEGER(iwp) :: c !< bin index in derived type aerosol_size_bin 7381 INTEGER(iwp) :: i !< 7382 INTEGER(iwp) :: j !< 7383 INTEGER(iwp) :: k !< 7384 INTEGER(iwp) :: nc !< (c-1)*nbins+b 7385 REAL(wp), DIMENSION(nzb:nzt+1) :: rs_init !< 7386 REAL(wp), DIMENSION(:,:,:), POINTER :: rs_p !< 7387 REAL(wp), DIMENSION(:,:,:), POINTER :: rs !< 7388 REAL(wp), DIMENSION(:,:,:), POINTER :: trs_m !< 7389 7390 nc = (c-1)*nbins+b 7384 7385 CHARACTER(LEN = *) :: id 7386 7387 INTEGER(iwp) :: ib !< loop index for aerosol number bin OR gas index 7388 INTEGER(iwp) :: ic !< loop index for aerosol mass bin 7389 INTEGER(iwp) :: icc !< (c-1)*nbins_aerosol+b 7390 INTEGER(iwp) :: i !< 7391 INTEGER(iwp) :: j !< 7392 INTEGER(iwp) :: k !< 7393 7394 LOGICAL :: do_sedimentation !< 7395 7396 REAL(wp), DIMENSION(nzb:nzt+1) :: rs_init !< 7397 7398 REAL(wp), DIMENSION(:,:,:), POINTER :: rs_p !< 7399 REAL(wp), DIMENSION(:,:,:), POINTER :: rs !< 7400 REAL(wp), DIMENSION(:,:,:), POINTER :: trs_m !< 7401 7402 icc = ( ic - 1 ) * nbins_aerosol + ib 7391 7403 ! 7392 7404 !-- Tendency-terms for reactive scalar 7393 7405 tend = 0.0_wp 7394 7395 IF ( id == 'aerosol_number' .AND. lod_aero == 3 ) THEN 7396 tend = tend + aerosol_number(b)%source 7397 ELSEIF ( id == 'aerosol_mass' .AND. lod_aero == 3 ) THEN 7398 tend = tend + aerosol_mass(nc)%source 7399 ENDIF 7400 ! 7406 ! 7401 7407 !-- Advection terms 7402 7408 IF ( timestep_scheme(1:5) == 'runge' ) THEN … … 7410 7416 ENDIF 7411 7417 ! 7412 !-- Diffusion terms 7413 IF ( id == 'aerosol_number' ) THEN 7414 CALL diffusion_s( rs, surf_def_h(0)%answs(:,b), & 7415 surf_def_h(1)%answs(:,b), surf_def_h(2)%answs(:,b), & 7416 surf_lsm_h%answs(:,b), surf_usm_h%answs(:,b), & 7417 surf_def_v(0)%answs(:,b), surf_def_v(1)%answs(:,b), & 7418 surf_def_v(2)%answs(:,b), surf_def_v(3)%answs(:,b), & 7419 surf_lsm_v(0)%answs(:,b), surf_lsm_v(1)%answs(:,b), & 7420 surf_lsm_v(2)%answs(:,b), surf_lsm_v(3)%answs(:,b), & 7421 surf_usm_v(0)%answs(:,b), surf_usm_v(1)%answs(:,b), & 7422 surf_usm_v(2)%answs(:,b), surf_usm_v(3)%answs(:,b) ) 7423 ELSEIF ( id == 'aerosol_mass' ) THEN 7424 CALL diffusion_s( rs, surf_def_h(0)%amsws(:,nc), & 7425 surf_def_h(1)%amsws(:,nc), surf_def_h(2)%amsws(:,nc), & 7426 surf_lsm_h%amsws(:,nc), surf_usm_h%amsws(:,nc), & 7427 surf_def_v(0)%amsws(:,nc), surf_def_v(1)%amsws(:,nc), & 7428 surf_def_v(2)%amsws(:,nc), surf_def_v(3)%amsws(:,nc), & 7429 surf_lsm_v(0)%amsws(:,nc), surf_lsm_v(1)%amsws(:,nc), & 7430 surf_lsm_v(2)%amsws(:,nc), surf_lsm_v(3)%amsws(:,nc), & 7431 surf_usm_v(0)%amsws(:,nc), surf_usm_v(1)%amsws(:,nc), & 7432 surf_usm_v(2)%amsws(:,nc), surf_usm_v(3)%amsws(:,nc) ) 7433 ELSEIF ( id == 'salsa_gas' ) THEN 7434 CALL diffusion_s( rs, surf_def_h(0)%gtsws(:,b), & 7435 surf_def_h(1)%gtsws(:,b), surf_def_h(2)%gtsws(:,b), & 7436 surf_lsm_h%gtsws(:,b), surf_usm_h%gtsws(:,b), & 7437 surf_def_v(0)%gtsws(:,b), surf_def_v(1)%gtsws(:,b), & 7438 surf_def_v(2)%gtsws(:,b), surf_def_v(3)%gtsws(:,b), & 7439 surf_lsm_v(0)%gtsws(:,b), surf_lsm_v(1)%gtsws(:,b), & 7440 surf_lsm_v(2)%gtsws(:,b), surf_lsm_v(3)%gtsws(:,b), & 7441 surf_usm_v(0)%gtsws(:,b), surf_usm_v(1)%gtsws(:,b), & 7442 surf_usm_v(2)%gtsws(:,b), surf_usm_v(3)%gtsws(:,b) ) 7443 ENDIF 7418 !-- Diffusion terms 7419 SELECT CASE ( id ) 7420 CASE ( 'aerosol_number' ) 7421 CALL diffusion_s( rs, surf_def_h(0)%answs(:,ib), & 7422 surf_def_h(1)%answs(:,ib), surf_def_h(2)%answs(:,ib), & 7423 surf_lsm_h%answs(:,ib), surf_usm_h%answs(:,ib), & 7424 surf_def_v(0)%answs(:,ib), surf_def_v(1)%answs(:,ib), & 7425 surf_def_v(2)%answs(:,ib), surf_def_v(3)%answs(:,ib), & 7426 surf_lsm_v(0)%answs(:,ib), surf_lsm_v(1)%answs(:,ib), & 7427 surf_lsm_v(2)%answs(:,ib), surf_lsm_v(3)%answs(:,ib), & 7428 surf_usm_v(0)%answs(:,ib), surf_usm_v(1)%answs(:,ib), & 7429 surf_usm_v(2)%answs(:,ib), surf_usm_v(3)%answs(:,ib) ) 7430 CASE ( 'aerosol_mass' ) 7431 CALL diffusion_s( rs, surf_def_h(0)%amsws(:,icc), & 7432 surf_def_h(1)%amsws(:,icc), surf_def_h(2)%amsws(:,icc), & 7433 surf_lsm_h%amsws(:,icc), surf_usm_h%amsws(:,icc), & 7434 surf_def_v(0)%amsws(:,icc), surf_def_v(1)%amsws(:,icc), & 7435 surf_def_v(2)%amsws(:,icc), surf_def_v(3)%amsws(:,icc), & 7436 surf_lsm_v(0)%amsws(:,icc), surf_lsm_v(1)%amsws(:,icc), & 7437 surf_lsm_v(2)%amsws(:,icc), surf_lsm_v(3)%amsws(:,icc), & 7438 surf_usm_v(0)%amsws(:,icc), surf_usm_v(1)%amsws(:,icc), & 7439 surf_usm_v(2)%amsws(:,icc), surf_usm_v(3)%amsws(:,icc) ) 7440 CASE ( 'salsa_gas' ) 7441 CALL diffusion_s( rs, surf_def_h(0)%gtsws(:,ib), & 7442 surf_def_h(1)%gtsws(:,ib), surf_def_h(2)%gtsws(:,ib), & 7443 surf_lsm_h%gtsws(:,ib), surf_usm_h%gtsws(:,ib), & 7444 surf_def_v(0)%gtsws(:,ib), surf_def_v(1)%gtsws(:,ib), & 7445 surf_def_v(2)%gtsws(:,ib), surf_def_v(3)%gtsws(:,ib), & 7446 surf_lsm_v(0)%gtsws(:,ib), surf_lsm_v(1)%gtsws(:,ib), & 7447 surf_lsm_v(2)%gtsws(:,ib), surf_lsm_v(3)%gtsws(:,ib), & 7448 surf_usm_v(0)%gtsws(:,ib), surf_usm_v(1)%gtsws(:,ib), & 7449 surf_usm_v(2)%gtsws(:,ib), surf_usm_v(3)%gtsws(:,ib) ) 7450 END SELECT 7444 7451 ! 7445 7452 !-- Prognostic equation for a scalar 7446 7453 DO i = nxl, nxr 7447 7454 DO j = nys, nyn 7448 IF ( id == 'salsa_gas' .AND. lod_gases == 3 ) THEN 7449 tend(:,j,i) = tend(:,j,i) + salsa_gas(b)%source(:,j,i) * & 7450 for_ppm_to_nconc * hyp(:) / pt(:,j,i) * ( hyp(:) / & 7451 100000.0_wp )**0.286_wp ! ppm to #/m3 7452 ELSEIF ( id == 'aerosol_mass' .OR. id == 'aerosol_number') THEN 7453 ! 7454 !-- Sedimentation for aerosol number and mass 7455 IF ( lsdepo ) THEN 7456 tend(nzb+1:nzt,j,i) = tend(nzb+1:nzt,j,i) - MAX( 0.0_wp, & 7457 ( rs(nzb+2:nzt+1,j,i) * sedim_vd(nzb+2:nzt+1,j,i,b) - & 7458 rs(nzb+1:nzt,j,i) * sedim_vd(nzb+1:nzt,j,i,b) ) * & 7459 ddzu(nzb+1:nzt) ) * MERGE( 1.0_wp, 0.0_wp, & 7460 BTEST( wall_flags_0(nzb:nzt-1,j,i), 0 ) ) 7461 ENDIF 7455 ! 7456 !-- Sedimentation for aerosol number and mass 7457 IF ( lsdepo .AND. do_sedimentation ) THEN 7458 tend(nzb+1:nzt,j,i) = tend(nzb+1:nzt,j,i) - MAX( 0.0_wp, ( rs(nzb+2:nzt+1,j,i) * & 7459 sedim_vd(nzb+2:nzt+1,j,i,ib) - rs(nzb+1:nzt,j,i) * & 7460 sedim_vd(nzb+1:nzt,j,i,ib) ) * ddzu(nzb+1:nzt) ) * & 7461 MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(nzb:nzt-1,j,i), 0 ) ) 7462 7462 ENDIF 7463 7463 DO k = nzb+1, nzt 7464 rs_p(k,j,i) = rs(k,j,i) + ( dt_3d * ( tsc(2) * tend(k,j,i) + & 7465 tsc(3) * trs_m(k,j,i) ) & 7466 - tsc(5) * rdf_sc(k) & 7467 * ( rs(k,j,i) - rs_init(k) ) )& 7468 * MERGE( 1.0_wp, 0.0_wp, & 7469 BTEST( wall_flags_0(k,j,i), 0 ) ) 7470 IF ( rs_p(k,j,i) < 0.0_wp ) rs_p(k,j,i) = 0.1_wp * rs(k,j,i) 7464 rs_p(k,j,i) = rs(k,j,i) + ( dt_3d * ( tsc(2) * tend(k,j,i) + tsc(3) * trs_m(k,j,i) )& 7465 - tsc(5) * rdf_sc(k) * ( rs(k,j,i) - rs_init(k) )& 7466 ) * MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(k,j,i), 0 ) ) 7467 IF ( rs_p(k,j,i) < 0.0_wp ) rs_p(k,j,i) = 0.1_wp * rs(k,j,i) 7471 7468 ENDDO 7472 7469 ENDDO 7473 7470 ENDDO 7474 7475 7471 ! 7476 7472 !-- Calculate tendencies for the next Runge-Kutta step … … 7484 7480 ENDDO 7485 7481 ENDDO 7486 ELSEIF ( intermediate_timestep_count < & 7487 intermediate_timestep_count_max ) THEN 7482 ELSEIF ( intermediate_timestep_count < intermediate_timestep_count_max ) THEN 7488 7483 DO i = nxl, nxr 7489 7484 DO j = nys, nyn 7490 7485 DO k = nzb+1, nzt 7491 trs_m(k,j,i) = -9.5625_wp * tend(k,j,i) & 7492 + 5.3125_wp * trs_m(k,j,i) 7486 trs_m(k,j,i) = -9.5625_wp * tend(k,j,i) + 5.3125_wp * trs_m(k,j,i) 7493 7487 ENDDO 7494 7488 ENDDO … … 7496 7490 ENDIF 7497 7491 ENDIF 7498 7492 7499 7493 END SUBROUTINE salsa_tendency 7500 7494 7501 7495 !------------------------------------------------------------------------------! 7502 7496 ! Description: 7503 7497 ! ------------ 7504 7498 !> Boundary conditions for prognostic variables in SALSA 7505 !------------------------------------------------------------------------------! 7499 !------------------------------------------------------------------------------! 7506 7500 SUBROUTINE salsa_boundary_conds 7507 7508 USE surface_mod, & 7501 7502 USE arrays_3d, & 7503 ONLY: dzu 7504 7505 USE surface_mod, & 7509 7506 ONLY : bc_h 7510 7507 7511 7508 IMPLICIT NONE 7512 7509 7513 INTEGER(iwp) :: b !< index for aerosol size bins 7514 INTEGER(iwp) :: c !< index for chemical compounds in aerosols 7515 INTEGER(iwp) :: g !< idex for gaseous compounds 7516 INTEGER(iwp) :: i !< grid index x direction 7517 INTEGER(iwp) :: j !< grid index y direction 7518 INTEGER(iwp) :: k !< grid index y direction 7519 INTEGER(iwp) :: kb !< variable to set respective boundary value, depends on 7520 !< facing. 7521 INTEGER(iwp) :: l !< running index boundary type, for up- and downward- 7522 !< facing walls 7523 INTEGER(iwp) :: m !< running index surface elements 7524 7525 ! 7526 !-- Surface conditions: 7527 IF ( ibc_salsa_b == 0 ) THEN ! Dirichlet 7528 ! 7529 !-- Run loop over all non-natural and natural walls. Note, in wall-datatype 7530 !-- the k coordinate belongs to the atmospheric grid point, therefore, set 7531 !-- s_p at k-1 7532 7533 DO l = 0, 1 7534 ! 7535 !-- Set kb, for upward-facing surfaces value at topography top (k-1) is 7536 !-- set, for downward-facing surfaces at topography bottom (k+1) 7537 kb = MERGE ( -1, 1, l == 0 ) 7538 !$OMP PARALLEL PRIVATE( b, c, g, i, j, k ) 7539 !$OMP DO 7540 DO m = 1, bc_h(l)%ns 7541 7542 i = bc_h(l)%i(m) 7543 j = bc_h(l)%j(m) 7544 k = bc_h(l)%k(m) 7545 7546 DO b = 1, nbins 7547 aerosol_number(b)%conc_p(k+kb,j,i) = & 7548 aerosol_number(b)%conc(k+kb,j,i) 7549 DO c = 1, ncc_tot 7550 aerosol_mass((c-1)*nbins+b)%conc_p(k+kb,j,i) = & 7551 aerosol_mass((c-1)*nbins+b)%conc(k+kb,j,i) 7510 INTEGER(iwp) :: i !< grid index x direction 7511 INTEGER(iwp) :: ib !< index for aerosol size bins 7512 INTEGER(iwp) :: ic !< index for chemical compounds in aerosols 7513 INTEGER(iwp) :: icc !< additional index for chemical compounds in aerosols 7514 INTEGER(iwp) :: ig !< idex for gaseous compounds 7515 INTEGER(iwp) :: j !< grid index y direction 7516 INTEGER(iwp) :: k !< grid index y direction 7517 INTEGER(iwp) :: kb !< variable to set respective boundary value, depends on facing. 7518 INTEGER(iwp) :: l !< running index boundary type, for up- and downward-facing walls 7519 INTEGER(iwp) :: m !< running index surface elements 7520 7521 IF ( time_since_reference_point >= skip_time_do_salsa ) THEN 7522 7523 ! 7524 !-- Surface conditions: 7525 IF ( ibc_salsa_b == 0 ) THEN ! Dirichlet 7526 ! 7527 !-- Run loop over all non-natural and natural walls. Note, in wall-datatype the k coordinate 7528 !-- belongs to the atmospheric grid point, therefore, set s_p at k-1 7529 DO l = 0, 1 7530 ! 7531 !-- Set kb, for upward-facing surfaces value at topography top (k-1) is 7532 !-- set, for downward-facing surfaces at topography bottom (k+1) 7533 kb = MERGE ( -1, 1, l == 0 ) 7534 !$OMP PARALLEL PRIVATE( ib, ic, icc, ig, i, j, k ) 7535 !$OMP DO 7536 DO m = 1, bc_h(l)%ns 7537 7538 i = bc_h(l)%i(m) 7539 j = bc_h(l)%j(m) 7540 k = bc_h(l)%k(m) 7541 7542 DO ib = 1, nbins_aerosol 7543 aerosol_number(ib)%conc_p(k+kb,j,i) = aerosol_number(ib)%conc(k+kb,j,i) 7544 DO ic = 1, ncomponents_mass 7545 icc = ( ic - 1 ) * nbins_aerosol + ib 7546 aerosol_mass(icc)%conc_p(k+kb,j,i) = aerosol_mass(icc)%conc(k+kb,j,i) 7547 ENDDO 7552 7548 ENDDO 7549 IF ( .NOT. salsa_gases_from_chem ) THEN 7550 DO ig = 1, ngases_salsa 7551 salsa_gas(ig)%conc_p(k+kb,j,i) = salsa_gas(ig)%conc(k+kb,j,i) 7552 ENDDO 7553 ENDIF 7554 7553 7555 ENDDO 7554 IF ( .NOT. salsa_gases_from_chem ) THEN 7555 DO g = 1, ngast 7556 salsa_gas(g)%conc_p(k+kb,j,i) = salsa_gas(g)%conc(k+kb,j,i) 7556 !$OMP END PARALLEL 7557 7558 ENDDO 7559 7560 ELSE ! Neumann 7561 7562 DO l = 0, 1 7563 ! 7564 !-- Set kb, for upward-facing surfaces value at topography top (k-1) is 7565 !-- set, for downward-facing surfaces at topography bottom (k+1) 7566 kb = MERGE( -1, 1, l == 0 ) 7567 !$OMP PARALLEL PRIVATE( ib, ic, icc, ig, i, j, k ) 7568 !$OMP DO 7569 DO m = 1, bc_h(l)%ns 7570 7571 i = bc_h(l)%i(m) 7572 j = bc_h(l)%j(m) 7573 k = bc_h(l)%k(m) 7574 7575 DO ib = 1, nbins_aerosol 7576 aerosol_number(ib)%conc_p(k+kb,j,i) = aerosol_number(ib)%conc_p(k,j,i) 7577 DO ic = 1, ncomponents_mass 7578 icc = ( ic - 1 ) * nbins_aerosol + ib 7579 aerosol_mass(icc)%conc_p(k+kb,j,i) = aerosol_mass(icc)%conc_p(k,j,i) 7580 ENDDO 7557 7581 ENDDO 7558 ENDIF 7559 7582 IF ( .NOT. salsa_gases_from_chem ) THEN 7583 DO ig = 1, ngases_salsa 7584 salsa_gas(ig)%conc_p(k+kb,j,i) = salsa_gas(ig)%conc_p(k,j,i) 7585 ENDDO 7586 ENDIF 7587 7588 ENDDO 7589 !$OMP END PARALLEL 7560 7590 ENDDO 7561 !$OMP END PARALLEL 7562 7563 ENDDO 7564 7565 ELSE ! Neumann 7566 7567 DO l = 0, 1 7568 ! 7569 !-- Set kb, for upward-facing surfaces value at topography top (k-1) is 7570 !-- set, for downward-facing surfaces at topography bottom (k+1) 7571 kb = MERGE( -1, 1, l == 0 ) 7572 !$OMP PARALLEL PRIVATE( b, c, g, i, j, k ) 7573 !$OMP DO 7574 DO m = 1, bc_h(l)%ns 7575 7576 i = bc_h(l)%i(m) 7577 j = bc_h(l)%j(m) 7578 k = bc_h(l)%k(m) 7579 7580 DO b = 1, nbins 7581 aerosol_number(b)%conc_p(k+kb,j,i) = & 7582 aerosol_number(b)%conc_p(k,j,i) 7583 DO c = 1, ncc_tot 7584 aerosol_mass((c-1)*nbins+b)%conc_p(k+kb,j,i) = & 7585 aerosol_mass((c-1)*nbins+b)%conc_p(k,j,i) 7586 ENDDO 7591 7592 ENDIF 7593 ! 7594 !-- Top boundary conditions: 7595 IF ( ibc_salsa_t == 0 ) THEN ! Dirichlet 7596 7597 DO ib = 1, nbins_aerosol 7598 aerosol_number(ib)%conc_p(nzt+1,:,:) = aerosol_number(ib)%conc(nzt+1,:,:) 7599 DO ic = 1, ncomponents_mass 7600 icc = ( ic - 1 ) * nbins_aerosol + ib 7601 aerosol_mass(icc)%conc_p(nzt+1,:,:) = aerosol_mass(icc)%conc(nzt+1,:,:) 7587 7602 ENDDO 7588 IF ( .NOT. salsa_gases_from_chem ) THEN7589 DO g = 1, ngast7590 salsa_gas(g)%conc_p(k+kb,j,i) = salsa_gas(g)%conc_p(k,j,i)7591 ENDDO7592 ENDIF7593 7594 7603 ENDDO 7595 !$OMP END PARALLEL 7596 ENDDO 7597 7598 ENDIF 7599 7600 ! 7601 !--Top boundary conditions: 7602 IF ( ibc_salsa_t == 0 ) THEN ! Dirichlet 7603 7604 DO b = 1, nbins 7605 aerosol_number(b)%conc_p(nzt+1,:,:) = & 7606 aerosol_number(b)%conc(nzt+1,:,:) 7607 DO c = 1, ncc_tot 7608 aerosol_mass((c-1)*nbins+b)%conc_p(nzt+1,:,:) = & 7609 aerosol_mass((c-1)*nbins+b)%conc(nzt+1,:,:) 7604 IF ( .NOT. salsa_gases_from_chem ) THEN 7605 DO ig = 1, ngases_salsa 7606 salsa_gas(ig)%conc_p(nzt+1,:,:) = salsa_gas(ig)%conc(nzt+1,:,:) 7607 ENDDO 7608 ENDIF 7609 7610 ELSEIF ( ibc_salsa_t == 1 ) THEN ! Neumann 7611 7612 DO ib = 1, nbins_aerosol 7613 aerosol_number(ib)%conc_p(nzt+1,:,:) = aerosol_number(ib)%conc_p(nzt,:,:) 7614 DO ic = 1, ncomponents_mass 7615 icc = ( ic - 1 ) * nbins_aerosol + ib 7616 aerosol_mass(icc)%conc_p(nzt+1,:,:) = aerosol_mass(icc)%conc_p(nzt,:,:) 7617 ENDDO 7610 7618 ENDDO 7611 ENDDO 7612 IF ( .NOT. salsa_gases_from_chem ) THEN 7613 DO g = 1, ngast 7614 salsa_gas(g)%conc_p(nzt+1,:,:) = salsa_gas(g)%conc(nzt+1,:,:) 7619 IF ( .NOT. salsa_gases_from_chem ) THEN 7620 DO ig = 1, ngases_salsa 7621 salsa_gas(ig)%conc_p(nzt+1,:,:) = salsa_gas(ig)%conc_p(nzt,:,:) 7622 ENDDO 7623 ENDIF 7624 7625 ELSEIF ( ibc_salsa_t == 2 ) THEN ! nested 7626 7627 DO ib = 1, nbins_aerosol 7628 aerosol_number(ib)%conc_p(nzt+1,:,:) = aerosol_number(ib)%conc_p(nzt,:,:) + & 7629 bc_an_t_val(ib) * dzu(nzt+1) 7630 DO ic = 1, ncomponents_mass 7631 icc = ( ic - 1 ) * nbins_aerosol + ib 7632 aerosol_mass(icc)%conc_p(nzt+1,:,:) = aerosol_mass(icc)%conc_p(nzt,:,:) + & 7633 bc_am_t_val(icc) * dzu(nzt+1) 7634 ENDDO 7615 7635 ENDDO 7616 ENDIF 7617 7618 ELSEIF ( ibc_salsa_t == 1 ) THEN ! Neumann 7619 7620 DO b = 1, nbins 7621 aerosol_number(b)%conc_p(nzt+1,:,:) = & 7622 aerosol_number(b)%conc_p(nzt,:,:) 7623 DO c = 1, ncc_tot 7624 aerosol_mass((c-1)*nbins+b)%conc_p(nzt+1,:,:) = & 7625 aerosol_mass((c-1)*nbins+b)%conc_p(nzt,:,:) 7636 IF ( .NOT. salsa_gases_from_chem ) THEN 7637 DO ig = 1, ngases_salsa 7638 salsa_gas(ig)%conc_p(nzt+1,:,:) = salsa_gas(ig)%conc_p(nzt,:,:) + & 7639 bc_gt_t_val(ig) * dzu(nzt+1) 7640 ENDDO 7641 ENDIF 7642 7643 ENDIF 7644 ! 7645 !-- Lateral boundary conditions at the outflow 7646 IF ( bc_radiation_s ) THEN 7647 DO ib = 1, nbins_aerosol 7648 aerosol_number(ib)%conc_p(:,nys-1,:) = aerosol_number(ib)%conc_p(:,nys,:) 7649 DO ic = 1, ncomponents_mass 7650 icc = ( ic - 1 ) * nbins_aerosol + ib 7651 aerosol_mass(icc)%conc_p(:,nys-1,:) = aerosol_mass(icc)%conc_p(:,nys,:) 7652 ENDDO 7626 7653 ENDDO 7627 ENDDO 7628 IF ( .NOT. salsa_gases_from_chem ) THEN 7629 DO g = 1, ngast 7630 salsa_gas(g)%conc_p(nzt+1,:,:) = salsa_gas(g)%conc_p(nzt,:,:) 7654 IF ( .NOT. salsa_gases_from_chem ) THEN 7655 DO ig = 1, ngases_salsa 7656 salsa_gas(ig)%conc_p(:,nys-1,:) = salsa_gas(ig)%conc_p(:,nys,:) 7657 ENDDO 7658 ENDIF 7659 7660 ELSEIF ( bc_radiation_n ) THEN 7661 DO ib = 1, nbins_aerosol 7662 aerosol_number(ib)%conc_p(:,nyn+1,:) = aerosol_number(ib)%conc_p(:,nyn,:) 7663 DO ic = 1, ncomponents_mass 7664 icc = ( ic - 1 ) * nbins_aerosol + ib 7665 aerosol_mass(icc)%conc_p(:,nyn+1,:) = aerosol_mass(icc)%conc_p(:,nyn,:) 7666 ENDDO 7631 7667 ENDDO 7632 ENDIF 7633 7634 ENDIF 7635 ! 7636 !-- Lateral boundary conditions at the outflow 7637 IF ( bc_radiation_s ) THEN 7638 DO b = 1, nbins 7639 aerosol_number(b)%conc_p(:,nys-1,:) = aerosol_number(b)%conc_p(:,nys,:) 7640 DO c = 1, ncc_tot 7641 aerosol_mass((c-1)*nbins+b)%conc_p(:,nys-1,:) = & 7642 aerosol_mass((c-1)*nbins+b)%conc_p(:,nys,:) 7668 IF ( .NOT. salsa_gases_from_chem ) THEN 7669 DO ig = 1, ngases_salsa 7670 salsa_gas(ig)%conc_p(:,nyn+1,:) = salsa_gas(ig)%conc_p(:,nyn,:) 7671 ENDDO 7672 ENDIF 7673 7674 ELSEIF ( bc_radiation_l ) THEN 7675 DO ib = 1, nbins_aerosol 7676 aerosol_number(ib)%conc_p(:,:,nxl-1) = aerosol_number(ib)%conc_p(:,:,nxl) 7677 DO ic = 1, ncomponents_mass 7678 icc = ( ic - 1 ) * nbins_aerosol + ib 7679 aerosol_mass(icc)%conc_p(:,:,nxl-1) = aerosol_mass(icc)%conc_p(:,:,nxl) 7680 ENDDO 7643 7681 ENDDO 7644 ENDDO 7645 ELSEIF ( bc_radiation_n ) THEN 7646 DO b = 1, nbins 7647 aerosol_number(b)%conc_p(:,nyn+1,:) = aerosol_number(b)%conc_p(:,nyn,:) 7648 DO c = 1, ncc_tot 7649 aerosol_mass((c-1)*nbins+b)%conc_p(:,nyn+1,:) = & 7650 aerosol_mass((c-1)*nbins+b)%conc_p(:,nyn,:) 7682 IF ( .NOT. salsa_gases_from_chem ) THEN 7683 DO ig = 1, ngases_salsa 7684 salsa_gas(ig)%conc_p(:,:,nxl-1) = salsa_gas(ig)%conc_p(:,:,nxl) 7685 ENDDO 7686 ENDIF 7687 7688 ELSEIF ( bc_radiation_r ) THEN 7689 DO ib = 1, nbins_aerosol 7690 aerosol_number(ib)%conc_p(:,:,nxr+1) = aerosol_number(ib)%conc_p(:,:,nxr) 7691 DO ic = 1, ncomponents_mass 7692 icc = ( ic - 1 ) * nbins_aerosol + ib 7693 aerosol_mass(icc)%conc_p(:,:,nxr+1) = aerosol_mass(icc)%conc_p(:,:,nxr) 7694 ENDDO 7651 7695 ENDDO 7652 ENDDO 7653 ELSEIF ( bc_radiation_l ) THEN 7654 DO b = 1, nbins 7655 aerosol_number(b)%conc_p(:,nxl-1,:) = aerosol_number(b)%conc_p(:,nxl,:) 7656 DO c = 1, ncc_tot 7657 aerosol_mass((c-1)*nbins+b)%conc_p(:,nxl-1,:) = & 7658 aerosol_mass((c-1)*nbins+b)%conc_p(:,nxl,:) 7659 ENDDO 7660 ENDDO 7661 ELSEIF ( bc_radiation_r ) THEN 7662 DO b = 1, nbins 7663 aerosol_number(b)%conc_p(:,nxr+1,:) = aerosol_number(b)%conc_p(:,nxr,:) 7664 DO c = 1, ncc_tot 7665 aerosol_mass((c-1)*nbins+b)%conc_p(:,nxr+1,:) = & 7666 aerosol_mass((c-1)*nbins+b)%conc_p(:,nxr,:) 7667 ENDDO 7668 ENDDO 7696 IF ( .NOT. salsa_gases_from_chem ) THEN 7697 DO ig = 1, ngases_salsa 7698 salsa_gas(ig)%conc_p(:,:,nxr+1) = salsa_gas(ig)%conc_p(:,:,nxr) 7699 ENDDO 7700 ENDIF 7701 7702 ENDIF 7703 7669 7704 ENDIF 7670 7705 … … 7675 7710 ! ------------ 7676 7711 ! Undoing of the previously done cyclic boundary conditions. 7677 !------------------------------------------------------------------------------! 7712 !------------------------------------------------------------------------------! 7678 7713 SUBROUTINE salsa_boundary_conds_decycle ( sq, sq_init ) 7679 7714 7680 7715 IMPLICIT NONE 7681 7716 7682 INTEGER(iwp) :: boundary !< 7683 INTEGER(iwp) :: ee !< 7684 INTEGER(iwp) :: copied !< 7685 INTEGER(iwp) :: i !< 7686 INTEGER(iwp) :: j !< 7687 INTEGER(iwp) :: k !< 7688 INTEGER(iwp) :: ss !< 7689 REAL(wp), DIMENSION(nzb:nzt+1) :: sq_init 7690 REAL(wp), DIMENSION(nzb:nzt+1,nysg:nyng,nxlg:nxrg) :: sq 7691 REAL(wp) :: flag !< flag to mask topography grid points 7717 INTEGER(iwp) :: boundary !< 7718 INTEGER(iwp) :: ee !< 7719 INTEGER(iwp) :: copied !< 7720 INTEGER(iwp) :: i !< 7721 INTEGER(iwp) :: j !< 7722 INTEGER(iwp) :: k !< 7723 INTEGER(iwp) :: ss !< 7724 7725 REAL(wp) :: flag !< flag to mask topography grid points 7726 7727 REAL(wp), DIMENSION(nzb:nzt+1) :: sq_init !< initial concentration profile 7728 7729 REAL(wp), DIMENSION(nzb:nzt+1,nysg:nyng,nxlg:nxrg) :: sq !< concentration array 7692 7730 7693 7731 flag = 0.0_wp … … 7695 7733 !-- Left and right boundaries 7696 7734 IF ( decycle_lr .AND. ( bc_lr_cyc .OR. bc_lr == 'nested' ) ) THEN 7697 7735 7698 7736 DO boundary = 1, 2 7699 7737 7700 7738 IF ( decycle_method(boundary) == 'dirichlet' ) THEN 7701 ! 7702 !-- Initial profile is copied to ghost and first three layers 7739 ! 7740 !-- Initial profile is copied to ghost and first three layers 7703 7741 ss = 1 7704 7742 ee = 0 … … 7710 7748 ee = nxrg 7711 7749 ENDIF 7712 7750 7713 7751 DO i = ss, ee 7714 7752 DO j = nysg, nyng 7715 DO k = nzb+1, nzt 7716 flag = MERGE( 1.0_wp, 0.0_wp, & 7717 BTEST( wall_flags_0(k,j,i), 0 ) ) 7753 DO k = nzb+1, nzt 7754 flag = MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(k,j,i), 0 ) ) 7718 7755 sq(k,j,i) = sq_init(k) * flag 7719 7756 ENDDO 7720 7757 ENDDO 7721 7758 ENDDO 7722 7759 7723 7760 ELSEIF ( decycle_method(boundary) == 'neumann' ) THEN 7724 7761 ! 7725 !-- The value at the boundary is copied to the ghost layers to simulate 7726 !-- an outlet withzero gradient7762 !-- The value at the boundary is copied to the ghost layers to simulate an outlet with 7763 !-- zero gradient 7727 7764 ss = 1 7728 7765 ee = 0 … … 7736 7773 copied = nxr 7737 7774 ENDIF 7738 7775 7739 7776 DO i = ss, ee 7740 7777 DO j = nysg, nyng 7741 DO k = nzb+1, nzt 7742 flag = MERGE( 1.0_wp, 0.0_wp, & 7743 BTEST( wall_flags_0(k,j,i), 0 ) ) 7778 DO k = nzb+1, nzt 7779 flag = MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(k,j,i), 0 ) ) 7744 7780 sq(k,j,i) = sq(k,j,copied) * flag 7745 7781 ENDDO 7746 7782 ENDDO 7747 7783 ENDDO 7748 7784 7749 7785 ELSE 7750 WRITE(message_string,*) & 7751 'unknown decycling method: decycle_method (', & 7752 boundary, ') ="' // TRIM( decycle_method(boundary) ) // '"' 7753 CALL message( 'salsa_boundary_conds_decycle', 'SA0029', & 7754 1, 2, 0, 6, 0 ) 7786 WRITE(message_string,*) 'unknown decycling method: decycle_method (', boundary, & 7787 ') ="' // TRIM( decycle_method(boundary) ) // '"' 7788 CALL message( 'salsa_boundary_conds_decycle', 'PA0626', 1, 2, 0, 6, 0 ) 7755 7789 ENDIF 7756 7790 ENDDO 7757 7791 ENDIF 7758 7792 7759 7793 ! 7760 7794 !-- South and north boundaries 7761 7795 IF ( decycle_ns .AND. ( bc_ns_cyc .OR. bc_ns == 'nested' ) ) THEN 7762 7796 7763 7797 DO boundary = 3, 4 7764 7798 7765 7799 IF ( decycle_method(boundary) == 'dirichlet' ) THEN 7766 ! 7767 !-- Initial profile is copied to ghost and first three layers 7800 ! 7801 !-- Initial profile is copied to ghost and first three layers 7768 7802 ss = 1 7769 7803 ee = 0 … … 7775 7809 ee = nyng 7776 7810 ENDIF 7777 7811 7778 7812 DO i = nxlg, nxrg 7779 7813 DO j = ss, ee 7780 DO k = nzb+1, nzt 7781 flag = MERGE( 1.0_wp, 0.0_wp, & 7782 BTEST( wall_flags_0(k,j,i), 0 ) ) 7814 DO k = nzb+1, nzt 7815 flag = MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(k,j,i), 0 ) ) 7783 7816 sq(k,j,i) = sq_init(k) * flag 7784 7817 ENDDO 7785 7818 ENDDO 7786 7819 ENDDO 7787 7820 7788 7821 ELSEIF ( decycle_method(boundary) == 'neumann' ) THEN 7789 7822 ! 7790 !-- The value at the boundary is copied to the ghost layers to simulate 7791 !-- an outlet withzero gradient7823 !-- The value at the boundary is copied to the ghost layers to simulate an outlet with 7824 !-- zero gradient 7792 7825 ss = 1 7793 7826 ee = 0 … … 7801 7834 copied = nyn 7802 7835 ENDIF 7803 7836 7804 7837 DO i = nxlg, nxrg 7805 7838 DO j = ss, ee 7806 DO k = nzb+1, nzt 7807 flag = MERGE( 1.0_wp, 0.0_wp, & 7808 BTEST( wall_flags_0(k,j,i), 0 ) ) 7839 DO k = nzb+1, nzt 7840 flag = MERGE( 1.0_wp, 0.0_wp, BTEST( wall_flags_0(k,j,i), 0 ) ) 7809 7841 sq(k,j,i) = sq(k,copied,i) * flag 7810 7842 ENDDO 7811 7843 ENDDO 7812 7844 ENDDO 7813 7845 7814 7846 ELSE 7815 WRITE(message_string,*) & 7816 'unknown decycling method: decycle_method (', & 7817 boundary, ') ="' // TRIM( decycle_method(boundary) ) // '"' 7818 CALL message( 'salsa_boundary_conds_decycle', 'SA0030', & 7819 1, 2, 0, 6, 0 ) 7847 WRITE(message_string,*) 'unknown decycling method: decycle_method (', boundary, & 7848 ') ="' // TRIM( decycle_method(boundary) ) // '"' 7849 CALL message( 'salsa_boundary_conds_decycle', 'PA0627', 1, 2, 0, 6, 0 ) 7820 7850 ENDIF 7821 7851 ENDDO 7822 ENDIF 7823 7852 ENDIF 7853 7824 7854 END SUBROUTINE salsa_boundary_conds_decycle 7825 7855 … … 7834 7864 7835 7865 IMPLICIT NONE 7836 7837 CHARACTER(len=*), INTENT(in) :: itype !< 'dry' or 'wet' 7866 7867 CHARACTER(len=*), INTENT(in) :: itype !< 'dry' or 'wet' 7868 7869 INTEGER(iwp) :: ic !< loop index for mass bin number 7870 INTEGER(iwp) :: iend !< end index: include water or not 7871 7838 7872 INTEGER(iwp), INTENT(in) :: ibin !< index of the chemical component 7839 7873 INTEGER(iwp), INTENT(in) :: i !< loop index for x-direction 7840 INTEGER(iwp), INTENT(in) :: j !< loop index for y-direction 7841 REAL(wp), DIMENSION(:), INTENT(out) :: mconc !< total dry or wet mass 7842 !< concentration 7843 7844 INTEGER(iwp) :: c !< loop index for mass bin number 7845 INTEGER(iwp) :: iend !< end index: include water or not 7846 7874 INTEGER(iwp), INTENT(in) :: j !< loop index for y-direction 7875 7876 REAL(wp), DIMENSION(:), INTENT(out) :: mconc !< total dry or wet mass concentration 7877 7847 7878 !-- Number of components 7848 7879 IF ( itype == 'dry' ) THEN 7849 iend = get_n_comp( prtcl )- 17880 iend = prtcl%ncomp - 1 7850 7881 ELSE IF ( itype == 'wet' ) THEN 7851 iend = get_n_comp( prtcl )7882 iend = prtcl%ncomp 7852 7883 ELSE 7853 STOP 1 ! "INFO for Developer: please use the message routine to pass the output string" bin_mixrat: Error in itype 7884 message_string = 'Error in itype!' 7885 CALL message( 'salsa_mod: bin_mixrat', 'PA0628', 2, 2, 0, 6, 0 ) 7854 7886 ENDIF 7855 7887 7856 7888 mconc = 0.0_wp 7857 7858 DO c = ibin, iend*nbins+ibin, nbins!< every nbins'th element7859 mconc = mconc + aerosol_mass( c)%conc(:,j,i)7889 7890 DO ic = ibin, iend*nbins_aerosol+ibin, nbins_aerosol !< every nbins'th element 7891 mconc = mconc + aerosol_mass(ic)%conc(:,j,i) 7860 7892 ENDDO 7861 7862 END SUBROUTINE bin_mixrat 7893 7894 END SUBROUTINE bin_mixrat 7895 7896 !------------------------------------------------------------------------------! 7897 ! Description: 7898 ! ------------ 7899 !> Sets surface fluxes 7900 !------------------------------------------------------------------------------! 7901 SUBROUTINE salsa_emission_update 7902 7903 USE control_parameters, & 7904 ONLY: time_since_reference_point 7905 7906 IMPLICIT NONE 7907 7908 IF ( time_since_reference_point >= skip_time_do_salsa ) THEN 7909 7910 IF ( next_aero_emission_update <= time_since_reference_point ) THEN 7911 CALL salsa_emission_setup( .FALSE. ) 7912 ENDIF 7913 7914 IF ( next_gas_emission_update <= time_since_reference_point ) THEN 7915 IF ( salsa_emission_mode == 'read_from_file' .AND. .NOT. salsa_gases_from_chem ) THEN 7916 CALL salsa_gas_emission_setup( .FALSE. ) 7917 ENDIF 7918 ENDIF 7919 7920 ENDIF 7921 7922 END SUBROUTINE salsa_emission_update 7863 7923 7864 7924 !------------------------------------------------------------------------------! … … 7866 7926 !> ------------ 7867 7927 !> Define aerosol fluxes: constant or read from a from file 7868 !------------------------------------------------------------------------------! 7869 SUBROUTINE salsa_set_source 7870 7871 ! USE date_and_time_mod, & 7872 ! ONLY: index_dd, index_hh, index_mm 7928 !> @todo - Emission stack height is not used yet. For default mode, emissions 7929 !> are assumed to occur on upward facing horizontal surfaces. 7930 !------------------------------------------------------------------------------! 7931 SUBROUTINE salsa_emission_setup( init ) 7932 7933 USE control_parameters, & 7934 ONLY: time_since_reference_point 7935 7936 USE date_and_time_mod, & 7937 ONLY: day_of_month, hour_of_day, index_dd, index_hh, index_mm, month_of_year, & 7938 time_default_indices, time_utc_init 7939 7940 USE netcdf_data_input_mod, & 7941 ONLY: check_existence, get_attribute, get_variable, inquire_num_variables, & 7942 inquire_variable_names, netcdf_data_input_get_dimension_length, open_read_file 7943 7944 USE surface_mod, & 7945 ONLY: surf_def_h, surf_lsm_h, surf_usm_h 7946 7947 IMPLICIT NONE 7948 7949 CHARACTER(LEN=80) :: daytype = 'workday' !< default day type 7950 CHARACTER(LEN=25) :: in_name !< name of a gas in the input file 7951 CHARACTER(LEN=25) :: mod_name !< name in the input file 7952 7953 INTEGER(iwp) :: ib !< loop index: aerosol number bins 7954 INTEGER(iwp) :: ic !< loop index: aerosol chemical components 7955 INTEGER(iwp) :: id_salsa !< NetCDF id of aerosol emission input file 7956 INTEGER(iwp) :: in !< loop index: emission category 7957 INTEGER(iwp) :: inn !< loop index 7958 INTEGER(iwp) :: ss !< loop index 7959 7960 INTEGER(iwp), DIMENSION(maxspec) :: cc_i2m !< 7961 7962 LOGICAL :: netcdf_extend = .FALSE. !< NetCDF input file exists 7963 7964 LOGICAL, INTENT(in) :: init !< if .TRUE. --> initialisation call 7965 7966 REAL(wp), DIMENSION(:), ALLOCATABLE :: nsect_emission !< sectional number emission 7967 7968 REAL(wp), DIMENSION(:,:,:), ALLOCATABLE :: source_array !< temporary source array 7969 7970 ! 7971 !-- Allocate source arrays: 7972 DO ib = 1, nbins_aerosol 7973 IF ( init ) ALLOCATE( aerosol_number(ib)%source(nys:nyn,nxl:nxr) ) 7974 aerosol_number(ib)%source = 0.0_wp 7975 ENDDO 7976 7977 DO ic = 1, ncomponents_mass * nbins_aerosol 7978 IF ( init ) ALLOCATE( aerosol_mass(ic)%source(nys:nyn,nxl:nxr) ) 7979 aerosol_mass(ic)%source = 0.0_wp 7980 ENDDO 7981 7982 ! 7983 !-- Define emissions: 7984 7985 SELECT CASE ( salsa_emission_mode ) 7986 7987 CASE ( 'uniform' ) 7988 7989 IF ( init ) THEN ! Do only once 7990 ! 7991 !- Form a sectional size distribution for the emissions 7992 ALLOCATE( nsect_emission(1:nbins_aerosol), & 7993 source_array(nys:nyn,nxl:nxr,1:nbins_aerosol) ) 7994 ! 7995 !-- Precalculate a size distribution for the emission based on the mean diameter, standard 7996 !-- deviation and number concentration per each log-normal mode 7997 CALL size_distribution( surface_aerosol_flux, aerosol_flux_dpg, aerosol_flux_sigmag, & 7998 nsect_emission ) 7999 DO ib = 1, nbins_aerosol 8000 source_array(:,:,ib) = nsect_emission(ib) 8001 ENDDO 8002 ! 8003 !-- Check which chemical components are used 8004 cc_i2m = 0 8005 IF ( index_so4 > 0 ) cc_i2m(1) = index_so4 8006 IF ( index_oc > 0 ) cc_i2m(2) = index_oc 8007 IF ( index_bc > 0 ) cc_i2m(3) = index_bc 8008 IF ( index_du > 0 ) cc_i2m(4) = index_du 8009 IF ( index_ss > 0 ) cc_i2m(5) = index_ss 8010 IF ( index_no > 0 ) cc_i2m(6) = index_no 8011 IF ( index_nh > 0 ) cc_i2m(7) = index_nh 8012 ! 8013 !-- Normalise mass fractions so that their sum is 1 8014 aerosol_flux_mass_fracs_a = aerosol_flux_mass_fracs_a / & 8015 SUM( aerosol_flux_mass_fracs_a(1:ncc ) ) 8016 ! 8017 !-- Set uniform fluxes of default horizontal surfaces 8018 CALL set_flux( surf_def_h(0), cc_i2m, aerosol_flux_mass_fracs_a, source_array ) 8019 ! 8020 !-- Subrange 2b: 8021 IF ( SUM( aerosol_flux_mass_fracs_b ) > 0.0_wp ) THEN 8022 CALL location_message( ' salsa_emission_setup: emissions are soluble!', .TRUE. ) 8023 ENDIF 8024 8025 DEALLOCATE( nsect_emission, source_array ) 8026 ENDIF 8027 8028 CASE ( 'parameterized' ) 8029 ! 8030 !-- TO DO 8031 8032 CASE ( 'read_from_file' ) 8033 ! 8034 !-- Reset surface fluxes 8035 surf_def_h(0)%answs = 0.0_wp 8036 surf_def_h(0)%amsws = 0.0_wp 8037 surf_lsm_h%answs = 0.0_wp 8038 surf_lsm_h%amsws = 0.0_wp 8039 surf_usm_h%answs = 0.0_wp 8040 surf_usm_h%amsws = 0.0_wp 8041 7873 8042 #if defined( __netcdf ) 7874 USE NETCDF 7875 7876 USE netcdf_data_input_mod, & 7877 ONLY: get_attribute, get_variable, & 7878 netcdf_data_input_get_dimension_length, open_read_file 7879 7880 USE surface_mod, & 7881 ONLY: surf_def_h, surf_lsm_h, surf_usm_h 7882 7883 IMPLICIT NONE 7884 7885 INTEGER(iwp), PARAMETER :: ndm = 3 !< number of default modes 7886 INTEGER(iwp), PARAMETER :: ndc = 4 !< number of default categories 7887 7888 CHARACTER (LEN=10) :: unita !< Unit of aerosol fluxes 7889 CHARACTER (LEN=10) :: unitg !< Unit of gaseous fluxes 7890 INTEGER(iwp) :: b !< loop index: aerosol number bins 7891 INTEGER(iwp) :: c !< loop index: aerosol chemical components 7892 INTEGER(iwp) :: ee !< loop index: end 7893 INTEGER(iwp), ALLOCATABLE, DIMENSION(:) :: eci !< emission category index 7894 INTEGER(iwp) :: g !< loop index: gaseous tracers 7895 INTEGER(iwp) :: i !< loop index: x-direction 7896 INTEGER(iwp) :: id_faero !< NetCDF id of aerosol source input file 7897 INTEGER(iwp) :: id_fchem !< NetCDF id of aerosol source input file 7898 INTEGER(iwp) :: id_sa !< NetCDF id of variable: source 7899 INTEGER(iwp) :: j !< loop index: y-direction 7900 INTEGER(iwp) :: k !< loop index: z-direction 7901 INTEGER(iwp) :: n_dt !< number of time steps in the emission file 7902 INTEGER(iwp) :: nc_stat !< local variable for storing the result of 7903 !< netCDF calls for error message handling 7904 INTEGER(iwp) :: nb_file !< Number of grid-points in file (bins) 7905 INTEGER(iwp) :: ncat !< Number of emission categories 7906 INTEGER(iwp) :: ng_file !< Number of grid-points in file (gases) 7907 INTEGER(iwp) :: nz_file !< number of grid-points in file 7908 INTEGER(iwp) :: n !< loop index 7909 INTEGER(iwp) :: ni !< loop index 7910 INTEGER(iwp) :: ss !< loop index 7911 LOGICAL :: netcdf_extend = .FALSE. !< Flag indicating wether netcdf 7912 !< topography input file or not 7913 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:,:) :: dum_var_4d !< variable for 7914 !< temporary data 7915 REAL(wp) :: fillval !< fill value 7916 REAL(wp) :: flag !< flag to mask topography grid points 7917 REAL(wp), DIMENSION(nbins) :: nsect_emission !< sectional emission (lod1) 7918 REAL(wp), ALLOCATABLE, DIMENSION(:,:,:) :: pm_emission !< aerosol mass 7919 !< emission (lod1) 7920 REAL(wp), DIMENSION(nbins) :: source_ijka !< aerosol source at (k,j,i) 7921 ! 7922 !-- The default size distribution and mass composition per emission category: 7923 !-- 1 = traffic, 2 = road dust, 3 = wood combustion, 4 = other 7924 !-- Mass fractions: H2SO4, OC, BC, DU, SS, HNO3, NH3 7925 ! CHARACTER(LEN=15), DIMENSION(ndc) :: cat_name_table = &!< emission category 7926 ! (/'road traffic ','road dust ',& 7927 ! 'wood combustion','other '/) 7928 REAL(wp), DIMENSION(ndc) :: avg_density !< average density 7929 REAL(wp), DIMENSION(ndc) :: conversion_factor !< unit conversion factor 7930 !< for aerosol emissions 7931 REAL(wp), DIMENSION(ndm), PARAMETER :: dpg_table = & !< mean diameter (mum) 7932 (/ 13.5E-3_wp, 1.4_wp, 5.4E-2_wp/) 7933 REAL(wp), DIMENSION(ndm) :: ntot_table 7934 REAL(wp), DIMENSION(maxspec,ndc), PARAMETER :: mass_fraction_table = & 7935 RESHAPE( (/ 0.04_wp, 0.48_wp, 0.48_wp, 0.0_wp, 0.0_wp, 0.0_wp, 0.0_wp, & 7936 0.0_wp, 0.05_wp, 0.0_wp, 0.95_wp, 0.0_wp, 0.0_wp, 0.0_wp, & 7937 0.0_wp, 0.5_wp, 0.5_wp, 0.0_wp, 0.0_wp, 0.0_wp, 0.0_wp, & 7938 0.0_wp, 0.5_wp, 0.5_wp, 0.0_wp, 0.0_wp, 0.0_wp, 0.0_wp & 7939 /), (/maxspec,ndc/) ) 7940 REAL(wp), DIMENSION(ndm,ndc), PARAMETER :: PMfrac_table = & !< rel. mass 7941 RESHAPE( (/ 0.016_wp, 0.000_wp, 0.984_wp, & 7942 0.000_wp, 1.000_wp, 0.000_wp, & 7943 0.000_wp, 0.000_wp, 1.000_wp, & 7944 1.000_wp, 0.000_wp, 1.000_wp & 7945 /), (/ndm,ndc/) ) 7946 REAL(wp), DIMENSION(ndm), PARAMETER :: sigmag_table = & !< mode std 7947 (/1.6_wp, 1.4_wp, 1.7_wp/) 7948 avg_density = 1.0_wp 7949 nb_file = 0 7950 ng_file = 0 7951 nsect_emission = 0.0_wp 7952 nz_file = 0 7953 source_ijka = 0.0_wp 7954 ! 7955 !-- First gases, if needed: 7956 IF ( .NOT. salsa_gases_from_chem ) THEN 7957 ! 7958 !-- Read sources from PIDS_CHEM 7959 INQUIRE( FILE='PIDS_CHEM' // TRIM( coupling_char ), EXIST=netcdf_extend ) 7960 IF ( .NOT. netcdf_extend ) THEN 7961 message_string = 'Input file '// TRIM( 'PIDS_CHEM' ) // & 7962 TRIM( coupling_char ) // ' for SALSA missing!' 7963 CALL message( 'salsa_mod: salsa_set_source', 'SA0027', 1, 2, 0, 6, 0 ) 7964 ENDIF ! netcdf_extend 7965 7966 CALL location_message( ' salsa_set_source: NOTE! Gaseous emissions'//& 7967 ' should be provided with following emission indices:'// & 7968 ' 1=H2SO4, 2=HNO3, 3=NH3, 4=OCNV, 5=OCSV', .TRUE. ) 7969 CALL location_message( ' salsa_set_source: No time dependency for '//& 7970 'gaseous emissions. Use emission_values '// & 7971 'directly.', .TRUE. ) 7972 ! 7973 !-- Open PIDS_CHEM in read-only mode 7974 CALL open_read_file( 'PIDS_CHEM' // TRIM( coupling_char ), id_fchem ) 7975 ! 7976 !-- Inquire the level of detail (lod) 7977 CALL get_attribute( id_fchem, 'lod', lod_gases, .FALSE., & 7978 "emission_values" ) 7979 7980 IF ( lod_gases == 2 ) THEN 7981 ! 7982 !-- Index of gaseous compounds 7983 CALL netcdf_data_input_get_dimension_length( id_fchem, ng_file, & 7984 "nspecies" ) 7985 IF ( ng_file < 5 ) THEN 7986 message_string = 'Some gaseous emissions missing.' 7987 CALL message( 'salsa_mod: salsa_set_source', 'SA0041', & 7988 1, 2, 0, 6, 0 ) 7989 ENDIF 7990 ! 7991 !-- Get number of emission categories 7992 CALL netcdf_data_input_get_dimension_length( id_fchem, ncat, "ncat" ) 7993 ! 7994 !-- Inquire the unit of gaseous fluxes 7995 CALL get_attribute( id_fchem, 'units', unitg, .FALSE., & 7996 "emission_values") 7997 ! 7998 !-- Inquire the fill value 7999 CALL get_attribute( id_fchem, '_FillValue', fillval, .FALSE., & 8000 "emission_values" ) 8001 ! 8002 !-- Read surface emission data (x,y) PE-wise 8003 ALLOCATE( dum_var_4d(ng_file,ncat,nys:nyn,nxl:nxr) ) 8004 CALL get_variable( id_fchem, 'emission_values', dum_var_4d, nxl, nxr,& 8005 nys, nyn, 0, ncat-1, 0, ng_file-1 ) 8006 DO g = 1, ngast 8007 ALLOCATE( salsa_gas(g)%source(ncat,nys:nyn,nxl:nxr) ) 8008 salsa_gas(g)%source = 0.0_wp 8009 salsa_gas(g)%source = salsa_gas(g)%source + dum_var_4d(g,:,:,:) 8010 ENDDO 8011 ! 8012 !-- Set surface fluxes of gaseous compounds on horizontal surfaces. 8013 !-- Set fluxes only for either default, land or urban surface. 8014 IF ( .NOT. land_surface .AND. .NOT. urban_surface ) THEN 8015 CALL set_gas_flux( surf_def_h(0), ncat, unitg ) 8016 ELSE 8017 CALL set_gas_flux( surf_lsm_h, ncat, unitg ) 8018 CALL set_gas_flux( surf_usm_h, ncat, unitg ) 8043 IF ( init ) THEN 8044 ! 8045 !-- Check existence of PIDS_SALSA file 8046 INQUIRE( FILE = input_file_salsa // TRIM( coupling_char ), EXIST = netcdf_extend ) 8047 IF ( .NOT. netcdf_extend ) THEN 8048 message_string = 'Input file '// TRIM( input_file_salsa ) // TRIM( coupling_char )& 8049 // ' missing!' 8050 CALL message( 'salsa_emission_setup', 'PA0629', 1, 2, 0, 6, 0 ) 8051 ENDIF 8052 ! 8053 !-- Open file in read-only mode 8054 CALL open_read_file( input_file_salsa // TRIM( coupling_char ), id_salsa ) 8055 ! 8056 !-- Read the index and name of chemical components 8057 CALL netcdf_data_input_get_dimension_length( id_salsa, aero_emission_att%ncc, & 8058 'composition_index' ) 8059 ALLOCATE( aero_emission_att%cc_index(1:aero_emission_att%ncc) ) 8060 CALL get_variable( id_salsa, 'composition_index', aero_emission_att%cc_index ) 8061 CALL get_variable( id_salsa, 'composition_name', aero_emission_att%cc_name, & 8062 aero_emission_att%ncc ) 8063 ! 8064 !-- Find the corresponding chemical components in the model 8065 aero_emission_att%cc_input_to_model = 0 8066 DO ic = 1, aero_emission_att%ncc 8067 in_name = aero_emission_att%cc_name(ic) 8068 SELECT CASE ( TRIM( in_name ) ) 8069 CASE ( 'H2SO4', 'h2so4', 'SO4', 'so4' ) 8070 aero_emission_att%cc_input_to_model(1) = ic 8071 CASE ( 'OC', 'oc', 'organics' ) 8072 aero_emission_att%cc_input_to_model(2) = ic 8073 CASE ( 'BC', 'bc' ) 8074 aero_emission_att%cc_input_to_model(3) = ic 8075 CASE ( 'DU', 'du' ) 8076 aero_emission_att%cc_input_to_model(4) = ic 8077 CASE ( 'SS', 'ss' ) 8078 aero_emission_att%cc_input_to_model(5) = ic 8079 CASE ( 'HNO3', 'hno3', 'NO', 'no' ) 8080 aero_emission_att%cc_input_to_model(6) = ic 8081 CASE ( 'NH3', 'nh3', 'NH', 'nh' ) 8082 aero_emission_att%cc_input_to_model(7) = ic 8083 END SELECT 8084 8085 ENDDO 8086 8087 IF ( SUM( aero_emission_att%cc_input_to_model ) == 0 ) THEN 8088 message_string = 'None of the aerosol chemical components in ' // TRIM( & 8089 input_file_salsa ) // ' correspond to the ones applied in SALSA.' 8090 CALL message( 'salsa_emission_setup', 'PA0630', 1, 2, 0, 6, 0 ) 8091 ENDIF 8092 ! 8093 !-- Inquire the fill value 8094 CALL get_attribute( id_salsa, '_FillValue', aero_emission%fill, .FALSE., & 8095 'aerosol_emission_values' ) 8096 ! 8097 !-- Inquire units of emissions 8098 CALL get_attribute( id_salsa, 'units', aero_emission_att%units, .FALSE., & 8099 'aerosol_emission_values' ) 8100 ! 8101 !-- Inquire the level of detail (lod) 8102 CALL get_attribute( id_salsa, 'lod', aero_emission_att%lod, .FALSE., & 8103 'aerosol_emission_values' ) 8104 ! 8105 !-- Variable names 8106 CALL inquire_num_variables( id_salsa, aero_emission_att%num_vars ) 8107 ALLOCATE( aero_emission_att%var_names(1:aero_emission_att%num_vars) ) 8108 CALL inquire_variable_names( id_salsa, aero_emission_att%var_names ) 8109 8110 ! 8111 !-- Read different emission information depending on the level of detail of emissions: 8112 8113 ! 8114 !-- Default mode: 8115 IF ( aero_emission_att%lod == 1 ) THEN 8116 ! 8117 !-- Unit conversion factor: convert to SI units (kg/m2/s) 8118 IF ( aero_emission_att%units == 'kg/m2/yr' ) THEN 8119 aero_emission_att%conversion_factor = 1.0_wp / 3600.0_wp 8120 ELSEIF ( aero_emission_att%units == 'g/m2/yr' ) THEN 8121 aero_emission_att%conversion_factor = 0.001_wp / 3600.0_wp 8122 ELSE 8123 message_string = 'unknown unit for aerosol emissions: ' // & 8124 TRIM( aero_emission_att%units ) // ' (lod1)' 8125 CALL message( 'salsa_emission_setup','PA0631', 1, 2, 0, 6, 0 ) 8126 ENDIF 8127 ! 8128 !-- Get number of emission categories and allocate emission arrays 8129 CALL netcdf_data_input_get_dimension_length( id_salsa, aero_emission_att%ncat, & 8130 'ncat' ) 8131 ALLOCATE( aero_emission_att%cat_index(1:aero_emission_att%ncat), & 8132 aero_emission_att%rho(1:aero_emission_att%ncat), & 8133 aero_emission_att%time_factor(1:aero_emission_att%ncat) ) 8134 ! 8135 !-- Get emission category names and indices 8136 CALL get_variable( id_salsa, 'emission_category_name', aero_emission_att%cat_name, & 8137 aero_emission_att%ncat) 8138 CALL get_variable( id_salsa, 'emission_category_index', aero_emission_att%cat_index ) 8139 ! 8140 !-- Find corresponding emission categories 8141 DO in = 1, aero_emission_att%ncat 8142 in_name = aero_emission_att%cat_name(in) 8143 DO ss = 1, def_modes%ndc 8144 mod_name = def_modes%cat_name_table(ss) 8145 IF ( TRIM( in_name(1:4) ) == TRIM( mod_name(1:4 ) ) ) THEN 8146 def_modes%cat_input_to_model(ss) = in 8147 ENDIF 8148 ENDDO 8149 ENDDO 8150 8151 IF ( SUM( def_modes%cat_input_to_model ) == 0 ) THEN 8152 message_string = 'None of the emission categories in ' // TRIM( & 8153 input_file_salsa ) // ' match with the ones in the model.' 8154 CALL message( 'salsa_emission_setup', 'PA0632', 1, 2, 0, 6, 0 ) 8155 ENDIF 8156 ! 8157 !-- Emission time factors: Find check whether emission time factors are given for each 8158 !-- hour of year OR based on month, day and hour 8159 ! 8160 !-- For each hour of year: 8161 IF ( check_existence( aero_emission_att%var_names, 'nhoursyear' ) ) THEN 8162 CALL netcdf_data_input_get_dimension_length( id_salsa, aero_emission_att%nhoursyear,& 8163 'nhoursyear' ) 8164 ALLOCATE( aero_emission_att%etf(1:aero_emission_att%ncat, & 8165 1:aero_emission_att%nhoursyear) ) 8166 CALL get_variable( id_salsa, 'emission_time_factors', aero_emission_att%etf, & 8167 0, aero_emission_att%nhoursyear-1, 0, aero_emission_att%ncat-1 ) 8168 ! 8169 !-- Based on the month, day and hour: 8170 ELSEIF ( check_existence( aero_emission_att%var_names, 'nmonthdayhour' ) ) THEN 8171 CALL netcdf_data_input_get_dimension_length( id_salsa, & 8172 aero_emission_att%nmonthdayhour, & 8173 'nmonthdayhour' ) 8174 ALLOCATE( aero_emission_att%etf(1:aero_emission_att%ncat, & 8175 1:aero_emission_att%nmonthdayhour) ) 8176 CALL get_variable( id_salsa, 'emission_time_factors', aero_emission_att%etf, & 8177 0, aero_emission_att%nmonthdayhour-1, 0, aero_emission_att%ncat-1 ) 8178 ELSE 8179 message_string = 'emission_time_factors should be given for each nhoursyear ' //& 8180 'OR nmonthdayhour' 8181 CALL message( 'salsa_emission_setup','PA0633', 1, 2, 0, 6, 0 ) 8182 ENDIF 8183 ! 8184 !-- Next emission update 8185 next_aero_emission_update = MOD( time_utc_init, 3600.0_wp ) - 3600.0_wp 8186 ! 8187 !-- Get chemical composition (i.e. mass fraction of different species) in aerosols 8188 ALLOCATE( aero_emission%def_mass_fracs(1:aero_emission_att%ncat, & 8189 1:aero_emission_att%ncc) ) 8190 aero_emission%def_mass_fracs = 0.0_wp 8191 CALL get_variable( id_salsa, 'emission_mass_fracs', aero_emission%def_mass_fracs, & 8192 0, aero_emission_att%ncc-1, 0, aero_emission_att%ncat-1 ) 8193 ! 8194 !-- If the chemical component is not activated, set its mass fraction to 0 to avoid 8195 !-- inbalance between number and mass flux 8196 cc_i2m = aero_emission_att%cc_input_to_model 8197 IF ( index_so4 < 0 .AND. cc_i2m(1) /= 0 ) & 8198 aero_emission%def_mass_fracs(:,cc_i2m(1)) = 0.0_wp 8199 IF ( index_oc < 0 .AND. cc_i2m(2) /= 0 ) & 8200 aero_emission%def_mass_fracs(:,cc_i2m(2)) = 0.0_wp 8201 IF ( index_bc < 0 .AND. cc_i2m(3) /= 0 ) & 8202 aero_emission%def_mass_fracs(:,cc_i2m(3)) = 0.0_wp 8203 IF ( index_du < 0 .AND. cc_i2m(4) /= 0 ) & 8204 aero_emission%def_mass_fracs(:,cc_i2m(4)) = 0.0_wp 8205 IF ( index_ss < 0 .AND. cc_i2m(5) /= 0 ) & 8206 aero_emission%def_mass_fracs(:,cc_i2m(5)) = 0.0_wp 8207 IF ( index_no < 0 .AND. cc_i2m(6) /= 0 ) & 8208 aero_emission%def_mass_fracs(:,cc_i2m(6)) = 0.0_wp 8209 IF ( index_nh < 0 .AND. cc_i2m(7) /= 0 ) & 8210 aero_emission%def_mass_fracs(:,cc_i2m(7)) = 0.0_wp 8211 ! 8212 !-- Then normalise the mass fraction so that SUM = 1 8213 DO in = 1, aero_emission_att%ncat 8214 aero_emission%def_mass_fracs(in,:) = aero_emission%def_mass_fracs(in,:) / & 8215 SUM( aero_emission%def_mass_fracs(in,:) ) 8216 ENDDO 8217 ! 8218 !-- Calculate average mass density (kg/m3) 8219 aero_emission_att%rho = 0.0_wp 8220 8221 IF ( cc_i2m(1) /= 0 ) aero_emission_att%rho = aero_emission_att%rho + arhoh2so4 *& 8222 aero_emission%def_mass_fracs(:,cc_i2m(1)) 8223 IF ( cc_i2m(2) /= 0 ) aero_emission_att%rho = aero_emission_att%rho + arhooc * & 8224 aero_emission%def_mass_fracs(:,cc_i2m(2)) 8225 IF ( cc_i2m(3) /= 0 ) aero_emission_att%rho = aero_emission_att%rho + arhobc * & 8226 aero_emission%def_mass_fracs(:,cc_i2m(3)) 8227 IF ( cc_i2m(4) /= 0 ) aero_emission_att%rho = aero_emission_att%rho + arhodu * & 8228 aero_emission%def_mass_fracs(:,cc_i2m(4)) 8229 IF ( cc_i2m(5) /= 0 ) aero_emission_att%rho = aero_emission_att%rho + arhoss * & 8230 aero_emission%def_mass_fracs(:,cc_i2m(5)) 8231 IF ( cc_i2m(6) /= 0 ) aero_emission_att%rho = aero_emission_att%rho + arhohno3 * & 8232 aero_emission%def_mass_fracs(:,cc_i2m(6)) 8233 IF ( cc_i2m(7) /= 0 ) aero_emission_att%rho = aero_emission_att%rho + arhonh3 * & 8234 aero_emission%def_mass_fracs(:,cc_i2m(7)) 8235 ! 8236 !-- Allocate and read surface emission data (in total PM) 8237 ALLOCATE( aero_emission%def_data(nys:nyn,nxl:nxr,1:aero_emission_att%ncat) ) 8238 CALL get_variable( id_salsa, 'aerosol_emission_values', aero_emission%def_data, & 8239 0, aero_emission_att%ncat-1, nxl, nxr, nys, nyn ) 8240 8241 ! 8242 !-- Pre-processed mode 8243 ELSEIF ( aero_emission_att%lod == 2 ) THEN 8244 ! 8245 !-- Unit conversion factor: convert to SI units (#/m2/s) 8246 IF ( aero_emission_att%units == '#/m2/s' ) THEN 8247 aero_emission_att%conversion_factor = 1.0_wp 8248 ELSE 8249 message_string = 'unknown unit for aerosol emissions: ' // & 8250 TRIM( aero_emission_att%units ) 8251 CALL message( 'salsa_emission_setup','PA0634', 1, 2, 0, 6, 0 ) 8252 ENDIF 8253 ! 8254 !-- Number of aerosol size bins in the emission data 8255 CALL netcdf_data_input_get_dimension_length( id_salsa, aero_emission_att%nbins, & 8256 'Dmid' ) 8257 IF ( aero_emission_att%nbins /= nbins_aerosol ) THEN 8258 message_string = 'The number of size bins in aerosol input data does not ' // & 8259 'correspond to the model set-up' 8260 CALL message( 'salsa_emission_setup','PA0635', 1, 2, 0, 6, 0 ) 8261 ENDIF 8262 ! 8263 !-- Number of time steps in the emission data 8264 CALL netcdf_data_input_get_dimension_length( id_salsa, aero_emission_att%nt, 'time') 8265 ! 8266 !-- Allocate bin diameters, time and mass fraction array 8267 ALLOCATE( aero_emission_att%dmid(1:nbins_aerosol), & 8268 aero_emission_att%time(1:aero_emission_att%nt), & 8269 aero_emission%preproc_mass_fracs(1:aero_emission_att%ncc) ) 8270 ! 8271 !-- Read mean diameters 8272 CALL get_variable( id_salsa, 'Dmid', aero_emission_att%dmid ) 8273 ! 8274 !-- Check whether the sectional representation of the aerosol size distribution conform 8275 !-- to the one applied in the model 8276 IF ( ANY( ABS( ( aero(1:nbins_aerosol)%dmid - aero_emission_att%dmid ) / & 8277 aero(1:nbins_aerosol)%dmid ) > 0.1_wp ) ) THEN 8278 message_string = 'Mean diameters of size bins in ' // TRIM( input_file_salsa ) & 8279 // ' do not match with the ones in the model.' 8280 CALL message( 'salsa_emission_setup','PA0636', 1, 2, 0, 6, 0 ) 8281 ENDIF 8282 ! 8283 !-- Read time stamps: 8284 CALL get_variable( id_salsa, 'time', aero_emission_att%time ) 8285 ! 8286 !-- Read emission mass fractions 8287 CALL get_variable( id_salsa, 'emission_mass_fracs', aero_emission%preproc_mass_fracs ) 8288 ! 8289 !-- If the chemical component is not activated, set its mass fraction to 0 8290 cc_i2m = aero_emission_att%cc_input_to_model 8291 IF ( index_so4 < 0 .AND. cc_i2m(1) /= 0 ) & 8292 aero_emission%preproc_mass_fracs(cc_i2m(1)) = 0.0_wp 8293 IF ( index_oc < 0 .AND. cc_i2m(2) /= 0 ) & 8294 aero_emission%preproc_mass_fracs(cc_i2m(2)) = 0.0_wp 8295 IF ( index_bc < 0 .AND. cc_i2m(3) /= 0 ) & 8296 aero_emission%preproc_mass_fracs(cc_i2m(3)) = 0.0_wp 8297 IF ( index_du < 0 .AND. cc_i2m(4) /= 0 ) & 8298 aero_emission%preproc_mass_fracs(cc_i2m(4)) = 0.0_wp 8299 IF ( index_ss < 0 .AND. cc_i2m(5) /= 0 ) & 8300 aero_emission%preproc_mass_fracs(cc_i2m(5)) = 0.0_wp 8301 IF ( index_no < 0 .AND. cc_i2m(6) /= 0 ) & 8302 aero_emission%preproc_mass_fracs(cc_i2m(6)) = 0.0_wp 8303 IF ( index_nh < 0 .AND. cc_i2m(7) /= 0 ) & 8304 aero_emission%preproc_mass_fracs(cc_i2m(7)) = 0.0_wp 8305 ! 8306 !-- Then normalise the mass fraction so that SUM = 1 8307 aero_emission%preproc_mass_fracs = aero_emission%preproc_mass_fracs / & 8308 SUM( aero_emission%preproc_mass_fracs ) 8309 8310 ELSE 8311 message_string = 'Unknown lod for aerosol_emission_values.' 8312 CALL message( 'salsa_emission','PA0637', 1, 2, 0, 6, 0 ) 8313 ENDIF 8314 8315 ENDIF ! init 8316 ! 8317 !-- Define and set current emission values: 8318 ! 8319 !-- Default type emissions (aerosol emission given as total mass emission per year): 8320 IF ( aero_emission_att%lod == 1 ) THEN 8321 ! 8322 !-- Emission time factors for each emission category at current time step 8323 IF ( aero_emission_att%nhoursyear > aero_emission_att%nmonthdayhour ) THEN 8324 ! 8325 !-- Get the index of the current hour 8326 CALL time_default_indices( month_of_year, day_of_month, hour_of_day, index_hh ) 8327 aero_emission_att%time_factor = aero_emission_att%etf(:,index_hh) 8328 8329 ELSEIF ( aero_emission_att%nhoursyear < aero_emission_att%nmonthdayhour ) THEN 8330 ! 8331 !-- Get the index of current hour (index_hh) (TODO: Now "workday" is always assumed. 8332 !-- Needs to be calculated.) 8333 CALL time_default_indices( daytype, month_of_year, day_of_month, hour_of_day, & 8334 index_mm, index_dd, index_hh ) 8335 aero_emission_att%time_factor = aero_emission_att%etf(:,index_mm) * & 8336 aero_emission_att%etf(:,index_dd) * & 8337 aero_emission_att%etf(:,index_hh) 8338 ENDIF 8339 8340 ! 8341 !-- Create a sectional number size distribution for emissions 8342 ALLOCATE( nsect_emission(1:nbins_aerosol),source_array(nys:nyn,nxl:nxr,1:nbins_aerosol) ) 8343 DO in = 1, aero_emission_att%ncat 8344 8345 inn = def_modes%cat_input_to_model(in) 8346 ! 8347 !-- Calculate the number concentration (1/m3) of a log-normal size distribution 8348 !-- following Jacobson (2005): Eq 13.25. 8349 def_modes%ntot_table = 6.0_wp * def_modes%pm_frac_table(:,inn) / ( pi * & 8350 ( def_modes%dpg_table )**3 * EXP( 4.5_wp * & 8351 LOG( def_modes%sigmag_table )**2 ) ) 8352 ! 8353 !-- Sectional size distibution (1/m3) from a log-normal one 8354 CALL size_distribution( def_modes%ntot_table, def_modes%dpg_table, & 8355 def_modes%sigmag_table, nsect_emission ) 8356 8357 source_array = 0.0_wp 8358 DO ib = 1, nbins_aerosol 8359 source_array(:,:,ib) = aero_emission%def_data(:,:,in) * & 8360 aero_emission_att%conversion_factor / & 8361 aero_emission_att%rho(in) * nsect_emission(ib) * & 8362 aero_emission_att%time_factor(in) 8363 ENDDO 8364 ! 8365 !-- Set surface fluxes of aerosol number and mass on horizontal surfaces. Set fluxes 8366 !-- only for either default, land or urban surface. 8367 IF ( .NOT. land_surface .AND. .NOT. urban_surface ) THEN 8368 CALL set_flux( surf_def_h(0), aero_emission_att%cc_input_to_model, & 8369 aero_emission%def_mass_fracs(in,:), source_array ) 8370 ELSE 8371 CALL set_flux( surf_usm_h, aero_emission_att%cc_input_to_model, & 8372 aero_emission%def_mass_fracs(in,:), source_array ) 8373 CALL set_flux( surf_lsm_h, aero_emission_att%cc_input_to_model, & 8374 aero_emission%def_mass_fracs(in,:), source_array ) 8375 ENDIF 8376 ENDDO 8377 ! 8378 !-- The next emission update is again after one hour 8379 next_aero_emission_update = next_aero_emission_update + 3600.0_wp 8380 8381 8382 DEALLOCATE( source_array ) 8383 ! 8384 !-- Pre-processed: 8385 ELSEIF ( aero_emission_att%lod == 2 ) THEN 8386 ! 8387 !-- Obtain time index for current input starting at 0. 8388 !-- @todo: At the moment emission data and simulated time correspond to each other. 8389 aero_emission_att%tind = MINLOC( ABS( aero_emission_att%time - & 8390 time_since_reference_point ), DIM = 1 ) - 1 8391 ! 8392 !-- Allocate the data input array always before reading in the data and deallocate after 8393 ALLOCATE( aero_emission%preproc_data(nys:nyn,nxl:nxr,1:nbins_aerosol) ) 8394 ! 8395 !-- Read in the next time step 8396 CALL get_variable( id_salsa, 'aerosol_emission_values', aero_emission%preproc_data,& 8397 aero_emission_att%tind, 0, nbins_aerosol-1, nxl, nxr, nys, nyn ) 8398 ! 8399 !-- Set surface fluxes of aerosol number and mass on horizontal surfaces. Set fluxes only 8400 !-- for either default, land and urban surface. 8401 IF ( .NOT. land_surface .AND. .NOT. urban_surface ) THEN 8402 CALL set_flux( surf_def_h(0), aero_emission_att%cc_input_to_model, & 8403 aero_emission%preproc_mass_fracs, aero_emission%preproc_data ) 8404 ELSE 8405 CALL set_flux( surf_usm_h, aero_emission_att%cc_input_to_model, & 8406 aero_emission%preproc_mass_fracs, aero_emission%preproc_data ) 8407 CALL set_flux( surf_lsm_h, aero_emission_att%cc_input_to_model, & 8408 aero_emission%preproc_mass_fracs, aero_emission%preproc_data ) 8409 ENDIF 8410 ! 8411 !-- Determine the next emission update 8412 next_aero_emission_update = aero_emission_att%time(aero_emission_att%tind+2) 8413 8414 DEALLOCATE( aero_emission%preproc_data ) 8415 8019 8416 ENDIF 8020 8021 DEALLOCATE( dum_var_4d ) 8022 DO g = 1, ngast 8023 DEALLOCATE( salsa_gas(g)%source ) 8024 ENDDO 8025 ELSE 8026 message_string = 'Input file PIDS_CHEM needs to have lod = 2 when '//& 8027 'SALSA is applied but not the chemistry module!' 8028 CALL message( 'salsa_mod: salsa_set_source', 'SA0039', 1, 2, 0, 6, 0 ) 8029 ENDIF 8030 ENDIF 8031 ! 8032 !-- Read sources from PIDS_SALSA 8033 INQUIRE( FILE='PIDS_SALSA' // TRIM( coupling_char ), EXIST=netcdf_extend ) 8034 IF ( .NOT. netcdf_extend ) THEN 8035 message_string = 'Input file '// TRIM( 'PIDS_SALSA' ) // & 8036 TRIM( coupling_char ) // ' for SALSA missing!' 8037 CALL message( 'salsa_mod: salsa_set_source', 'SA0034', 1, 2, 0, 6, 0 ) 8038 ENDIF ! netcdf_extend 8039 ! 8040 !-- Open file in read-only mode 8041 CALL open_read_file( 'PIDS_SALSA' // TRIM( coupling_char ), id_faero ) 8042 ! 8043 !-- Get number of emission categories and their indices 8044 CALL netcdf_data_input_get_dimension_length( id_faero, ncat, "ncat" ) 8045 ! 8046 !-- Get emission category indices 8047 ALLOCATE( eci(1:ncat) ) 8048 CALL get_variable( id_faero, 'emission_category_index', eci ) 8049 ! 8050 !-- Inquire the level of detail (lod) 8051 CALL get_attribute( id_faero, 'lod', lod_aero, .FALSE., & 8052 "aerosol_emission_values" ) 8053 8054 IF ( lod_aero < 3 .AND. ibc_salsa_b == 0 ) THEN 8055 message_string = 'lod1/2 for aerosol emissions requires '// & 8056 'bc_salsa_b = "Neumann"' 8057 CALL message( 'salsa_mod: salsa_set_source','SA0025', 1, 2, 0, 6, 0 ) 8058 ENDIF 8059 ! 8060 !-- Inquire the fill value 8061 CALL get_attribute( id_faero, '_FillValue', fillval, .FALSE., & 8062 "aerosol_emission_values" ) 8063 ! 8064 !-- Aerosol chemical composition: 8065 ALLOCATE( emission_mass_fracs(1:ncat,1:maxspec) ) 8066 emission_mass_fracs = 0.0_wp 8067 !-- Chemical composition: 1: H2SO4 (sulphuric acid), 2: OC (organic carbon), 8068 !-- 3: BC (black carbon), 4: DU (dust), 8069 !-- 5: SS (sea salt), 6: HNO3 (nitric acid), 8070 !-- 7: NH3 (ammonia) 8071 DO n = 1, ncat 8072 IF ( lod_aero < 2 ) THEN 8073 emission_mass_fracs(n,:) = mass_fraction_table(:,n) 8074 ELSE 8075 CALL get_variable( id_faero, "emission_mass_fracs", & 8076 emission_mass_fracs(n,:) ) 8077 ENDIF 8078 ! 8079 !-- If the chemical component is not activated, set its mass fraction to 0 8080 !-- to avoid inbalance between number and mass flux 8081 IF ( iso4 < 0 ) emission_mass_fracs(n,1) = 0.0_wp 8082 IF ( ioc < 0 ) emission_mass_fracs(n,2) = 0.0_wp 8083 IF ( ibc < 0 ) emission_mass_fracs(n,3) = 0.0_wp 8084 IF ( idu < 0 ) emission_mass_fracs(n,4) = 0.0_wp 8085 IF ( iss < 0 ) emission_mass_fracs(n,5) = 0.0_wp 8086 IF ( ino < 0 ) emission_mass_fracs(n,6) = 0.0_wp 8087 IF ( inh < 0 ) emission_mass_fracs(n,7) = 0.0_wp 8088 !-- Then normalise the mass fraction so that SUM = 1 8089 emission_mass_fracs(n,:) = emission_mass_fracs(n,:) / & 8090 SUM( emission_mass_fracs(n,:) ) 8091 ENDDO 8092 8093 IF ( lod_aero > 1 ) THEN 8094 ! 8095 !-- Aerosol geometric mean diameter 8096 CALL netcdf_data_input_get_dimension_length( id_faero, nb_file, 'Dmid' ) 8097 IF ( nb_file /= nbins ) THEN 8098 message_string = 'The number of size bins in aerosol input data '// & 8099 'does not correspond to the model set-up' 8100 CALL message( 'salsa_mod: salsa_set_source','SA0040', 1, 2, 0, 6, 0 ) 8101 ENDIF 8102 ENDIF 8103 8104 IF ( lod_aero < 3 ) THEN 8105 CALL location_message( ' salsa_set_source: No time dependency for '//& 8106 'aerosol emissions. Use aerosol_emission_values'//& 8107 ' directly.', .TRUE. ) 8108 ! 8109 !-- Allocate source arrays 8110 DO b = 1, nbins 8111 ALLOCATE( aerosol_number(b)%source(1:ncat,nys:nyn,nxl:nxr) ) 8112 aerosol_number(b)%source = 0.0_wp 8113 ENDDO 8114 DO c = 1, ncc_tot*nbins 8115 ALLOCATE( aerosol_mass(c)%source(1:ncat,nys:nyn,nxl:nxr) ) 8116 aerosol_mass(c)%source = 0.0_wp 8117 ENDDO 8118 8119 IF ( lod_aero == 1 ) THEN 8120 DO n = 1, ncat 8121 avg_density(n) = emission_mass_fracs(n,1) * arhoh2so4 + & 8122 emission_mass_fracs(n,2) * arhooc + & 8123 emission_mass_fracs(n,3) * arhobc + & 8124 emission_mass_fracs(n,4) * arhodu + & 8125 emission_mass_fracs(n,5) * arhoss + & 8126 emission_mass_fracs(n,6) * arhohno3 + & 8127 emission_mass_fracs(n,7) * arhonh3 8128 ENDDO 8129 ! 8130 !-- Emission unit 8131 CALL get_attribute( id_faero, 'units', unita, .FALSE., & 8132 "aerosol_emission_values") 8133 conversion_factor = 1.0_wp 8134 IF ( unita == 'kg/m2/yr' ) THEN 8135 conversion_factor = 3.170979e-8_wp / avg_density 8136 ELSEIF ( unita == 'g/m2/yr' ) THEN 8137 conversion_factor = 3.170979e-8_wp * 1.0E-3_wp / avg_density 8138 ELSEIF ( unita == 'kg/m2/s' ) THEN 8139 conversion_factor = 1.0_wp / avg_density 8140 ELSEIF ( unita == 'g/m2/s' ) THEN 8141 conversion_factor = 1.0E-3_wp / avg_density 8142 ELSE 8143 message_string = 'unknown unit for aerosol emissions: ' & 8144 // TRIM( unita ) // ' (lod1)' 8145 CALL message( 'salsa_mod: salsa_set_source','SA0035', & 8146 1, 2, 0, 6, 0 ) 8147 ENDIF 8148 ! 8149 !-- Read surface emission data (x,y) PE-wise 8150 ALLOCATE( pm_emission(ncat,nys:nyn,nxl:nxr) ) 8151 CALL get_variable( id_faero, 'aerosol_emission_values', pm_emission, & 8152 nxl, nxr, nys, nyn, 0, ncat-1 ) 8153 DO ni = 1, SIZE( eci ) 8154 n = eci(ni) 8155 ! 8156 !-- Calculate the number concentration of a log-normal size 8157 !-- distribution following Jacobson (2005): Eq 13.25. 8158 ntot_table = 6.0_wp * PMfrac_table(:,n) / ( pi * dpg_table**3 * & 8159 EXP( 4.5_wp * LOG( sigmag_table )**2 ) ) * 1.0E+12_wp 8160 ! 8161 !-- Sectional size distibution from a log-normal one 8162 CALL size_distribution( ntot_table, dpg_table, sigmag_table, & 8163 nsect_emission ) 8164 DO b = 1, nbins 8165 aerosol_number(b)%source(ni,:,:) = & 8166 aerosol_number(b)%source(ni,:,:) + & 8167 pm_emission(ni,:,:) * conversion_factor(n) & 8168 * nsect_emission(b) 8169 ENDDO 8170 ENDDO 8171 ELSEIF ( lod_aero == 2 ) THEN 8172 ! 8173 !-- Read surface emission data (x,y) PE-wise 8174 ALLOCATE( dum_var_4d(nb_file,ncat,nys:nyn,nxl:nxr) ) 8175 CALL get_variable( id_faero, 'aerosol_emission_values', dum_var_4d, & 8176 nxl, nxr, nys, nyn, 0, ncat-1, 0, nb_file-1 ) 8177 DO b = 1, nbins 8178 aerosol_number(b)%source = dum_var_4d(b,:,:,:) 8179 ENDDO 8180 DEALLOCATE( dum_var_4d ) 8181 ENDIF 8182 ! 8183 !-- Set surface fluxes of aerosol number and mass on horizontal surfaces. 8184 !-- Set fluxes only for either default, land or urban surface. 8185 IF ( .NOT. land_surface .AND. .NOT. urban_surface ) THEN 8186 CALL set_flux( surf_def_h(0), ncat ) 8187 ELSE 8188 CALL set_flux( surf_usm_h, ncat ) 8189 CALL set_flux( surf_lsm_h, ncat ) 8190 ENDIF 8191 8192 ELSEIF ( lod_aero == 3 ) THEN 8193 ! 8194 !-- Inquire aerosol emission rate per bin (#/(m3s)) 8195 nc_stat = NF90_INQ_VARID( id_faero, "aerosol_emission_values", id_sa ) 8196 8197 ! 8198 !-- Emission time step 8199 CALL netcdf_data_input_get_dimension_length( id_faero, n_dt, & 8200 'dt_emission' ) 8201 IF ( n_dt > 1 ) THEN 8202 CALL location_message( ' salsa_set_source: hourly emission data'//& 8203 ' provided but currently the value of the '// & 8204 ' first hour is applied.', .TRUE. ) 8205 ENDIF 8206 ! 8207 !-- Allocate source arrays 8208 DO b = 1, nbins 8209 ALLOCATE( aerosol_number(b)%source(nzb:nzt+1,nys:nyn,nxl:nxr) ) 8210 aerosol_number(b)%source = 0.0_wp 8211 ENDDO 8212 DO c = 1, ncc_tot*nbins 8213 ALLOCATE( aerosol_mass(c)%source(nzb:nzt+1,nys:nyn,nxl:nxr) ) 8214 aerosol_mass(c)%source = 0.0_wp 8215 ENDDO 8216 ! 8217 !-- Get dimension of z-axis: 8218 CALL netcdf_data_input_get_dimension_length( id_faero, nz_file, 'z' ) 8219 ! 8220 !-- Read surface emission data (x,y) PE-wise 8221 DO i = nxl, nxr 8222 DO j = nys, nyn 8223 DO k = 0, nz_file-1 8224 ! 8225 !-- Predetermine flag to mask topography 8226 flag = MERGE( 1.0_wp, 0.0_wp, BTEST(wall_flags_0(k,j,i), 0 )) 8227 ! 8228 !-- No sources inside buildings ! 8229 IF ( flag == 0.0_wp ) CYCLE 8230 ! 8231 !-- Read volume source: 8232 nc_stat = NF90_GET_VAR( id_faero, id_sa, source_ijka, & 8233 start = (/ i+1, j+1, k+1, 1, 1 /), & 8234 count = (/ 1, 1, 1, 1, nb_file /) ) 8235 IF ( nc_stat /= NF90_NOERR ) THEN 8236 message_string = 'error in aerosol emissions: lod3' 8237 CALL message( 'salsa_mod: salsa_set_source','SA0038', 1, 2, & 8238 0, 6, 0 ) 8417 8418 #else 8419 message_string = 'salsa_emission_mode = "read_from_file", but preprocessor directive ' //& 8420 ' __netcdf is not used in compiling!' 8421 CALL message( 'salsa_emission_setup', 'PA0638', 1, 2, 0, 6, 0 ) 8422 8423 #endif 8424 CASE DEFAULT 8425 message_string = 'unknown salsa_emission_mode: ' // TRIM( salsa_emission_mode ) 8426 CALL message( 'salsa_emission_setup', 'PA0639', 1, 2, 0, 6, 0 ) 8427 8428 END SELECT 8429 8430 CONTAINS 8431 8432 !------------------------------------------------------------------------------! 8433 ! Description: 8434 ! ------------ 8435 !> Sets the aerosol flux to aerosol arrays in 2a and 2b. 8436 !------------------------------------------------------------------------------! 8437 SUBROUTINE set_flux( surface, cc_i_mod, mass_fracs, source_array ) 8438 8439 USE arrays_3d, & 8440 ONLY: rho_air_zw 8441 8442 USE surface_mod, & 8443 ONLY: surf_type 8444 8445 IMPLICIT NONE 8446 8447 INTEGER(iwp) :: i !< loop index 8448 INTEGER(iwp) :: ib !< loop index 8449 INTEGER(iwp) :: ic !< loop index 8450 INTEGER(iwp) :: j !< loop index 8451 INTEGER(iwp) :: k !< loop index 8452 INTEGER(iwp) :: m !< running index for surface elements 8453 8454 INTEGER(iwp), DIMENSION(:) :: cc_i_mod !< index of chemical component in the input data 8455 8456 REAL(wp) :: so4_oc !< mass fraction between SO4 and OC in 1a 8457 8458 REAL(wp), DIMENSION(:), INTENT(in) :: mass_fracs !< mass fractions of chemical components 8459 8460 REAL(wp), DIMENSION(nys:nyn,nxl:nxr,1:nbins_aerosol), INTENT(inout) :: source_array !< 8461 8462 TYPE(surf_type), INTENT(inout) :: surface !< respective surface type 8463 8464 so4_oc = 0.0_wp 8465 8466 DO m = 1, surface%ns 8467 ! 8468 !-- Get indices of respective grid point 8469 i = surface%i(m) 8470 j = surface%j(m) 8471 k = surface%k(m) 8472 8473 DO ib = 1, nbins_aerosol 8474 IF ( source_array(j,i,ib) < nclim ) THEN 8475 source_array(j,i,ib) = 0.0_wp 8476 ENDIF 8477 ! 8478 !-- Set mass fluxes. First bins include only SO4 and/or OC. 8479 IF ( ib <= end_subrange_1a ) THEN 8480 ! 8481 !-- Both sulphate and organic carbon 8482 IF ( index_so4 > 0 .AND. index_oc > 0 ) THEN 8483 8484 ic = ( index_so4 - 1 ) * nbins_aerosol + ib 8485 so4_oc = mass_fracs(cc_i_mod(1)) / ( mass_fracs(cc_i_mod(1)) + & 8486 mass_fracs(cc_i_mod(2)) ) 8487 surface%amsws(m,ic) = surface%amsws(m,ic) + so4_oc * source_array(j,i,ib) & 8488 * api6 * aero(ib)%dmid**3 * arhoh2so4 * rho_air_zw(k-1) 8489 aerosol_mass(ic)%source(j,i) = aerosol_mass(ic)%source(j,i) + surface%amsws(m,ic) 8490 8491 ic = ( index_oc - 1 ) * nbins_aerosol + ib 8492 surface%amsws(m,ic) = surface%amsws(m,ic) + ( 1-so4_oc ) * source_array(j,i,ib) & 8493 * api6 * aero(ib)%dmid**3 * arhooc * rho_air_zw(k-1) 8494 aerosol_mass(ic)%source(j,i) = aerosol_mass(ic)%source(j,i) + surface%amsws(m,ic) 8495 ! 8496 !-- Only sulphates 8497 ELSEIF ( index_so4 > 0 .AND. index_oc < 0 ) THEN 8498 ic = ( index_so4 - 1 ) * nbins_aerosol + ib 8499 surface%amsws(m,ic) = surface%amsws(m,ic) + source_array(j,i,ib) * api6 * & 8500 aero(ib)%dmid**3 * arhoh2so4 * rho_air_zw(k-1) 8501 aerosol_mass(ic)%source(j,i) = aerosol_mass(ic)%source(j,i) + surface%amsws(m,ic) 8502 ! 8503 !-- Only organic carbon 8504 ELSEIF ( index_so4 < 0 .AND. index_oc > 0 ) THEN 8505 ic = ( index_oc - 1 ) * nbins_aerosol + ib 8506 surface%amsws(m,ic) = surface%amsws(m,ic) + source_array(j,i,ib) * api6 * & 8507 aero(ib)%dmid**3 * arhooc * rho_air_zw(k-1) 8508 aerosol_mass(ic)%source(j,i) = aerosol_mass(ic)%source(j,i) + surface%amsws(m,ic) 8239 8509 ENDIF 8240 ! 8241 !-- Set mass fluxes. First bins include only SO4 and/or OC. Call 8242 !-- subroutine set_mass_source for larger bins. 8243 ! 8244 !-- Sulphate and organic carbon 8245 IF ( iso4 > 0 .AND. ioc > 0 ) THEN 8246 !-- First sulphate: 8247 ss = ( iso4 - 1 ) * nbins + in1a ! start 8248 ee = ( iso4 - 1 ) * nbins + fn1a ! end 8249 b = in1a 8250 DO c = ss, ee 8251 IF ( source_ijka(b) /= fillval ) & 8252 aerosol_mass(c)%source(k,j,i) = & 8253 aerosol_mass(c)%source(k,j,i) + & 8254 emission_mass_fracs(1,1) / ( emission_mass_fracs(1,1) & 8255 + emission_mass_fracs(1,2) ) * source_ijka(b) * & 8256 aero(b)%core * arhoh2so4 8257 b = b+1 8258 ENDDO 8259 !-- Then organic carbon: 8260 ss = ( ioc - 1 ) * nbins + in1a ! start 8261 ee = ( ioc - 1 ) * nbins + fn1a ! end 8262 b = in1a 8263 DO c = ss, ee 8264 IF ( source_ijka(b) /= fillval ) & 8265 aerosol_mass(c)%source(k,j,i) = & 8266 aerosol_mass(c)%source(k,j,i) + & 8267 emission_mass_fracs(1,2) / ( emission_mass_fracs(1,1) & 8268 + emission_mass_fracs(1,2) ) * source_ijka(b) * & 8269 aero(b)%core * arhooc 8270 b = b+1 8271 ENDDO 8272 8273 CALL set_mass_source( k, j, i, iso4, & 8274 emission_mass_fracs(1,1), arhoh2so4, & 8275 source_ijka, fillval ) 8276 CALL set_mass_source( k, j, i, ioc, emission_mass_fracs(1,2),& 8277 arhooc, source_ijka, fillval ) 8278 !-- Only sulphate: 8279 ELSEIF ( iso4 > 0 .AND. ioc < 0 ) THEN 8280 ss = ( iso4 - 1 ) * nbins + in1a ! start 8281 ee = ( iso4 - 1 ) * nbins + fn1a ! end 8282 b = in1a 8283 DO c = ss, ee 8284 IF ( source_ijka(b) /= fillval ) & 8285 aerosol_mass(c)%source(k,j,i) = & 8286 aerosol_mass(c)%source(k,j,i) + source_ijka(b) * & 8287 aero(b)%core * arhoh2so4 8288 b = b+1 8289 ENDDO 8290 CALL set_mass_source( k, j, i, iso4, & 8291 emission_mass_fracs(1,1), arhoh2so4, & 8292 source_ijka, fillval ) 8293 !-- Only organic carbon: 8294 ELSEIF ( iso4 < 0 .AND. ioc > 0 ) THEN 8295 ss = ( ioc - 1 ) * nbins + in1a ! start 8296 ee = ( ioc - 1 ) * nbins + fn1a ! end 8297 b = in1a 8298 DO c = ss, ee 8299 IF ( source_ijka(b) /= fillval ) & 8300 aerosol_mass(c)%source(k,j,i) = & 8301 aerosol_mass(c)%source(k,j,i) + source_ijka(b) * & 8302 aero(b)%core * arhooc 8303 b = b+1 8304 ENDDO 8305 CALL set_mass_source( k, j, i, ioc, emission_mass_fracs(1,2),& 8306 arhooc, source_ijka, fillval ) 8510 8511 ELSE 8512 ! 8513 !-- Sulphate 8514 IF ( index_so4 > 0 ) THEN 8515 ic = cc_i_mod(1) 8516 CALL set_mass_flux( surface, m, ib, index_so4, mass_fracs(ic), arhoh2so4, & 8517 source_array(j,i,ib) ) 8307 8518 ENDIF 8519 ! 8520 !-- Organic carbon 8521 IF ( index_oc > 0 ) THEN 8522 ic = cc_i_mod(2) 8523 CALL set_mass_flux( surface, m, ib, index_oc, mass_fracs(ic),arhooc, & 8524 source_array(j,i,ib) ) 8525 ENDIF 8526 ! 8308 8527 !-- Black carbon 8309 IF ( ibc > 0 ) THEN 8310 CALL set_mass_source( k, j, i, ibc, emission_mass_fracs(1,3),& 8311 arhobc, source_ijka, fillval ) 8528 IF ( index_bc > 0 ) THEN 8529 ic = cc_i_mod(3) 8530 CALL set_mass_flux( surface, m, ib, index_bc, mass_fracs(ic), arhobc, & 8531 source_array(j,i,ib) ) 8312 8532 ENDIF 8533 ! 8313 8534 !-- Dust 8314 IF ( idu > 0 ) THEN 8315 CALL set_mass_source( k, j, i, idu, emission_mass_fracs(1,4),& 8316 arhodu, source_ijka, fillval ) 8535 IF ( index_du > 0 ) THEN 8536 ic = cc_i_mod(4) 8537 CALL set_mass_flux( surface, m, ib, index_du, mass_fracs(ic), arhodu, & 8538 source_array(j,i,ib) ) 8317 8539 ENDIF 8540 ! 8318 8541 !-- Sea salt 8319 IF ( iss > 0 ) THEN 8320 CALL set_mass_source( k, j, i, iss, emission_mass_fracs(1,5),& 8321 arhoss, source_ijka, fillval ) 8542 IF ( index_ss > 0 ) THEN 8543 ic = cc_i_mod(5) 8544 CALL set_mass_flux( surface, m, ib, index_ss, mass_fracs(ic), arhoss, & 8545 source_array(j,i,ib) ) 8322 8546 ENDIF 8547 ! 8323 8548 !-- Nitric acid 8324 IF ( ino > 0 ) THEN 8325 CALL set_mass_source( k, j, i, ino, emission_mass_fracs(1,6),& 8326 arhohno3, source_ijka, fillval ) 8549 IF ( index_no > 0 ) THEN 8550 ic = cc_i_mod(6) 8551 CALL set_mass_flux( surface, m, ib, index_no, mass_fracs(ic), arhohno3, & 8552 source_array(j,i,ib) ) 8327 8553 ENDIF 8554 ! 8328 8555 !-- Ammonia 8329 IF ( inh > 0 ) THEN 8330 CALL set_mass_source( k, j, i, inh, emission_mass_fracs(1,7),& 8331 arhonh3, source_ijka, fillval ) 8556 IF ( index_nh > 0 ) THEN 8557 ic = cc_i_mod(7) 8558 CALL set_mass_flux( surface, m, ib, index_nh, mass_fracs(ic), arhonh3, & 8559 source_array(j,i,ib) ) 8332 8560 ENDIF 8333 ! 8334 !-- Save aerosol number sources in the end 8335 DO b = 1, nbins 8336 IF ( source_ijka(b) /= fillval ) & 8337 aerosol_number(b)%source(k,j,i) = & 8338 aerosol_number(b)%source(k,j,i) + source_ijka(b) 8339 ENDDO 8340 ENDDO ! k 8341 ENDDO ! j 8342 ENDDO ! i 8343 8344 ELSE 8345 message_string = 'NetCDF attribute lod is not set properly.' 8346 CALL message( 'salsa_mod: salsa_set_source','SA0026', 1, 2, 0, 6, 0 ) 8347 ENDIF 8348 8349 #endif 8350 END SUBROUTINE salsa_set_source 8351 8561 8562 ENDIF 8563 ! 8564 !-- Save number fluxes in the end 8565 surface%answs(m,ib) = surface%answs(m,ib) + source_array(j,i,ib) * rho_air_zw(k-1) 8566 aerosol_number(ib)%source(j,i) = aerosol_number(ib)%source(j,i) + surface%answs(m,ib) 8567 8568 ENDDO ! ib 8569 ENDDO ! m 8570 8571 END SUBROUTINE set_flux 8572 8573 !------------------------------------------------------------------------------! 8574 ! Description: 8575 ! ------------ 8576 !> Sets the mass emissions to aerosol arrays in 2a and 2b. 8577 !------------------------------------------------------------------------------! 8578 SUBROUTINE set_mass_flux( surface, surf_num, ib, ispec, mass_frac, prho, nsource ) 8579 8580 USE arrays_3d, & 8581 ONLY: rho_air_zw 8582 8583 USE surface_mod, & 8584 ONLY: surf_type 8585 8586 IMPLICIT NONE 8587 8588 INTEGER(iwp) :: i !< loop index 8589 INTEGER(iwp) :: j !< loop index 8590 INTEGER(iwp) :: k !< loop index 8591 INTEGER(iwp) :: ic !< loop index 8592 8593 INTEGER(iwp), INTENT(in) :: ib !< Aerosol size bin index 8594 INTEGER(iwp), INTENT(in) :: ispec !< Aerosol species index 8595 INTEGER(iwp), INTENT(in) :: surf_num !< index surface elements 8596 8597 REAL(wp), INTENT(in) :: mass_frac !< mass fraction of a chemical compound in all bins 8598 REAL(wp), INTENT(in) :: nsource !< number source (#/m2/s) 8599 REAL(wp), INTENT(in) :: prho !< Aerosol density 8600 8601 TYPE(surf_type), INTENT(inout) :: surface !< respective surface type 8602 ! 8603 !-- Get indices of respective grid point 8604 i = surface%i(surf_num) 8605 j = surface%j(surf_num) 8606 k = surface%k(surf_num) 8607 ! 8608 !-- Subrange 2a: 8609 ic = ( ispec - 1 ) * nbins_aerosol + ib 8610 surface%amsws(surf_num,ic) = surface%amsws(surf_num,ic) + mass_frac * nsource * & 8611 aero(ib)%core * prho * rho_air_zw(k-1) 8612 aerosol_mass(ic)%source(j,i) = aerosol_mass(ic)%source(j,i) + surface%amsws(surf_num,ic) 8613 ! 8614 !-- Subrange 2b: 8615 IF ( .NOT. no_insoluble ) THEN 8616 CALL location_message( ' salsa_mass_flux: All emissions are soluble!', .TRUE. ) 8617 ENDIF 8618 8619 END SUBROUTINE set_mass_flux 8620 8621 END SUBROUTINE salsa_emission_setup 8622 8352 8623 !------------------------------------------------------------------------------! 8353 8624 ! Description: … … 8355 8626 !> Sets the gaseous fluxes 8356 8627 !------------------------------------------------------------------------------! 8357 SUBROUTINE set_gas_flux( surface, ncat_emission, unit ) 8358 8359 USE arrays_3d, & 8360 ONLY: dzw, hyp, pt, rho_air_zw 8361 8362 USE grid_variables, & 8363 ONLY: dx, dy 8364 8365 USE surface_mod, & 8366 ONLY: surf_type 8367 8628 SUBROUTINE salsa_gas_emission_setup( init ) 8629 8630 USE control_parameters, & 8631 ONLY: time_since_reference_point 8632 8633 USE date_and_time_mod, & 8634 ONLY: day_of_month, hour_of_day, index_dd, index_hh, index_mm, month_of_year, & 8635 time_default_indices, time_utc_init 8636 8637 USE netcdf_data_input_mod, & 8638 ONLY: check_existence, chem_emis_att_type, chem_emis_val_type, get_attribute, & 8639 get_variable, inquire_num_variables, inquire_variable_names, & 8640 netcdf_data_input_get_dimension_length, open_read_file 8641 8642 USE surface_mod, & 8643 ONLY: surf_def_h, surf_lsm_h, surf_usm_h 8644 8368 8645 IMPLICIT NONE 8369 8370 CHARACTER(LEN=*) :: unit !< flux unit in the input file 8371 INTEGER(iwp) :: ncat_emission !< number of emission categories 8372 TYPE(surf_type), INTENT(inout) :: surface !< respective surface type 8373 INTEGER(iwp) :: g !< loop index 8374 INTEGER(iwp) :: i !< loop index 8375 INTEGER(iwp) :: j !< loop index 8376 INTEGER(iwp) :: k !< loop index 8377 INTEGER(iwp) :: m !< running index for surface elements 8378 INTEGER(iwp) :: n !< running index for emission categories 8379 REAL(wp), DIMENSION(ngast) :: conversion_factor 8380 8381 conversion_factor = 1.0_wp 8382 8383 DO m = 1, surface%ns 8384 ! 8385 !-- Get indices of respective grid point 8386 i = surface%i(m) 8387 j = surface%j(m) 8388 k = surface%k(m) 8389 8390 IF ( unit == '#/m2/s' ) THEN 8391 conversion_factor = 1.0_wp 8392 ELSEIF ( unit == 'g/m2/s' ) THEN 8393 conversion_factor(1) = avo / ( amh2so4 * 1000.0_wp ) 8394 conversion_factor(2) = avo / ( amhno3 * 1000.0_wp ) 8395 conversion_factor(3) = avo / ( amnh3 * 1000.0_wp ) 8396 conversion_factor(4) = avo / ( amoc * 1000.0_wp ) 8397 conversion_factor(5) = avo / ( amoc * 1000.0_wp ) 8398 ELSEIF ( unit == 'ppm/m2/s' ) THEN 8399 conversion_factor = for_ppm_to_nconc * hyp(k) / pt(k,j,i) * ( hyp(k) & 8400 / 100000.0_wp )**0.286_wp * dx * dy * dzw(k) 8401 ELSEIF ( unit == 'mumol/m2/s' ) THEN 8402 conversion_factor = 1.0E-6_wp * avo 8646 8647 CHARACTER(LEN=80) :: daytype = 'workday' !< default day type 8648 CHARACTER(LEN=25) :: in_name !< name of a gas in the input file 8649 8650 CHARACTER(LEN=100), DIMENSION(:), ALLOCATABLE :: var_names !< variable names in input data 8651 8652 INTEGER(iwp) :: id_chem !< NetCDF id of chemistry emission file 8653 INTEGER(iwp) :: ig !< loop index 8654 INTEGER(iwp) :: in !< running index for emission categories 8655 INTEGER(iwp) :: num_vars !< number of variables 8656 8657 LOGICAL :: netcdf_extend = .FALSE. !< NetCDF input file exists 8658 8659 LOGICAL, INTENT(in) :: init !< if .TRUE. --> initialisation call 8660 8661 REAL(wp), DIMENSION(:), ALLOCATABLE :: time_factor !< emission time factor 8662 8663 TYPE(chem_emis_att_type) :: chem_emission_att !< chemistry emission attributes 8664 TYPE(chem_emis_val_type) :: chem_emission !< chemistry emission values 8665 8666 ! 8667 !-- Reset surface fluxes 8668 surf_def_h(0)%gtsws = 0.0_wp 8669 surf_lsm_h%gtsws = 0.0_wp 8670 surf_usm_h%gtsws = 0.0_wp 8671 8672 IF ( init ) THEN 8673 #if defined( __netcdf ) 8674 ! 8675 !-- Check existence of PIDS_CHEM file 8676 INQUIRE( FILE = 'PIDS_CHEM' // TRIM( coupling_char ), EXIST = netcdf_extend ) 8677 IF ( .NOT. netcdf_extend ) THEN 8678 message_string = 'Input file PIDS_CHEM' // TRIM( coupling_char ) // ' missing!' 8679 CALL message( 'salsa_gas_emission_setup', 'PA0640', 1, 2, 0, 6, 0 ) 8680 ENDIF 8681 ! 8682 !-- Open file in read-only mode 8683 CALL open_read_file( 'PIDS_CHEM' // TRIM( coupling_char ), id_chem ) 8684 ! 8685 !-- Read the index and name of chemical components 8686 CALL netcdf_data_input_get_dimension_length( id_chem, chem_emission_att%nspec, & 8687 'nspecies' ) 8688 ALLOCATE( chem_emission_att%species_index(1:chem_emission_att%nspec) ) 8689 CALL get_variable( id_chem, 'emission_index', chem_emission_att%species_index ) 8690 CALL get_variable( id_chem, 'emission_name', chem_emission_att%species_name, & 8691 chem_emission_att%nspec ) 8692 ! 8693 !-- Find the corresponding indices in the model 8694 emission_index_chem = 0 8695 DO ig = 1, chem_emission_att%nspec 8696 in_name = chem_emission_att%species_name(ig) 8697 SELECT CASE ( TRIM( in_name ) ) 8698 CASE ( 'H2SO4', 'h2so4' ) 8699 emission_index_chem(1) = ig 8700 CASE ( 'HNO3', 'hno3' ) 8701 emission_index_chem(2) = ig 8702 CASE ( 'NH3', 'nh3' ) 8703 emission_index_chem(3) = ig 8704 CASE ( 'OCNV', 'ocnv' ) 8705 emission_index_chem(4) = ig 8706 CASE ( 'OCSV', 'ocsv' ) 8707 emission_index_chem(5) = ig 8708 END SELECT 8709 ENDDO 8710 IF ( SUM( emission_index_chem ) == 0 ) THEN 8711 CALL location_message( ' salsa_gas_emission_setup: no gas emissions', .TRUE. ) 8712 ENDIF 8713 ! 8714 !-- Inquire the fill value 8715 CALL get_attribute( id_chem, '_FillValue', aero_emission%fill, .FALSE., 'emission_values' ) 8716 ! 8717 !-- Inquire units of emissions 8718 CALL get_attribute( id_chem, 'units', chem_emission_att%units, .FALSE., 'emission_values' ) 8719 ! 8720 !-- Inquire the level of detail (lod) 8721 CALL get_attribute( id_chem, 'lod', lod_gas_emissions, .FALSE., 'emission_values' ) 8722 ! 8723 !-- Variable names 8724 CALL inquire_num_variables( id_chem, num_vars ) 8725 ALLOCATE( var_names(1:num_vars) ) 8726 CALL inquire_variable_names( id_chem, var_names ) 8727 ! 8728 !-- Default mode: as total emissions per year 8729 IF ( lod_gas_emissions == 1 ) THEN 8730 8731 ! 8732 !-- Get number of emission categories and allocate emission arrays 8733 CALL netcdf_data_input_get_dimension_length( id_chem, chem_emission_att%ncat, 'ncat' ) 8734 ALLOCATE( chem_emission_att%cat_index(1:chem_emission_att%ncat), & 8735 time_factor(1:chem_emission_att%ncat) ) 8736 ! 8737 !-- Get emission category names and indices 8738 CALL get_variable( id_chem, 'emission_category_name', chem_emission_att%cat_name, & 8739 chem_emission_att%ncat) 8740 CALL get_variable( id_chem, 'emission_category_index', chem_emission_att%cat_index ) 8741 ! 8742 !-- Emission time factors: Find check whether emission time factors are given for each hour 8743 !-- of year OR based on month, day and hour 8744 ! 8745 !-- For each hour of year: 8746 IF ( check_existence( var_names, 'nhoursyear' ) ) THEN 8747 CALL netcdf_data_input_get_dimension_length( id_chem, chem_emission_att%nhoursyear, & 8748 'nhoursyear' ) 8749 ALLOCATE( chem_emission_att%hourly_emis_time_factor(1:chem_emission_att%ncat, & 8750 1:chem_emission_att%nhoursyear) ) 8751 CALL get_variable( id_chem, 'emission_time_factors', & 8752 chem_emission_att%hourly_emis_time_factor, & 8753 0, chem_emission_att%nhoursyear-1, 0, chem_emission_att%ncat-1 ) 8754 ! 8755 !-- Based on the month, day and hour: 8756 ELSEIF ( check_existence( var_names, 'nmonthdayhour' ) ) THEN 8757 CALL netcdf_data_input_get_dimension_length( id_chem, chem_emission_att%nmonthdayhour,& 8758 'nmonthdayhour' ) 8759 ALLOCATE( chem_emission_att%mdh_emis_time_factor(1:chem_emission_att%ncat, & 8760 1:chem_emission_att%nmonthdayhour) ) 8761 CALL get_variable( id_chem, 'emission_time_factors', & 8762 chem_emission_att%mdh_emis_time_factor, & 8763 0, chem_emission_att%nmonthdayhour-1, 0, chem_emission_att%ncat-1 ) 8764 ELSE 8765 message_string = 'emission_time_factors should be given for each nhoursyear OR ' // & 8766 'nmonthdayhour' 8767 CALL message( 'salsa_gas_emission_setup','PA0641', 1, 2, 0, 6, 0 ) 8768 ENDIF 8769 ! 8770 !-- Next emission update 8771 next_gas_emission_update = MOD( time_utc_init, 3600.0_wp ) - 3600.0_wp 8772 ! 8773 !-- Allocate and read surface emission data (in total PM) (NOTE that "preprocessed" input data 8774 !-- array is applied now here) 8775 ALLOCATE( chem_emission%preproc_emission_data(nys:nyn,nxl:nxr, 1:chem_emission_att%nspec,& 8776 1:chem_emission_att%ncat) ) 8777 CALL get_variable( id_chem, 'emission_values', chem_emission%preproc_emission_data, & 8778 0, chem_emission_att%ncat-1, 0, chem_emission_att%nspec-1, & 8779 nxl, nxr, nys, nyn ) 8780 ! 8781 !-- Pre-processed mode: 8782 ELSEIF ( lod_gas_emissions == 2 ) THEN 8783 ! 8784 !-- Number of time steps in the emission data 8785 CALL netcdf_data_input_get_dimension_length( id_chem, chem_emission_att%dt_emission, & 8786 'time' ) 8787 ! 8788 !-- Allocate and read time 8789 ALLOCATE( gas_emission_time(1:chem_emission_att%dt_emission) ) 8790 CALL get_variable( id_chem, 'time', gas_emission_time ) 8403 8791 ELSE 8404 message_string = 'Unknown unit for gaseous emissions!' 8405 CALL message( 'salsa_mod: set_gas_flux', 'SA0031', 1, 2, 0, 6, 0 ) 8406 ENDIF 8407 8408 DO n = 1, ncat_emission 8409 DO g = 1, ngast 8410 IF ( salsa_gas(g)%source(n,j,i) < 0.0_wp ) THEN 8411 salsa_gas(g)%source(n,j,i) = 0.0_wp 8412 CYCLE 8413 ENDIF 8414 surface%gtsws(m,g) = surface%gtsws(m,g) + & 8415 salsa_gas(g)%source(n,j,i) * rho_air_zw(k-1) & 8416 * conversion_factor(g) 8417 ENDDO 8792 message_string = 'Unknown lod for emission_values.' 8793 CALL message( 'salsa_gas_emission_setup','PA0642', 1, 2, 0, 6, 0 ) 8794 ENDIF ! lod 8795 8796 ENDIF ! init 8797 ! 8798 !-- Define and set current emission values: 8799 8800 IF ( lod_gas_emissions == 1 ) THEN 8801 ! 8802 !-- Emission time factors for each emission category at current time step 8803 IF ( chem_emission_att%nhoursyear > chem_emission_att%nmonthdayhour ) THEN 8804 ! 8805 !-- Get the index of the current hour 8806 CALL time_default_indices( month_of_year, day_of_month, hour_of_day, index_hh ) 8807 time_factor = chem_emission_att%hourly_emis_time_factor(:,index_hh) 8808 8809 ELSEIF ( chem_emission_att%nhoursyear < chem_emission_att%nmonthdayhour ) THEN 8810 ! 8811 !-- Get the index of current hour (index_hh) (TODO: Now "workday" is always assumed. 8812 !-- Needs to be calculated.) 8813 CALL time_default_indices( daytype, month_of_year, day_of_month, hour_of_day, & 8814 index_mm, index_dd, index_hh ) 8815 time_factor = chem_emission_att%mdh_emis_time_factor(:,index_mm) * & 8816 chem_emission_att%mdh_emis_time_factor(:,index_dd) * & 8817 chem_emission_att%mdh_emis_time_factor(:,index_hh) 8818 ENDIF 8819 ! 8820 !-- Set gas emissions for each emission category 8821 DO in = 1, chem_emission_att%ncat 8822 ! 8823 !-- Set surface fluxes only for either default, land or urban surface 8824 IF ( .NOT. land_surface .AND. .NOT. urban_surface ) THEN 8825 CALL set_gas_flux( surf_def_h(0), emission_index_chem, chem_emission_att%units, & 8826 chem_emission%preproc_emission_data(:,:,:,in), time_factor(in) ) 8827 ELSE 8828 CALL set_gas_flux( surf_usm_h, emission_index_chem, chem_emission_att%units, & 8829 chem_emission%preproc_emission_data(:,:,:,in), time_factor(in) ) 8830 CALL set_gas_flux( surf_lsm_h, emission_index_chem, chem_emission_att%units, & 8831 chem_emission%preproc_emission_data(:,:,:,in), time_factor(in) ) 8832 ENDIF 8418 8833 ENDDO 8419 ENDDO 8420 8421 END SUBROUTINE set_gas_flux 8422 8423 8834 ! 8835 !-- The next emission update is again after one hour 8836 next_gas_emission_update = next_gas_emission_update + 3600.0_wp 8837 8838 ELSEIF ( lod_gas_emissions == 2 ) THEN 8839 ! 8840 !-- Obtain time index for current input starting at 0. 8841 !-- @todo: At the moment emission data and simulated time correspond to each other. 8842 chem_emission_att%i_hour = MINLOC( ABS( gas_emission_time - time_since_reference_point ), & 8843 DIM = 1 ) - 1 8844 ! 8845 !-- Allocate the data input array always before reading in the data and deallocate after (NOTE 8846 !-- that "preprocessed" input data array is applied now here) 8847 ALLOCATE( chem_emission%default_emission_data(nys:nyn,nxl:nxr,1:nbins_aerosol) ) 8848 ! 8849 !-- Read in the next time step 8850 CALL get_variable( id_chem, 'emission_values', chem_emission%default_emission_data, & 8851 chem_emission_att%i_hour, 0, chem_emission_att%nspec-1, nxl, nxr, nys, nyn ) 8852 ! 8853 !-- Set surface fluxes only for either default, land or urban surface 8854 IF ( .NOT. land_surface .AND. .NOT. urban_surface ) THEN 8855 CALL set_gas_flux( surf_def_h(0), emission_index_chem, chem_emission_att%units, & 8856 chem_emission%default_emission_data ) 8857 ELSE 8858 CALL set_gas_flux( surf_usm_h, emission_index_chem, chem_emission_att%units, & 8859 chem_emission%default_emission_data ) 8860 CALL set_gas_flux( surf_lsm_h, emission_index_chem, chem_emission_att%units, & 8861 chem_emission%default_emission_data ) 8862 ENDIF 8863 ! 8864 !-- Determine the next emission update 8865 next_gas_emission_update = gas_emission_time(chem_emission_att%i_hour+2) 8866 8867 DEALLOCATE( chem_emission%default_emission_data ) 8868 ENDIF 8869 #else 8870 message_string = 'salsa_emission_mode = "read_from_file", but preprocessor directive ' // & 8871 ' __netcdf is not used in compiling!' 8872 CALL message( 'salsa_gas_emission_setup', 'PA0643', 1, 2, 0, 6, 0 ) 8873 8874 #endif 8875 8876 CONTAINS 8424 8877 !------------------------------------------------------------------------------! 8425 8878 ! Description: 8426 8879 ! ------------ 8427 !> Sets the aerosol flux to aerosol arrays in 2a and 2b. 8428 !------------------------------------------------------------------------------! 8429 SUBROUTINE set_flux( surface, ncat_emission ) 8430 8431 USE arrays_3d, & 8432 ONLY: rho_air_zw 8433 8434 USE surface_mod, & 8435 ONLY: surf_type 8436 8437 IMPLICIT NONE 8438 8439 INTEGER(iwp) :: ncat_emission !< number of emission categories 8440 TYPE(surf_type), INTENT(inout) :: surface !< respective surface type 8441 INTEGER(iwp) :: b !< loop index 8442 INTEGER(iwp) :: i !< loop index 8443 INTEGER(iwp) :: j !< loop index 8444 INTEGER(iwp) :: k !< loop index 8445 INTEGER(iwp) :: m !< running index for surface elements 8446 INTEGER(iwp) :: n !< loop index for emission categories 8447 INTEGER(iwp) :: c !< loop index 8448 8449 DO m = 1, surface%ns 8450 ! 8451 !-- Get indices of respective grid point 8452 i = surface%i(m) 8453 j = surface%j(m) 8454 k = surface%k(m) 8455 8456 DO n = 1, ncat_emission 8457 DO b = 1, nbins 8458 IF ( aerosol_number(b)%source(n,j,i) < 0.0_wp ) THEN 8459 aerosol_number(b)%source(n,j,i) = 0.0_wp 8460 CYCLE 8880 !> Set gas fluxes for selected type of surfaces 8881 !------------------------------------------------------------------------------! 8882 SUBROUTINE set_gas_flux( surface, cc_i_mod, unit, source_array, time_fac ) 8883 8884 USE arrays_3d, & 8885 ONLY: dzw, hyp, pt, rho_air_zw 8886 8887 USE grid_variables, & 8888 ONLY: dx, dy 8889 8890 USE surface_mod, & 8891 ONLY: surf_type 8892 8893 IMPLICIT NONE 8894 8895 CHARACTER(LEN=*), INTENT(in) :: unit !< flux unit in the input file 8896 8897 INTEGER(iwp) :: ig !< running index for gases 8898 INTEGER(iwp) :: i !< loop index 8899 INTEGER(iwp) :: j !< loop index 8900 INTEGER(iwp) :: k !< loop index 8901 INTEGER(iwp) :: m !< running index for surface elements 8902 8903 INTEGER(iwp), DIMENSION(:) :: cc_i_mod !< index of different gases in the input data 8904 8905 LOGICAL :: use_time_fac !< .TRUE. is time_fac present 8906 8907 REAL(wp), OPTIONAL :: time_fac !< emission time factor 8908 8909 REAL(wp), DIMENSION(ngases_salsa) :: conv !< unit conversion factor 8910 8911 REAL(wp), DIMENSION(nys:nyn,nxl:nxr,chem_emission_att%nspec), INTENT(in) :: source_array !< 8912 8913 TYPE(surf_type), INTENT(inout) :: surface !< respective surface type 8914 8915 use_time_fac = PRESENT( time_fac ) 8916 8917 DO m = 1, surface%ns 8918 ! 8919 !-- Get indices of respective grid point 8920 i = surface%i(m) 8921 j = surface%j(m) 8922 k = surface%k(m) 8923 ! 8924 !-- Unit conversion factor: convert to SI units (#/m2/s) 8925 SELECT CASE ( TRIM( unit ) ) 8926 CASE ( 'kg/m2/yr' ) 8927 conv(1) = avo / ( amh2so4 * 3600.0_wp ) 8928 conv(2) = avo / ( amhno3 * 3600.0_wp ) 8929 conv(3) = avo / ( amnh3 * 3600.0_wp ) 8930 conv(4) = avo / ( amoc * 3600.0_wp ) 8931 conv(5) = avo / ( amoc * 3600.0_wp ) 8932 CASE ( 'g/m2/yr' ) 8933 conv(1) = avo / ( amh2so4 * 3.6E+6_wp ) 8934 conv(2) = avo / ( amhno3 * 3.6E+6_wp ) 8935 conv(3) = avo / ( amnh3 * 3.6E+6_wp ) 8936 conv(4) = avo / ( amoc * 3.6E+6_wp ) 8937 conv(5) = avo / ( amoc * 3.6E+6_wp ) 8938 CASE ( 'g/m2/s' ) 8939 conv(1) = avo / ( amh2so4 * 1000.0_wp ) 8940 conv(2) = avo / ( amhno3 * 1000.0_wp ) 8941 conv(3) = avo / ( amnh3 * 1000.0_wp ) 8942 conv(4) = avo / ( amoc * 1000.0_wp ) 8943 conv(5) = avo / ( amoc * 1000.0_wp ) 8944 CASE ( '#/m2/s' ) 8945 conv = 1.0_wp 8946 CASE ( 'ppm/m2/s' ) 8947 conv = for_ppm_to_nconc * hyp(k) / pt(k,j,i) * ( 1.0E5_wp / hyp(k) )**0.286_wp * & 8948 dx * dy * dzw(k) 8949 CASE ( 'mumol/m2/s' ) 8950 conv = 1.0E-6_wp * avo 8951 CASE DEFAULT 8952 message_string = 'unknown unit for gas emissions: ' // TRIM( chem_emission_att%units ) 8953 CALL message( 'set_gas_flux','PA0644', 1, 2, 0, 6, 0 ) 8954 8955 END SELECT 8956 8957 DO ig = 1, ngases_salsa 8958 IF ( use_time_fac ) THEN 8959 surface%gtsws(m,ig) = surface%gtsws(m,ig) + rho_air_zw(k-1) * conv(ig) * time_fac & 8960 * MAX( 0.0_wp, source_array(j,i,cc_i_mod(ig) ) ) 8961 ELSE 8962 surface%gtsws(m,ig) = surface%gtsws(m,ig) + rho_air_zw(k-1) * conv(ig) & 8963 * MAX( 0.0_wp, source_array(j,i,cc_i_mod(ig) ) ) 8461 8964 ENDIF 8462 ! 8463 !-- Set mass fluxes. First bins include only SO4 and/or OC. 8464 8465 IF ( b <= fn1a ) THEN 8466 ! 8467 !-- Both sulphate and organic carbon 8468 IF ( iso4 > 0 .AND. ioc > 0 ) THEN 8469 8470 c = ( iso4 - 1 ) * nbins + b 8471 surface%amsws(m,c) = surface%amsws(m,c) + & 8472 emission_mass_fracs(n,1) / & 8473 ( emission_mass_fracs(n,1) + & 8474 emission_mass_fracs(n,2) ) * & 8475 aerosol_number(b)%source(n,j,i) * & 8476 api6 * aero(b)%dmid**3.0_wp * & 8477 arhoh2so4 * rho_air_zw(k-1) 8478 aerosol_mass(c)%source(n,j,i) = & 8479 aerosol_mass(c)%source(n,j,i) + surface%amsws(m,c) 8480 c = ( ioc - 1 ) * nbins + b 8481 surface%amsws(m,c) = surface%amsws(m,c) + & 8482 emission_mass_fracs(n,2) / & 8483 ( emission_mass_fracs(n,1) + & 8484 emission_mass_fracs(n,2) ) * & 8485 aerosol_number(b)%source(n,j,i) * & 8486 api6 * aero(b)%dmid**3.0_wp * arhooc & 8487 * rho_air_zw(k-1) 8488 aerosol_mass(c)%source(n,j,i) = & 8489 aerosol_mass(c)%source(n,j,i) + surface%amsws(m,c) 8490 ! 8491 !-- Only sulphates 8492 ELSEIF ( iso4 > 0 .AND. ioc < 0 ) THEN 8493 c = ( iso4 - 1 ) * nbins + b 8494 surface%amsws(m,c) = surface%amsws(m,c) + & 8495 aerosol_number(b)%source(n,j,i) * api6 & 8496 * aero(b)%dmid**3.0_wp * arhoh2so4 & 8497 * rho_air_zw(k-1) 8498 aerosol_mass(c)%source(n,j,i) = & 8499 aerosol_mass(c)%source(n,j,i) + surface%amsws(m,c) 8500 ! 8501 !-- Only organic carbon 8502 ELSEIF ( iso4 < 0 .AND. ioc > 0 ) THEN 8503 c = ( ioc - 1 ) * nbins + b 8504 surface%amsws(m,c) = surface%amsws(m,c) + & 8505 aerosol_number(b)%source(n,j,i) * api6 & 8506 * aero(b)%dmid**3.0_wp * arhooc & 8507 * rho_air_zw(k-1) 8508 aerosol_mass(c)%source(n,j,i) = & 8509 aerosol_mass(c)%source(n,j,i) + surface%amsws(m,c) 8510 ENDIF 8511 8512 ELSEIF ( b > fn1a ) THEN 8513 ! 8514 !-- Sulphate 8515 IF ( iso4 > 0 ) THEN 8516 CALL set_mass_flux( surface, m, b, iso4, n, & 8517 emission_mass_fracs(n,1), arhoh2so4, & 8518 aerosol_number(b)%source(n,j,i) ) 8519 ENDIF 8520 ! 8521 !-- Organic carbon 8522 IF ( ioc > 0 ) THEN 8523 CALL set_mass_flux( surface, m, b, ioc, n, & 8524 emission_mass_fracs(n,2), arhooc, & 8525 aerosol_number(b)%source(n,j,i) ) 8526 ENDIF 8527 ! 8528 !-- Black carbon 8529 IF ( ibc > 0 ) THEN 8530 CALL set_mass_flux( surface, m, b, ibc, n, & 8531 emission_mass_fracs(n,3), arhobc, & 8532 aerosol_number(b)%source(n,j,i) ) 8533 ENDIF 8534 ! 8535 !-- Dust 8536 IF ( idu > 0 ) THEN 8537 CALL set_mass_flux( surface, m, b, idu, n, & 8538 emission_mass_fracs(n,4), arhodu, & 8539 aerosol_number(b)%source(n,j,i) ) 8540 ENDIF 8541 ! 8542 !-- Sea salt 8543 IF ( iss > 0 ) THEN 8544 CALL set_mass_flux( surface, m, b, iss, n, & 8545 emission_mass_fracs(n,5), arhoss, & 8546 aerosol_number(b)%source(n,j,i) ) 8547 ENDIF 8548 ! 8549 !-- Nitric acid 8550 IF ( ino > 0 ) THEN 8551 CALL set_mass_flux( surface, m, b, ino, n, & 8552 emission_mass_fracs(n,6), arhohno3, & 8553 aerosol_number(b)%source(n,j,i) ) 8554 ENDIF 8555 ! 8556 !-- Ammonia 8557 IF ( inh > 0 ) THEN 8558 CALL set_mass_flux( surface, m, b, inh, n, & 8559 emission_mass_fracs(n,7), arhonh3, & 8560 aerosol_number(b)%source(n,j,i) ) 8561 ENDIF 8562 8563 ENDIF 8564 ! 8565 !-- Save number fluxes in the end 8566 surface%answs(m,b) = surface%answs(m,b) + & 8567 aerosol_number(b)%source(n,j,i) * rho_air_zw(k-1) 8568 aerosol_number(b)%source(n,j,i) = surface%answs(m,b) 8569 ENDDO 8570 8571 ENDDO 8572 8573 ENDDO 8574 8575 END SUBROUTINE set_flux 8576 8577 !------------------------------------------------------------------------------! 8578 ! Description: 8579 ! ------------ 8580 !> Sets the mass emissions to aerosol arrays in 2a and 2b. 8581 !------------------------------------------------------------------------------! 8582 SUBROUTINE set_mass_flux( surface, surf_num, b, ispec, n, mass_frac, prho, & 8583 nsource ) 8584 8585 USE arrays_3d, & 8586 ONLY: rho_air_zw 8587 8588 USE surface_mod, & 8589 ONLY: surf_type 8590 8591 IMPLICIT NONE 8592 8593 INTEGER(iwp), INTENT(in) :: b !< Aerosol size bin index 8594 INTEGER(iwp), INTENT(in) :: ispec !< Aerosol species index 8595 INTEGER(iwp), INTENT(in) :: n !< emission category number 8596 INTEGER(iwp), INTENT(in) :: surf_num !< index surface elements 8597 REAL(wp), INTENT(in) :: mass_frac !< mass fraction of a chemical 8598 !< compound in all bins 8599 REAL(wp), INTENT(in) :: nsource !< number source (#/m2/s) 8600 REAL(wp), INTENT(in) :: prho !< Aerosol density 8601 TYPE(surf_type), INTENT(inout) :: surface !< respective surface type 8602 8603 INTEGER(iwp) :: i !< loop index 8604 INTEGER(iwp) :: j !< loop index 8605 INTEGER(iwp) :: k !< loop index 8606 INTEGER(iwp) :: c !< loop index 8607 8608 ! 8609 !-- Get indices of respective grid point 8610 i = surface%i(surf_num) 8611 j = surface%j(surf_num) 8612 k = surface%k(surf_num) 8613 ! 8614 !-- Subrange 2a: 8615 c = ( ispec - 1 ) * nbins + b 8616 surface%amsws(surf_num,c) = surface%amsws(surf_num,c) + mass_frac * nsource& 8617 * aero(b)%core * prho * rho_air_zw(k-1) 8618 aerosol_mass(c)%source(n,j,i) = aerosol_mass(c)%source(n,j,i) + & 8619 surface%amsws(surf_num,c) 8620 ! 8621 !-- Subrange 2b: 8622 IF ( .NOT. no_insoluble ) THEN 8623 WRITE(*,*) 'All emissions are soluble!' 8624 ENDIF 8625 8626 END SUBROUTINE set_mass_flux 8627 8628 !------------------------------------------------------------------------------! 8629 ! Description: 8630 ! ------------ 8631 !> Sets the mass sources to aerosol arrays in 2a and 2b. 8632 !------------------------------------------------------------------------------! 8633 SUBROUTINE set_mass_source( k, j, i, ispec, mass_frac, prho, nsource, fillval ) 8634 8635 USE surface_mod, & 8636 ONLY: surf_type 8637 8638 IMPLICIT NONE 8639 8640 INTEGER(iwp), INTENT(in) :: ispec !< Aerosol species index 8641 REAL(wp), INTENT(in) :: fillval !< _FillValue in the NetCDF file 8642 REAL(wp), INTENT(in) :: mass_frac !< mass fraction of a chemical 8643 !< compound in all bins 8644 REAL(wp), INTENT(in), DIMENSION(:) :: nsource !< number source 8645 REAL(wp), INTENT(in) :: prho !< Aerosol density 8646 8647 INTEGER(iwp) :: b !< loop index 8648 INTEGER(iwp) :: ee !< index: end 8649 INTEGER(iwp) :: i !< loop index 8650 INTEGER(iwp) :: j !< loop index 8651 INTEGER(iwp) :: k !< loop index 8652 INTEGER(iwp) :: c !< loop index 8653 INTEGER(iwp) :: ss !<index: start 8654 ! 8655 !-- Subrange 2a: 8656 ss = ( ispec - 1 ) * nbins + in2a 8657 ee = ( ispec - 1 ) * nbins + fn2a 8658 b = in2a 8659 DO c = ss, ee 8660 IF ( nsource(b) /= fillval ) THEN 8661 aerosol_mass(c)%source(k,j,i) = aerosol_mass(c)%source(k,j,i) + & 8662 mass_frac * nsource(b) * aero(b)%core * & 8663 prho 8664 ENDIF 8665 b = b+1 8666 ENDDO 8667 ! 8668 !-- Subrange 2b: 8669 IF ( .NOT. no_insoluble ) THEN 8670 WRITE(*,*) 'All sources are soluble!' 8671 ENDIF 8672 8673 END SUBROUTINE set_mass_source 8674 8965 ENDDO ! ig 8966 8967 ENDDO ! m 8968 8969 END SUBROUTINE set_gas_flux 8970 8971 END SUBROUTINE salsa_gas_emission_setup 8972 8675 8973 !------------------------------------------------------------------------------! 8676 8974 ! Description: … … 8680 8978 SUBROUTINE salsa_check_data_output( var, unit ) 8681 8979 8682 USE control_parameters, &8980 USE control_parameters, & 8683 8981 ONLY: message_string 8684 8982 8685 8983 IMPLICIT NONE 8686 8984 8687 CHARACTER (LEN=*) :: unit !<8688 CHARACTER (LEN=*) :: var !<8985 CHARACTER(LEN=*) :: unit !< 8986 CHARACTER(LEN=*) :: var !< 8689 8987 8690 8988 SELECT CASE ( TRIM( var ) ) 8691 8692 CASE ( 'g_H2SO4', 'g_HNO3', 'g_NH3', 'g_OCNV', 'g_OCSV', & 8693 'N_bin1', 'N_bin2', 'N_bin3', 'N_bin4', 'N_bin5', 'N_bin6', & 8694 'N_bin7', 'N_bin8', 'N_bin9', 'N_bin10', 'N_bin11', 'N_bin12', & 8695 'Ntot' ) 8989 8990 CASE ( 'g_H2SO4', 'g_HNO3', 'g_NH3', 'g_OCNV', 'g_OCSV', 'N_bin1', 'N_bin2', 'N_bin3', & 8991 'N_bin4', 'N_bin5', 'N_bin6', 'N_bin7', 'N_bin8', 'N_bin9', 'N_bin10', 'N_bin11', & 8992 'N_bin12', 'Ntot' ) 8696 8993 IF ( .NOT. salsa ) THEN 8697 message_string = 'output of "' // TRIM( var ) // '" requi' // & 8698 'res salsa = .TRUE.' 8699 CALL message( 'check_parameters', 'SA0006', 1, 2, 0, 6, 0 ) 8994 message_string = 'output of "' // TRIM( var ) // '" requires salsa = .TRUE.' 8995 CALL message( 'check_parameters', 'PA0645', 1, 2, 0, 6, 0 ) 8700 8996 ENDIF 8701 8997 unit = '#/m3' 8702 8998 8703 8999 CASE ( 'LDSA' ) 8704 9000 IF ( .NOT. salsa ) THEN 8705 message_string = 'output of "' // TRIM( var ) // '" requi' // & 8706 'res salsa = .TRUE.' 8707 CALL message( 'check_parameters', 'SA0003', 1, 2, 0, 6, 0 ) 9001 message_string = 'output of "' // TRIM( var ) // '" requires salsa = .TRUE.' 9002 CALL message( 'check_parameters', 'PA0646', 1, 2, 0, 6, 0 ) 8708 9003 ENDIF 8709 unit = 'mum2/cm3' 8710 8711 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6', & 8712 'm_bin7', 'm_bin8', 'm_bin9', 'm_bin10', 'm_bin11', 'm_bin12', & 8713 'PM2.5', 'PM10', 's_BC', 's_DU', 's_H2O', 's_NH', & 8714 's_NO', 's_OC', 's_SO4', 's_SS' ) 9004 unit = 'mum2/cm3' 9005 9006 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6', 'm_bin7', 'm_bin8', & 9007 'm_bin9', 'm_bin10', 'm_bin11', 'm_bin12', 'PM2.5', 'PM10', 's_BC', 's_DU', & 9008 's_H2O', 's_NH', 's_NO', 's_OC', 's_SO4', 's_SS' ) 8715 9009 IF ( .NOT. salsa ) THEN 8716 message_string = 'output of "' // TRIM( var ) // '" requi' // & 8717 'res salsa = .TRUE.' 8718 CALL message( 'check_parameters', 'SA0001', 1, 2, 0, 6, 0 ) 9010 message_string = 'output of "' // TRIM( var ) // '" requires salsa = .TRUE.' 9011 CALL message( 'check_parameters', 'PA0647', 1, 2, 0, 6, 0 ) 8719 9012 ENDIF 8720 9013 unit = 'kg/m3' 8721 9014 8722 9015 CASE DEFAULT 8723 9016 unit = 'illegal' … … 8726 9019 8727 9020 END SUBROUTINE salsa_check_data_output 8728 9021 8729 9022 !------------------------------------------------------------------------------! 8730 9023 ! … … 8734 9027 !------------------------------------------------------------------------------! 8735 9028 SUBROUTINE salsa_3d_data_averaging( mode, variable ) 8736 8737 9029 8738 9030 USE control_parameters … … 8744 9036 IMPLICIT NONE 8745 9037 8746 CHARACTER (LEN=*) :: mode !<8747 CHARACTER (LEN=*) :: variable !<8748 8749 INTEGER(iwp) :: b !< 8750 INTEGER(iwp) :: c!<8751 INTEGER(iwp) :: i !<8752 INTEGER(iwp) :: i cc!<8753 INTEGER(iwp) :: j !<8754 INTEGER(iwp) :: k !<8755 8756 REAL(wp) :: df !< For calculating LDSA: fraction of particles 8757 !< depositing in the alveolar (or tracheobronchial)8758 !< region of the lung. Depends on the particle size9038 CHARACTER(LEN=*) :: mode !< 9039 CHARACTER(LEN=10) :: vari !< 9040 CHARACTER(LEN=*) :: variable !< 9041 9042 INTEGER(iwp) :: found_index !< 9043 INTEGER(iwp) :: i !< 9044 INTEGER(iwp) :: ib !< 9045 INTEGER(iwp) :: ic !< 9046 INTEGER(iwp) :: j !< 9047 INTEGER(iwp) :: k !< 9048 9049 REAL(wp) :: df !< For calculating LDSA: fraction of particles depositing in the alveolar 9050 !< (or tracheobronchial) region of the lung. Depends on the particle size 8759 9051 REAL(wp) :: mean_d !< Particle diameter in micrometres 8760 9052 REAL(wp) :: nc !< Particle number concentration in units 1/cm**3 8761 REAL(wp) :: temp_bin !< 8762 REAL(wp), DIMENSION(:,:,:), POINTER :: to_be_resorted !< points to 8763 !<selected output variable8764 9053 REAL(wp) :: temp_bin !< temporary variable 9054 9055 REAL(wp), DIMENSION(:,:,:), POINTER :: to_be_resorted !< points to selected output variable 9056 8765 9057 temp_bin = 0.0_wp 8766 9058 … … 8768 9060 8769 9061 SELECT CASE ( TRIM( variable ) ) 8770 9062 8771 9063 CASE ( 'g_H2SO4' ) 8772 IF ( .NOT. ALLOCATED( g_ H2SO4_av ) ) THEN8773 ALLOCATE( g_ H2SO4_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9064 IF ( .NOT. ALLOCATED( g_h2so4_av ) ) THEN 9065 ALLOCATE( g_h2so4_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8774 9066 ENDIF 8775 g_ H2SO4_av = 0.0_wp8776 9067 g_h2so4_av = 0.0_wp 9068 8777 9069 CASE ( 'g_HNO3' ) 8778 IF ( .NOT. ALLOCATED( g_ HNO3_av ) ) THEN8779 ALLOCATE( g_ HNO3_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9070 IF ( .NOT. ALLOCATED( g_hno3_av ) ) THEN 9071 ALLOCATE( g_hno3_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8780 9072 ENDIF 8781 g_ HNO3_av = 0.0_wp8782 9073 g_hno3_av = 0.0_wp 9074 8783 9075 CASE ( 'g_NH3' ) 8784 IF ( .NOT. ALLOCATED( g_ NH3_av ) ) THEN8785 ALLOCATE( g_ NH3_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9076 IF ( .NOT. ALLOCATED( g_nh3_av ) ) THEN 9077 ALLOCATE( g_nh3_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8786 9078 ENDIF 8787 g_ NH3_av = 0.0_wp8788 9079 g_nh3_av = 0.0_wp 9080 8789 9081 CASE ( 'g_OCNV' ) 8790 IF ( .NOT. ALLOCATED( g_ OCNV_av ) ) THEN8791 ALLOCATE( g_ OCNV_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9082 IF ( .NOT. ALLOCATED( g_ocnv_av ) ) THEN 9083 ALLOCATE( g_ocnv_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8792 9084 ENDIF 8793 g_ OCNV_av = 0.0_wp8794 9085 g_ocnv_av = 0.0_wp 9086 8795 9087 CASE ( 'g_OCSV' ) 8796 IF ( .NOT. ALLOCATED( g_ OCSV_av ) ) THEN8797 ALLOCATE( g_ OCSV_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9088 IF ( .NOT. ALLOCATED( g_ocsv_av ) ) THEN 9089 ALLOCATE( g_ocsv_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8798 9090 ENDIF 8799 g_ OCSV_av = 0.0_wp8800 9091 g_ocsv_av = 0.0_wp 9092 8801 9093 CASE ( 'LDSA' ) 8802 IF ( .NOT. ALLOCATED( LDSA_av ) ) THEN8803 ALLOCATE( LDSA_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9094 IF ( .NOT. ALLOCATED( ldsa_av ) ) THEN 9095 ALLOCATE( ldsa_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8804 9096 ENDIF 8805 LDSA_av = 0.0_wp8806 8807 CASE ( 'N_bin1', 'N_bin2', 'N_bin3', 'N_bin4', 'N_bin5', 'N_bin6', &8808 'N_bin 7', 'N_bin8', 'N_bin9', 'N_bin10', 'N_bin11', 'N_bin12' )8809 IF ( .NOT. ALLOCATED( Nbins_av ) ) THEN8810 ALLOCATE( Nbins_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins) )9097 ldsa_av = 0.0_wp 9098 9099 CASE ( 'N_bin1', 'N_bin2', 'N_bin3', 'N_bin4', 'N_bin5', 'N_bin6', 'N_bin7', 'N_bin8', & 9100 'N_bin9', 'N_bin10', 'N_bin11', 'N_bin12' ) 9101 IF ( .NOT. ALLOCATED( nbins_av ) ) THEN 9102 ALLOCATE( nbins_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins_aerosol) ) 8811 9103 ENDIF 8812 Nbins_av = 0.0_wp8813 9104 nbins_av = 0.0_wp 9105 8814 9106 CASE ( 'Ntot' ) 8815 IF ( .NOT. ALLOCATED( Ntot_av ) ) THEN8816 ALLOCATE( Ntot_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9107 IF ( .NOT. ALLOCATED( ntot_av ) ) THEN 9108 ALLOCATE( ntot_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8817 9109 ENDIF 8818 Ntot_av = 0.0_wp8819 8820 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6', &8821 'm_bin 7', 'm_bin8', 'm_bin9', 'm_bin10', 'm_bin11', 'm_bin12' )9110 ntot_av = 0.0_wp 9111 9112 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6', 'm_bin7', 'm_bin8', & 9113 'm_bin9', 'm_bin10', 'm_bin11', 'm_bin12' ) 8822 9114 IF ( .NOT. ALLOCATED( mbins_av ) ) THEN 8823 ALLOCATE( mbins_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins ) )9115 ALLOCATE( mbins_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg,nbins_aerosol) ) 8824 9116 ENDIF 8825 9117 mbins_av = 0.0_wp 8826 9118 8827 9119 CASE ( 'PM2.5' ) 8828 IF ( .NOT. ALLOCATED( PM25_av ) ) THEN8829 ALLOCATE( PM25_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9120 IF ( .NOT. ALLOCATED( pm25_av ) ) THEN 9121 ALLOCATE( pm25_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8830 9122 ENDIF 8831 PM25_av = 0.0_wp8832 9123 pm25_av = 0.0_wp 9124 8833 9125 CASE ( 'PM10' ) 8834 IF ( .NOT. ALLOCATED( PM10_av ) ) THEN8835 ALLOCATE( PM10_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9126 IF ( .NOT. ALLOCATED( pm10_av ) ) THEN 9127 ALLOCATE( pm10_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8836 9128 ENDIF 8837 PM10_av = 0.0_wp8838 9129 pm10_av = 0.0_wp 9130 8839 9131 CASE ( 's_BC' ) 8840 IF ( .NOT. ALLOCATED( s_ BC_av ) ) THEN8841 ALLOCATE( s_ BC_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9132 IF ( .NOT. ALLOCATED( s_bc_av ) ) THEN 9133 ALLOCATE( s_bc_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8842 9134 ENDIF 8843 s_ BC_av = 0.0_wp8844 9135 s_bc_av = 0.0_wp 9136 8845 9137 CASE ( 's_DU' ) 8846 IF ( .NOT. ALLOCATED( s_ DU_av ) ) THEN8847 ALLOCATE( s_ DU_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9138 IF ( .NOT. ALLOCATED( s_du_av ) ) THEN 9139 ALLOCATE( s_du_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8848 9140 ENDIF 8849 s_ DU_av = 0.0_wp8850 9141 s_du_av = 0.0_wp 9142 8851 9143 CASE ( 's_H2O' ) 8852 IF ( .NOT. ALLOCATED( s_ H2O_av ) ) THEN8853 ALLOCATE( s_ H2O_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9144 IF ( .NOT. ALLOCATED( s_h2o_av ) ) THEN 9145 ALLOCATE( s_h2o_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8854 9146 ENDIF 8855 s_ H2O_av = 0.0_wp8856 9147 s_h2o_av = 0.0_wp 9148 8857 9149 CASE ( 's_NH' ) 8858 IF ( .NOT. ALLOCATED( s_ NH_av ) ) THEN8859 ALLOCATE( s_ NH_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9150 IF ( .NOT. ALLOCATED( s_nh_av ) ) THEN 9151 ALLOCATE( s_nh_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8860 9152 ENDIF 8861 s_ NH_av = 0.0_wp8862 9153 s_nh_av = 0.0_wp 9154 8863 9155 CASE ( 's_NO' ) 8864 IF ( .NOT. ALLOCATED( s_ NO_av ) ) THEN8865 ALLOCATE( s_ NO_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9156 IF ( .NOT. ALLOCATED( s_no_av ) ) THEN 9157 ALLOCATE( s_no_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8866 9158 ENDIF 8867 s_ NO_av = 0.0_wp8868 9159 s_no_av = 0.0_wp 9160 8869 9161 CASE ( 's_OC' ) 8870 IF ( .NOT. ALLOCATED( s_ OC_av ) ) THEN8871 ALLOCATE( s_ OC_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9162 IF ( .NOT. ALLOCATED( s_oc_av ) ) THEN 9163 ALLOCATE( s_oc_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8872 9164 ENDIF 8873 s_ OC_av = 0.0_wp8874 9165 s_oc_av = 0.0_wp 9166 8875 9167 CASE ( 's_SO4' ) 8876 IF ( .NOT. ALLOCATED( s_ SO4_av ) ) THEN8877 ALLOCATE( s_ SO4_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9168 IF ( .NOT. ALLOCATED( s_so4_av ) ) THEN 9169 ALLOCATE( s_so4_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8878 9170 ENDIF 8879 s_ SO4_av = 0.0_wp8880 9171 s_so4_av = 0.0_wp 9172 8881 9173 CASE ( 's_SS' ) 8882 IF ( .NOT. ALLOCATED( s_ SS_av ) ) THEN8883 ALLOCATE( s_ SS_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) )9174 IF ( .NOT. ALLOCATED( s_ss_av ) ) THEN 9175 ALLOCATE( s_ss_av(nzb:nzt+1,nysg:nyng,nxlg:nxrg) ) 8884 9176 ENDIF 8885 s_ SS_av = 0.0_wp8886 9177 s_ss_av = 0.0_wp 9178 8887 9179 CASE DEFAULT 8888 9180 CONTINUE … … 8893 9185 8894 9186 SELECT CASE ( TRIM( variable ) ) 8895 9187 8896 9188 CASE ( 'g_H2SO4', 'g_HNO3', 'g_NH3', 'g_OCNV', 'g_OCSV' ) 8897 IF ( TRIM( variable(3:) ) == 'H2SO4' ) THEN 8898 icc = 1 8899 to_be_resorted => g_H2SO4_av 8900 ELSEIF ( TRIM( variable(3:) ) == 'HNO3' ) THEN 8901 icc = 2 8902 to_be_resorted => g_HNO3_av 8903 ELSEIF ( TRIM( variable(3:) ) == 'NH3' ) THEN 8904 icc = 3 8905 to_be_resorted => g_NH3_av 8906 ELSEIF ( TRIM( variable(3:) ) == 'OCNV' ) THEN 8907 icc = 4 8908 to_be_resorted => g_OCNV_av 8909 ELSEIF ( TRIM( variable(3:) ) == 'OCSV' ) THEN 8910 icc = 5 8911 to_be_resorted => g_OCSV_av 8912 ENDIF 9189 9190 vari = TRIM( variable(3:) ) 9191 9192 SELECT CASE( vari ) 9193 9194 CASE( 'H2SO4' ) 9195 found_index = 1 9196 to_be_resorted => g_h2so4_av 9197 9198 CASE( 'HNO3' ) 9199 found_index = 2 9200 to_be_resorted => g_hno3_av 9201 9202 CASE( 'NH3' ) 9203 found_index = 3 9204 to_be_resorted => g_nh3_av 9205 9206 CASE( 'OCNV' ) 9207 found_index = 4 9208 to_be_resorted => g_ocnv_av 9209 9210 CASE( 'OCSN' ) 9211 found_index = 5 9212 to_be_resorted => g_ocsv_av 9213 9214 END SELECT 9215 8913 9216 DO i = nxlg, nxrg 8914 9217 DO j = nysg, nyng 8915 9218 DO k = nzb, nzt+1 8916 to_be_resorted(k,j,i) = to_be_resorted(k,j,i) + &8917 salsa_gas( icc)%conc(k,j,i)9219 to_be_resorted(k,j,i) = to_be_resorted(k,j,i) + & 9220 salsa_gas(found_index)%conc(k,j,i) 8918 9221 ENDDO 8919 9222 ENDDO 8920 9223 ENDDO 8921 9224 8922 9225 CASE ( 'LDSA' ) 8923 9226 DO i = nxlg, nxrg … … 8925 9228 DO k = nzb, nzt+1 8926 9229 temp_bin = 0.0_wp 8927 DO b = 1, nbins8928 ! 9230 DO ib = 1, nbins_aerosol 9231 ! 8929 9232 !-- Diameter in micrometres 8930 mean_d = 1.0E+6_wp * Ra_dry(k,j,i,b) * 2.0_wp 8931 ! 8932 !-- Deposition factor: alveolar (use Ra_dry) 8933 df = ( 0.01555_wp / mean_d ) * ( EXP( -0.416_wp * & 8934 ( LOG( mean_d ) + 2.84_wp )**2.0_wp ) & 8935 + 19.11_wp * EXP( -0.482_wp * & 8936 ( LOG( mean_d ) - 1.362_wp )**2.0_wp ) ) 8937 ! 9233 mean_d = 1.0E+6_wp * ra_dry(k,j,i,ib) * 2.0_wp 9234 ! 9235 !-- Deposition factor: alveolar (use ra_dry) 9236 df = ( 0.01555_wp / mean_d ) * ( EXP( -0.416_wp * ( LOG( mean_d ) + & 9237 2.84_wp )**2 ) + 19.11_wp * EXP( -0.482_wp * ( LOG( mean_d ) - & 9238 1.362_wp )**2 ) ) 9239 ! 8938 9240 !-- Number concentration in 1/cm3 8939 nc = 1.0E-6_wp * aerosol_number( b)%conc(k,j,i)8940 ! 8941 !-- Lung-deposited surface area LDSA (units mum2/cm3) 8942 temp_bin = temp_bin + pi * mean_d**2 .0_wp* df * nc9241 nc = 1.0E-6_wp * aerosol_number(ib)%conc(k,j,i) 9242 ! 9243 !-- Lung-deposited surface area LDSA (units mum2/cm3) 9244 temp_bin = temp_bin + pi * mean_d**2 * df * nc 8943 9245 ENDDO 8944 LDSA_av(k,j,i) = LDSA_av(k,j,i) + temp_bin9246 ldsa_av(k,j,i) = ldsa_av(k,j,i) + temp_bin 8945 9247 ENDDO 8946 9248 ENDDO 8947 9249 ENDDO 8948 8949 CASE ( 'N_bin1', 'N_bin2', 'N_bin3', 'N_bin4', 'N_bin5', 'N_bin6', &8950 'N_bin 7', 'N_bin8', 'N_bin9', 'N_bin10', 'N_bin11', 'N_bin12' )9250 9251 CASE ( 'N_bin1', 'N_bin2', 'N_bin3', 'N_bin4', 'N_bin5', 'N_bin6', 'N_bin7', 'N_bin8', & 9252 'N_bin9', 'N_bin10', 'N_bin11', 'N_bin12' ) 8951 9253 DO i = nxlg, nxrg 8952 9254 DO j = nysg, nyng 8953 9255 DO k = nzb, nzt+1 8954 DO b = 1, nbins 8955 Nbins_av(k,j,i,b) = Nbins_av(k,j,i,b) + & 8956 aerosol_number(b)%conc(k,j,i) 9256 DO ib = 1, nbins_aerosol 9257 nbins_av(k,j,i,ib) = nbins_av(k,j,i,ib) + aerosol_number(ib)%conc(k,j,i) 8957 9258 ENDDO 8958 9259 ENDDO 8959 9260 ENDDO 8960 9261 ENDDO 8961 9262 8962 9263 CASE ( 'Ntot' ) 8963 9264 DO i = nxlg, nxrg 8964 9265 DO j = nysg, nyng 8965 9266 DO k = nzb, nzt+1 8966 DO b = 1, nbins 8967 Ntot_av(k,j,i) = Ntot_av(k,j,i) + & 8968 aerosol_number(b)%conc(k,j,i) 9267 DO ib = 1, nbins_aerosol 9268 ntot_av(k,j,i) = ntot_av(k,j,i) + aerosol_number(ib)%conc(k,j,i) 8969 9269 ENDDO 8970 9270 ENDDO 8971 9271 ENDDO 8972 9272 ENDDO 8973 8974 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6', &8975 'm_bin 7', 'm_bin8', 'm_bin9', 'm_bin10', 'm_bin11', 'm_bin12' )9273 9274 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6', 'm_bin7', 'm_bin8', & 9275 'm_bin9', 'm_bin10', 'm_bin11', 'm_bin12' ) 8976 9276 DO i = nxlg, nxrg 8977 9277 DO j = nysg, nyng 8978 9278 DO k = nzb, nzt+1 8979 DO b = 1, nbins 8980 DO c = b, nbins*ncc_tot, nbins 8981 mbins_av(k,j,i,b) = mbins_av(k,j,i,b) + & 8982 aerosol_mass(c)%conc(k,j,i) 9279 DO ib = 1, nbins_aerosol 9280 DO ic = ib, nbins_aerosol * ncomponents_mass, nbins_aerosol 9281 mbins_av(k,j,i,ib) = mbins_av(k,j,i,ib) + aerosol_mass(ic)%conc(k,j,i) 8983 9282 ENDDO 8984 9283 ENDDO … … 8986 9285 ENDDO 8987 9286 ENDDO 8988 9287 8989 9288 CASE ( 'PM2.5' ) 8990 9289 DO i = nxlg, nxrg … … 8992 9291 DO k = nzb, nzt+1 8993 9292 temp_bin = 0.0_wp 8994 DO b = 1, nbins8995 IF ( 2.0_wp * Ra_dry(k,j,i,b) <= 2.5E-6_wp ) THEN8996 DO c = b, nbins*ncc, nbins8997 temp_bin = temp_bin + aerosol_mass( c)%conc(k,j,i)9293 DO ib = 1, nbins_aerosol 9294 IF ( 2.0_wp * ra_dry(k,j,i,ib) <= 2.5E-6_wp ) THEN 9295 DO ic = ib, nbins_aerosol * ncc, nbins_aerosol 9296 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 8998 9297 ENDDO 8999 9298 ENDIF 9000 9299 ENDDO 9001 PM25_av(k,j,i) = PM25_av(k,j,i) + temp_bin9300 pm25_av(k,j,i) = pm25_av(k,j,i) + temp_bin 9002 9301 ENDDO 9003 9302 ENDDO 9004 9303 ENDDO 9005 9304 9006 9305 CASE ( 'PM10' ) 9007 9306 DO i = nxlg, nxrg … … 9009 9308 DO k = nzb, nzt+1 9010 9309 temp_bin = 0.0_wp 9011 DO b = 1, nbins9012 IF ( 2.0_wp * Ra_dry(k,j,i,b) <= 10.0E-6_wp ) THEN9013 DO c = b, nbins*ncc, nbins9014 temp_bin = temp_bin + aerosol_mass( c)%conc(k,j,i)9310 DO ib = 1, nbins_aerosol 9311 IF ( 2.0_wp * ra_dry(k,j,i,ib) <= 10.0E-6_wp ) THEN 9312 DO ic = ib, nbins_aerosol * ncc, nbins_aerosol 9313 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 9015 9314 ENDDO 9016 9315 ENDIF 9017 9316 ENDDO 9018 PM10_av(k,j,i) = PM10_av(k,j,i) + temp_bin9317 pm10_av(k,j,i) = pm10_av(k,j,i) + temp_bin 9019 9318 ENDDO 9020 9319 ENDDO 9021 9320 ENDDO 9022 9023 CASE ( 's_BC', 's_DU', 's_H2O', 's_NH', 's_NO', 's_OC', 's_SO4', & 9024 's_SS' ) 9321 9322 CASE ( 's_BC', 's_DU', 's_H2O', 's_NH', 's_NO', 's_OC', 's_SO4', 's_SS' ) 9025 9323 IF ( is_used( prtcl, TRIM( variable(3:) ) ) ) THEN 9026 icc= get_index( prtcl, TRIM( variable(3:) ) )9027 IF ( TRIM( variable(3:) ) == 'BC' ) to_be_resorted => s_ BC_av9028 IF ( TRIM( variable(3:) ) == 'DU' ) to_be_resorted => s_ DU_av9029 IF ( TRIM( variable(3:) ) == 'NH' ) to_be_resorted => s_ NH_av9030 IF ( TRIM( variable(3:) ) == 'NO' ) to_be_resorted => s_ NO_av9031 IF ( TRIM( variable(3:) ) == 'OC' ) to_be_resorted => s_ OC_av9032 IF ( TRIM( variable(3:) ) == 'SO4' ) to_be_resorted => s_ SO4_av9033 IF ( TRIM( variable(3:) ) == 'SS' ) to_be_resorted => s_ SS_av9324 found_index = get_index( prtcl, TRIM( variable(3:) ) ) 9325 IF ( TRIM( variable(3:) ) == 'BC' ) to_be_resorted => s_bc_av 9326 IF ( TRIM( variable(3:) ) == 'DU' ) to_be_resorted => s_du_av 9327 IF ( TRIM( variable(3:) ) == 'NH' ) to_be_resorted => s_nh_av 9328 IF ( TRIM( variable(3:) ) == 'NO' ) to_be_resorted => s_no_av 9329 IF ( TRIM( variable(3:) ) == 'OC' ) to_be_resorted => s_oc_av 9330 IF ( TRIM( variable(3:) ) == 'SO4' ) to_be_resorted => s_so4_av 9331 IF ( TRIM( variable(3:) ) == 'SS' ) to_be_resorted => s_ss_av 9034 9332 DO i = nxlg, nxrg 9035 9333 DO j = nysg, nyng 9036 9334 DO k = nzb, nzt+1 9037 DO c = ( icc-1 )*nbins+1, icc*nbins9038 to_be_resorted(k,j,i) = to_be_resorted(k,j,i) + &9039 aerosol_mass( c)%conc(k,j,i)9335 DO ic = ( found_index-1 ) * nbins_aerosol + 1, found_index * nbins_aerosol 9336 to_be_resorted(k,j,i) = to_be_resorted(k,j,i) + & 9337 aerosol_mass(ic)%conc(k,j,i) 9040 9338 ENDDO 9041 9339 ENDDO … … 9043 9341 ENDDO 9044 9342 ENDIF 9045 9343 9046 9344 CASE DEFAULT 9047 9345 CONTINUE … … 9052 9350 9053 9351 SELECT CASE ( TRIM( variable ) ) 9054 9352 9055 9353 CASE ( 'g_H2SO4', 'g_HNO3', 'g_NH3', 'g_OCNV', 'g_OCSV' ) 9056 9354 IF ( TRIM( variable(3:) ) == 'H2SO4' ) THEN 9057 icc= 19058 to_be_resorted => g_ H2SO4_av9355 found_index = 1 9356 to_be_resorted => g_h2so4_av 9059 9357 ELSEIF ( TRIM( variable(3:) ) == 'HNO3' ) THEN 9060 icc= 29061 to_be_resorted => g_ HNO3_av9358 found_index = 2 9359 to_be_resorted => g_hno3_av 9062 9360 ELSEIF ( TRIM( variable(3:) ) == 'NH3' ) THEN 9063 icc= 39064 to_be_resorted => g_ NH3_av9361 found_index = 3 9362 to_be_resorted => g_nh3_av 9065 9363 ELSEIF ( TRIM( variable(3:) ) == 'OCNV' ) THEN 9066 icc= 49067 to_be_resorted => g_ OCNV_av9364 found_index = 4 9365 to_be_resorted => g_ocnv_av 9068 9366 ELSEIF ( TRIM( variable(3:) ) == 'OCSV' ) THEN 9069 icc= 59070 to_be_resorted => g_ OCSV_av9367 found_index = 5 9368 to_be_resorted => g_ocsv_av 9071 9369 ENDIF 9072 9370 DO i = nxlg, nxrg 9073 9371 DO j = nysg, nyng 9074 9372 DO k = nzb, nzt+1 9075 to_be_resorted(k,j,i) = to_be_resorted(k,j,i) &9076 /REAL( average_count_3d, KIND=wp )9373 to_be_resorted(k,j,i) = to_be_resorted(k,j,i) / & 9374 REAL( average_count_3d, KIND=wp ) 9077 9375 ENDDO 9078 9376 ENDDO 9079 9377 ENDDO 9080 9378 9081 9379 CASE ( 'LDSA' ) 9082 9380 DO i = nxlg, nxrg 9083 9381 DO j = nysg, nyng 9084 9382 DO k = nzb, nzt+1 9085 LDSA_av(k,j,i) = LDSA_av(k,j,i) & 9086 / REAL( average_count_3d, KIND=wp ) 9383 ldsa_av(k,j,i) = ldsa_av(k,j,i) / REAL( average_count_3d, KIND=wp ) 9087 9384 ENDDO 9088 9385 ENDDO 9089 9386 ENDDO 9090 9091 CASE ( 'N_bin1', 'N_bin2', 'N_bin3', 'N_bin4', 'N_bin5', 'N_bin6', &9092 'N_bin 7', 'N_bin8', 'N_bin9', 'N_bin10', 'N_bin11', 'N_bin12' )9387 9388 CASE ( 'N_bin1', 'N_bin2', 'N_bin3', 'N_bin4', 'N_bin5', 'N_bin6', 'N_bin7', 'N_bin8', & 9389 'N_bin9', 'N_bin10', 'N_bin11', 'N_bin12' ) 9093 9390 DO i = nxlg, nxrg 9094 9391 DO j = nysg, nyng 9095 9392 DO k = nzb, nzt+1 9096 DO b = 1, nbins 9097 Nbins_av(k,j,i,b) = Nbins_av(k,j,i,b) & 9098 / REAL( average_count_3d, KIND=wp ) 9393 DO ib = 1, nbins_aerosol 9394 nbins_av(k,j,i,ib) = nbins_av(k,j,i,ib) / REAL( average_count_3d, KIND=wp ) 9099 9395 ENDDO 9100 9396 ENDDO 9101 9397 ENDDO 9102 9398 ENDDO 9103 9399 9104 9400 CASE ( 'Ntot' ) 9105 9401 DO i = nxlg, nxrg 9106 9402 DO j = nysg, nyng 9107 9403 DO k = nzb, nzt+1 9108 Ntot_av(k,j,i) = Ntot_av(k,j,i) & 9109 / REAL( average_count_3d, KIND=wp ) 9404 ntot_av(k,j,i) = ntot_av(k,j,i) / REAL( average_count_3d, KIND=wp ) 9110 9405 ENDDO 9111 9406 ENDDO 9112 9407 ENDDO 9113 9114 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6', &9115 'm_bin 7', 'm_bin8', 'm_bin9', 'm_bin10', 'm_bin11', 'm_bin12' )9408 9409 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6', 'm_bin7', 'm_bin8', & 9410 'm_bin9', 'm_bin10', 'm_bin11', 'm_bin12' ) 9116 9411 DO i = nxlg, nxrg 9117 9412 DO j = nysg, nyng 9118 9413 DO k = nzb, nzt+1 9119 DO b = 1, nbins9120 DO c = b, nbins*ncc, nbins9121 mbins_av(k,j,i, b) = mbins_av(k,j,i,b)&9122 / REAL( average_count_3d, KIND=wp)9414 DO ib = 1, nbins_aerosol 9415 DO ic = ib, nbins_aerosol * ncomponents_mass, nbins_aerosol 9416 mbins_av(k,j,i,ib) = mbins_av(k,j,i,ib) / & 9417 REAL( average_count_3d, KIND=wp) 9123 9418 ENDDO 9124 9419 ENDDO … … 9126 9421 ENDDO 9127 9422 ENDDO 9128 9423 9129 9424 CASE ( 'PM2.5' ) 9130 9425 DO i = nxlg, nxrg 9131 9426 DO j = nysg, nyng 9132 9427 DO k = nzb, nzt+1 9133 PM25_av(k,j,i) = PM25_av(k,j,i) / & 9134 REAL( average_count_3d, KIND=wp ) 9428 pm25_av(k,j,i) = pm25_av(k,j,i) / REAL( average_count_3d, KIND=wp ) 9135 9429 ENDDO 9136 9430 ENDDO 9137 9431 ENDDO 9138 9432 9139 9433 CASE ( 'PM10' ) 9140 9434 DO i = nxlg, nxrg 9141 9435 DO j = nysg, nyng 9142 9436 DO k = nzb, nzt+1 9143 PM10_av(k,j,i) = PM10_av(k,j,i) / & 9144 REAL( average_count_3d, KIND=wp ) 9437 pm10_av(k,j,i) = pm10_av(k,j,i) / REAL( average_count_3d, KIND=wp ) 9145 9438 ENDDO 9146 9439 ENDDO 9147 9440 ENDDO 9148 9149 CASE ( 's_BC', 's_DU', 's_H2O', 's_NH', 's_NO', 's_OC', 's_SO4', & 9150 's_SS' ) 9441 9442 CASE ( 's_BC', 's_DU', 's_H2O', 's_NH', 's_NO', 's_OC', 's_SO4', 's_SS' ) 9151 9443 IF ( is_used( prtcl, TRIM( variable(3:) ) ) ) THEN 9152 icc= get_index( prtcl, TRIM( variable(3:) ) )9153 IF ( TRIM( variable(3:) ) == 'BC' ) to_be_resorted => s_ BC_av9154 IF ( TRIM( variable(3:) ) == 'DU' ) to_be_resorted => s_ DU_av9155 IF ( TRIM( variable(3:) ) == 'NH' ) to_be_resorted => s_ NH_av9156 IF ( TRIM( variable(3:) ) == 'NO' ) to_be_resorted => s_ NO_av9157 IF ( TRIM( variable(3:) ) == 'OC' ) to_be_resorted => s_ OC_av9158 IF ( TRIM( variable(3:) ) == 'SO4' ) to_be_resorted => s_ SO4_av9159 IF ( TRIM( variable(3:) ) == 'SS' ) to_be_resorted => s_ SS_av9444 found_index = get_index( prtcl, TRIM( variable(3:) ) ) 9445 IF ( TRIM( variable(3:) ) == 'BC' ) to_be_resorted => s_bc_av 9446 IF ( TRIM( variable(3:) ) == 'DU' ) to_be_resorted => s_du_av 9447 IF ( TRIM( variable(3:) ) == 'NH' ) to_be_resorted => s_nh_av 9448 IF ( TRIM( variable(3:) ) == 'NO' ) to_be_resorted => s_no_av 9449 IF ( TRIM( variable(3:) ) == 'OC' ) to_be_resorted => s_oc_av 9450 IF ( TRIM( variable(3:) ) == 'SO4' ) to_be_resorted => s_so4_av 9451 IF ( TRIM( variable(3:) ) == 'SS' ) to_be_resorted => s_ss_av 9160 9452 DO i = nxlg, nxrg 9161 9453 DO j = nysg, nyng 9162 9454 DO k = nzb, nzt+1 9163 to_be_resorted(k,j,i) = to_be_resorted(k,j,i) / &9455 to_be_resorted(k,j,i) = to_be_resorted(k,j,i) / & 9164 9456 REAL( average_count_3d, KIND=wp ) 9165 9457 ENDDO … … 9181 9473 !> Subroutine defining 2D output variables 9182 9474 !------------------------------------------------------------------------------! 9183 SUBROUTINE salsa_data_output_2d( av, variable, found, grid, mode, local_pf, & 9184 two_d, nzb_do, nzt_do ) 9185 9475 SUBROUTINE salsa_data_output_2d( av, variable, found, grid, mode, local_pf, two_d, nzb_do, nzt_do ) 9476 9186 9477 USE indices 9187 9478 … … 9191 9482 IMPLICIT NONE 9192 9483 9193 CHARACTER (LEN=*) :: grid !< 9194 CHARACTER (LEN=*) :: mode !< 9195 CHARACTER (LEN=*) :: variable !< 9196 CHARACTER (LEN=5) :: vari !< trimmed format of variable 9197 9198 INTEGER(iwp) :: av !< 9199 INTEGER(iwp) :: b !< running index: size bins 9200 INTEGER(iwp) :: c !< running index: mass bins 9201 INTEGER(iwp) :: i !< 9202 INTEGER(iwp) :: icc !< index of a chemical compound 9203 INTEGER(iwp) :: j !< 9204 INTEGER(iwp) :: k !< 9205 INTEGER(iwp) :: nzb_do !< 9206 INTEGER(iwp) :: nzt_do !< 9207 9208 LOGICAL :: found !< 9209 LOGICAL :: two_d !< flag parameter that indicates 2D variables 9210 !< (horizontal cross sections) 9211 9212 REAL(wp) :: df !< For calculating LDSA: fraction of particles 9213 !< depositing in the alveolar (or tracheobronchial) 9214 !< region of the lung. Depends on the particle size 9215 REAL(wp) :: fill_value = -9999.0_wp !< value for the _FillValue attribute 9216 REAL(wp) :: mean_d !< Particle diameter in micrometres 9217 REAL(wp) :: nc !< Particle number concentration in units 1/cm**3 9218 REAL(wp) :: temp_bin !< temporary array for calculating output variables 9219 9484 CHARACTER(LEN=*) :: grid !< 9485 CHARACTER(LEN=*) :: mode !< 9486 CHARACTER(LEN=*) :: variable !< 9487 CHARACTER(LEN=5) :: vari !< trimmed format of variable 9488 9489 INTEGER(iwp) :: av !< 9490 INTEGER(iwp) :: found_index !< index of a chemical compound 9491 INTEGER(iwp) :: i !< 9492 INTEGER(iwp) :: ib !< running index: size bins 9493 INTEGER(iwp) :: ic !< running index: mass bins 9494 INTEGER(iwp) :: j !< 9495 INTEGER(iwp) :: k !< 9496 INTEGER(iwp) :: nzb_do !< 9497 INTEGER(iwp) :: nzt_do !< 9498 9499 LOGICAL :: found !< 9500 LOGICAL :: two_d !< flag parameter to indicate 2D variables (horizontal cross sections) 9501 9502 REAL(wp) :: df !< For calculating LDSA: fraction of particles 9503 !< depositing in the alveolar (or tracheobronchial) 9504 !< region of the lung. Depends on the particle size 9505 REAL(wp) :: fill_value = -9999.0_wp !< value for the _FillValue attribute 9506 REAL(wp) :: mean_d !< Particle diameter in micrometres 9507 REAL(wp) :: nc !< Particle number concentration in units 1/cm**3 9508 REAL(wp) :: temp_bin !< temporary array for calculating output variables 9509 9220 9510 REAL(wp), DIMENSION(nxl:nxr,nys:nyn,nzb_do:nzt_do) :: local_pf !< output 9221 9511 9222 9512 REAL(wp), DIMENSION(:,:,:), POINTER :: to_be_resorted !< pointer 9223 9224 9513 ! 9225 9514 !-- Next statement is to avoid compiler warning about unused variable. May be removed in future. 9226 9515 IF ( two_d ) CONTINUE 9227 9516 9228 9517 found = .TRUE. 9229 9518 temp_bin = 0.0_wp 9230 9231 IF ( TRIM( variable(1:2) ) == 'g_' ) THEN 9232 vari = TRIM( variable( 3:LEN( TRIM( variable ) ) - 3 ) ) 9233 IF ( av == 0 ) THEN 9234 IF ( vari == 'H2SO4') icc = 1 9235 IF ( vari == 'HNO3') icc = 2 9236 IF ( vari == 'NH3') icc = 3 9237 IF ( vari == 'OCNV') icc = 4 9238 IF ( vari == 'OCSV') icc = 5 9239 DO i = nxl, nxr 9240 DO j = nys, nyn 9241 DO k = nzb_do, nzt_do 9242 local_pf(i,j,k) = MERGE( salsa_gas(icc)%conc(k,j,i), & 9243 REAL( fill_value, KIND = wp ), & 9244 BTEST( wall_flags_0(k,j,i), 0 ) ) 9245 ENDDO 9246 ENDDO 9247 ENDDO 9248 ELSE 9249 IF ( vari == 'H2SO4' ) to_be_resorted => g_H2SO4_av 9250 IF ( vari == 'HNO3' ) to_be_resorted => g_HNO3_av 9251 IF ( vari == 'NH3' ) to_be_resorted => g_NH3_av 9252 IF ( vari == 'OCNV' ) to_be_resorted => g_OCNV_av 9253 IF ( vari == 'OCSV' ) to_be_resorted => g_OCSV_av 9254 DO i = nxl, nxr 9255 DO j = nys, nyn 9256 DO k = nzb_do, nzt_do 9257 local_pf(i,j,k) = MERGE( to_be_resorted(k,j,i), & 9258 REAL( fill_value, KIND = wp ), & 9259 BTEST( wall_flags_0(k,j,i), 0 ) ) 9260 ENDDO 9261 ENDDO 9262 ENDDO 9263 ENDIF 9264 9265 IF ( mode == 'xy' ) grid = 'zu' 9266 9267 ELSEIF ( TRIM( variable(1:4) ) == 'LDSA' ) THEN 9268 IF ( av == 0 ) THEN 9269 DO i = nxl, nxr 9270 DO j = nys, nyn 9271 DO k = nzb_do, nzt_do 9272 temp_bin = 0.0_wp 9273 DO b = 1, nbins 9274 ! 9275 !-- Diameter in micrometres 9276 mean_d = 1.0E+6_wp * Ra_dry(k,j,i,b) * 2.0_wp 9277 ! 9278 !-- Deposition factor: alveolar 9279 df = ( 0.01555_wp / mean_d ) * ( EXP( -0.416_wp * ( LOG( & 9280 mean_d ) + 2.84_wp )**2.0_wp ) + 19.11_wp * EXP( & 9281 -0.482_wp * ( LOG( mean_d ) - 1.362_wp )**2.0_wp ) ) 9282 ! 9283 !-- Number concentration in 1/cm3 9284 nc = 1.0E-6_wp * aerosol_number(b)%conc(k,j,i) 9285 ! 9286 !-- Lung-deposited surface area LDSA (units mum2/cm3) 9287 temp_bin = temp_bin + pi * mean_d**2.0_wp * df * nc 9288 ENDDO 9289 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = & 9290 wp ), BTEST( wall_flags_0(k,j,i), 0 ) ) 9291 ENDDO 9292 ENDDO 9293 ENDDO 9294 ELSE 9295 DO i = nxl, nxr 9296 DO j = nys, nyn 9297 DO k = nzb_do, nzt_do 9298 local_pf(i,j,k) = MERGE( LDSA_av(k,j,i), REAL( fill_value, & 9299 KIND = wp ), BTEST( & 9300 wall_flags_0(k,j,i), 0 ) ) 9301 ENDDO 9302 ENDDO 9303 ENDDO 9304 ENDIF 9305 9306 IF ( mode == 'xy' ) grid = 'zu' 9307 9308 ELSEIF ( TRIM( variable(1:5) ) == 'N_bin' ) THEN 9309 9310 vari = TRIM( variable( 6:LEN( TRIM( variable ) ) - 3 ) ) 9311 9312 IF ( TRIM( vari ) == '1' ) b = 1 9313 IF ( TRIM( vari ) == '2' ) b = 2 9314 IF ( TRIM( vari ) == '3' ) b = 3 9315 IF ( TRIM( vari ) == '4' ) b = 4 9316 IF ( TRIM( vari ) == '5' ) b = 5 9317 IF ( TRIM( vari ) == '6' ) b = 6 9318 IF ( TRIM( vari ) == '7' ) b = 7 9319 IF ( TRIM( vari ) == '8' ) b = 8 9320 IF ( TRIM( vari ) == '9' ) b = 9 9321 IF ( TRIM( vari ) == '10' ) b = 10 9322 IF ( TRIM( vari ) == '11' ) b = 11 9323 IF ( TRIM( vari ) == '12' ) b = 12 9324 9325 IF ( av == 0 ) THEN 9326 DO i = nxl, nxr 9327 DO j = nys, nyn 9328 DO k = nzb_do, nzt_do 9329 local_pf(i,j,k) = MERGE( aerosol_number(b)%conc(k,j,i), & 9330 REAL( fill_value, KIND = wp ), & 9331 BTEST( wall_flags_0(k,j,i), 0 ) ) 9332 ENDDO 9333 ENDDO 9334 ENDDO 9335 ELSE 9336 DO i = nxl, nxr 9337 DO j = nys, nyn 9338 DO k = nzb_do, nzt_do 9339 local_pf(i,j,k) = MERGE( Nbins_av(k,j,i,b), & 9340 REAL( fill_value, KIND = wp ), & 9341 BTEST( wall_flags_0(k,j,i), 0 ) ) 9342 ENDDO 9343 ENDDO 9344 ENDDO 9345 ENDIF 9346 9347 IF ( mode == 'xy' ) grid = 'zu' 9348 9349 ELSEIF ( TRIM( variable(1:4) ) == 'Ntot' ) THEN 9350 IF ( av == 0 ) THEN 9351 DO i = nxl, nxr 9352 DO j = nys, nyn 9353 DO k = nzb_do, nzt_do 9354 temp_bin = 0.0_wp 9355 DO b = 1, nbins 9356 temp_bin = temp_bin + aerosol_number(b)%conc(k,j,i) 9357 ENDDO 9358 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = & 9359 wp ), BTEST( wall_flags_0(k,j,i), 0 ) ) 9360 ENDDO 9361 ENDDO 9362 ENDDO 9363 ELSE 9364 DO i = nxl, nxr 9365 DO j = nys, nyn 9366 DO k = nzb_do, nzt_do 9367 local_pf(i,j,k) = MERGE( Ntot_av(k,j,i), REAL( fill_value, & 9368 KIND = wp ), BTEST( & 9369 wall_flags_0(k,j,i), 0 ) ) 9370 ENDDO 9371 ENDDO 9372 ENDDO 9373 ENDIF 9374 9375 IF ( mode == 'xy' ) grid = 'zu' 9376 9377 9378 ELSEIF ( TRIM( variable(1:5) ) == 'm_bin' ) THEN 9379 9380 vari = TRIM( variable( 6:LEN( TRIM( variable ) ) - 3 ) ) 9381 9382 IF ( TRIM( vari ) == '1' ) b = 1 9383 IF ( TRIM( vari ) == '2' ) b = 2 9384 IF ( TRIM( vari ) == '3' ) b = 3 9385 IF ( TRIM( vari ) == '4' ) b = 4 9386 IF ( TRIM( vari ) == '5' ) b = 5 9387 IF ( TRIM( vari ) == '6' ) b = 6 9388 IF ( TRIM( vari ) == '7' ) b = 7 9389 IF ( TRIM( vari ) == '8' ) b = 8 9390 IF ( TRIM( vari ) == '9' ) b = 9 9391 IF ( TRIM( vari ) == '10' ) b = 10 9392 IF ( TRIM( vari ) == '11' ) b = 11 9393 IF ( TRIM( vari ) == '12' ) b = 12 9394 9395 IF ( av == 0 ) THEN 9396 DO i = nxl, nxr 9397 DO j = nys, nyn 9398 DO k = nzb_do, nzt_do 9399 temp_bin = 0.0_wp 9400 DO c = b, ncc_tot * nbins, nbins 9401 temp_bin = temp_bin + aerosol_mass(c)%conc(k,j,i) 9402 ENDDO 9403 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, & 9404 KIND = wp ), BTEST( & 9405 wall_flags_0(k,j,i), 0 ) ) 9406 ENDDO 9407 ENDDO 9408 ENDDO 9409 ELSE 9410 DO i = nxl, nxr 9411 DO j = nys, nyn 9412 DO k = nzb_do, nzt_do 9413 local_pf(i,j,k) = MERGE( mbins_av(k,j,i,b), REAL( fill_value,& 9414 KIND = wp ), BTEST( & 9415 wall_flags_0(k,j,i), 0 ) ) 9416 ENDDO 9417 ENDDO 9418 ENDDO 9419 ENDIF 9420 9421 IF ( mode == 'xy' ) grid = 'zu' 9422 9423 ELSEIF ( TRIM( variable(1:5) ) == 'PM2.5' ) THEN 9424 IF ( av == 0 ) THEN 9425 DO i = nxl, nxr 9426 DO j = nys, nyn 9427 DO k = nzb_do, nzt_do 9428 temp_bin = 0.0_wp 9429 DO b = 1, nbins 9430 IF ( 2.0_wp * Ra_dry(k,j,i,b) <= 2.5E-6_wp ) THEN 9431 DO c = b, nbins*ncc, nbins 9432 temp_bin = temp_bin + aerosol_mass(c)%conc(k,j,i) 9433 ENDDO 9434 ENDIF 9435 ENDDO 9436 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, & 9437 KIND = wp ), BTEST( & 9438 wall_flags_0(k,j,i), 0 ) ) 9439 ENDDO 9440 ENDDO 9441 ENDDO 9442 ELSE 9443 DO i = nxl, nxr 9444 DO j = nys, nyn 9445 DO k = nzb_do, nzt_do 9446 local_pf(i,j,k) = MERGE( PM25_av(k,j,i), REAL( fill_value, & 9447 KIND = wp ), BTEST( & 9448 wall_flags_0(k,j,i), 0 ) ) 9449 ENDDO 9450 ENDDO 9451 ENDDO 9452 ENDIF 9453 9454 IF ( mode == 'xy' ) grid = 'zu' 9455 9456 9457 ELSEIF ( TRIM( variable(1:4) ) == 'PM10' ) THEN 9458 IF ( av == 0 ) THEN 9459 DO i = nxl, nxr 9460 DO j = nys, nyn 9461 DO k = nzb_do, nzt_do 9462 temp_bin = 0.0_wp 9463 DO b = 1, nbins 9464 IF ( 2.0_wp * Ra_dry(k,j,i,b) <= 10.0E-6_wp ) THEN 9465 DO c = b, nbins*ncc, nbins 9466 temp_bin = temp_bin + aerosol_mass(c)%conc(k,j,i) 9467 ENDDO 9468 ENDIF 9469 ENDDO 9470 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, & 9471 KIND = wp ), BTEST( & 9472 wall_flags_0(k,j,i), 0 ) ) 9473 ENDDO 9474 ENDDO 9475 ENDDO 9476 ELSE 9477 DO i = nxl, nxr 9478 DO j = nys, nyn 9479 DO k = nzb_do, nzt_do 9480 local_pf(i,j,k) = MERGE( PM10_av(k,j,i), REAL( fill_value, & 9481 KIND = wp ), BTEST( & 9482 wall_flags_0(k,j,i), 0 ) ) 9483 ENDDO 9484 ENDDO 9485 ENDDO 9486 ENDIF 9487 9488 IF ( mode == 'xy' ) grid = 'zu' 9489 9490 ELSEIF ( TRIM( variable(1:2) ) == 's_' ) THEN 9491 vari = TRIM( variable( 3:LEN( TRIM( variable ) ) - 3 ) ) 9492 IF ( is_used( prtcl, vari ) ) THEN 9493 icc = get_index( prtcl, vari ) 9519 9520 SELECT CASE ( TRIM( variable( 1:LEN( TRIM( variable ) ) - 3 ) ) ) ! cut out _xy, _xz or _yz 9521 9522 CASE ( 'g_H2SO4', 'g_HNO3', 'g_NH3', 'g_OCNV', 'g_OCSV' ) 9523 vari = TRIM( variable( 3:LEN( TRIM( variable ) ) - 3 ) ) 9494 9524 IF ( av == 0 ) THEN 9525 IF ( vari == 'H2SO4') found_index = 1 9526 IF ( vari == 'HNO3') found_index = 2 9527 IF ( vari == 'NH3') found_index = 3 9528 IF ( vari == 'OCNV') found_index = 4 9529 IF ( vari == 'OCSV') found_index = 5 9495 9530 DO i = nxl, nxr 9496 9531 DO j = nys, nyn 9497 9532 DO k = nzb_do, nzt_do 9498 temp_bin = 0.0_wp 9499 DO c = ( icc-1 )*nbins+1, icc*nbins, 1 9500 temp_bin = temp_bin + aerosol_mass(c)%conc(k,j,i) 9501 ENDDO 9502 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, & 9503 KIND = wp ), BTEST( & 9504 wall_flags_0(k,j,i), 0 ) ) 9533 local_pf(i,j,k) = MERGE( salsa_gas(found_index)%conc(k,j,i), REAL( fill_value, & 9534 KIND = wp ), BTEST( wall_flags_0(k,j,i), 0 ) ) 9505 9535 ENDDO 9506 9536 ENDDO 9507 9537 ENDDO 9508 9538 ELSE 9509 IF ( vari == 'BC' ) to_be_resorted => s_BC_av 9510 IF ( vari == 'DU' ) to_be_resorted => s_DU_av 9511 IF ( vari == 'NH' ) to_be_resorted => s_NH_av 9512 IF ( vari == 'NO' ) to_be_resorted => s_NO_av 9513 IF ( vari == 'OC' ) to_be_resorted => s_OC_av 9514 IF ( vari == 'SO4' ) to_be_resorted => s_SO4_av 9515 IF ( vari == 'SS' ) to_be_resorted => s_SS_av 9539 IF ( vari == 'H2SO4' ) to_be_resorted => g_h2so4_av 9540 IF ( vari == 'HNO3' ) to_be_resorted => g_hno3_av 9541 IF ( vari == 'NH3' ) to_be_resorted => g_nh3_av 9542 IF ( vari == 'OCNV' ) to_be_resorted => g_ocnv_av 9543 IF ( vari == 'OCSV' ) to_be_resorted => g_ocsv_av 9516 9544 DO i = nxl, nxr 9517 9545 DO j = nys, nyn 9518 9546 DO k = nzb_do, nzt_do 9519 local_pf(i,j,k) = MERGE( to_be_resorted(k,j,i), & 9520 REAL( fill_value, KIND = wp ), & 9521 BTEST( wall_flags_0(k,j,i), 0 ) ) 9547 local_pf(i,j,k) = MERGE( to_be_resorted(k,j,i), REAL( fill_value, & 9548 KIND = wp ), BTEST( wall_flags_0(k,j,i), 0 ) ) 9522 9549 ENDDO 9523 9550 ENDDO 9524 9551 ENDDO 9525 9552 ENDIF 9526 ELSE 9527 local_pf = fill_value 9528 ENDIF 9529 9530 IF ( mode == 'xy' ) grid = 'zu' 9531 9532 ELSE 9533 found = .FALSE. 9534 grid = 'none' 9535 9536 ENDIF 9537 9538 END SUBROUTINE salsa_data_output_2d 9539 9540 9541 !------------------------------------------------------------------------------! 9542 ! 9543 ! Description: 9544 ! ------------ 9545 !> Subroutine defining 3D output variables 9546 !------------------------------------------------------------------------------! 9547 SUBROUTINE salsa_data_output_3d( av, variable, found, local_pf, nzb_do, & 9548 nzt_do ) 9549 9550 USE indices 9551 9552 USE kinds 9553 9554 9555 IMPLICIT NONE 9556 9557 CHARACTER (LEN=*), INTENT(in) :: variable !< 9558 9559 INTEGER(iwp) :: av !< 9560 INTEGER(iwp) :: b !< running index: size bins 9561 INTEGER(iwp) :: c !< running index: mass bins 9562 INTEGER(iwp) :: i !< 9563 INTEGER(iwp) :: icc !< index of a chemical compound 9564 INTEGER(iwp) :: j !< 9565 INTEGER(iwp) :: k !< 9566 INTEGER(iwp) :: nzb_do !< 9567 INTEGER(iwp) :: nzt_do !< 9568 9569 LOGICAL :: found !< 9570 9571 REAL(wp) :: df !< For calculating LDSA: fraction of particles 9572 !< depositing in the alveolar (or tracheobronchial) 9573 !< region of the lung. Depends on the particle size 9574 REAL(wp) :: fill_value = -9999.0_wp !< value for the _FillValue attribute 9575 REAL(wp) :: mean_d !< Particle diameter in micrometres 9576 REAL(wp) :: nc !< Particle number concentration in units 1/cm**3 9577 REAL(wp) :: temp_bin !< temporary array for calculating output variables 9578 9579 REAL(sp), DIMENSION(nxl:nxr,nys:nyn,nzb_do:nzt_do) :: local_pf !< local 9580 9581 REAL(wp), DIMENSION(:,:,:), POINTER :: to_be_resorted !< pointer 9582 9583 9584 found = .TRUE. 9585 temp_bin = 0.0_wp 9586 9587 SELECT CASE ( TRIM( variable ) ) 9588 9589 CASE ( 'g_H2SO4', 'g_HNO3', 'g_NH3', 'g_OCNV', 'g_OCSV' ) 9590 IF ( av == 0 ) THEN 9591 IF ( TRIM( variable ) == 'g_H2SO4') icc = 1 9592 IF ( TRIM( variable ) == 'g_HNO3') icc = 2 9593 IF ( TRIM( variable ) == 'g_NH3') icc = 3 9594 IF ( TRIM( variable ) == 'g_OCNV') icc = 4 9595 IF ( TRIM( variable ) == 'g_OCSV') icc = 5 9596 9597 DO i = nxl, nxr 9598 DO j = nys, nyn 9599 DO k = nzb_do, nzt_do 9600 local_pf(i,j,k) = MERGE( salsa_gas(icc)%conc(k,j,i), & 9601 REAL( fill_value, KIND = wp ), & 9602 BTEST( wall_flags_0(k,j,i), 0 ) ) 9603 ENDDO 9604 ENDDO 9605 ENDDO 9606 ELSE 9607 IF ( TRIM( variable(3:) ) == 'H2SO4' ) to_be_resorted => g_H2SO4_av 9608 IF ( TRIM( variable(3:) ) == 'HNO3' ) to_be_resorted => g_HNO3_av 9609 IF ( TRIM( variable(3:) ) == 'NH3' ) to_be_resorted => g_NH3_av 9610 IF ( TRIM( variable(3:) ) == 'OCNV' ) to_be_resorted => g_OCNV_av 9611 IF ( TRIM( variable(3:) ) == 'OCSV' ) to_be_resorted => g_OCSV_av 9612 DO i = nxl, nxr 9613 DO j = nys, nyn 9614 DO k = nzb_do, nzt_do 9615 local_pf(i,j,k) = MERGE( to_be_resorted(k,j,i), & 9616 REAL( fill_value, KIND = wp ), & 9617 BTEST( wall_flags_0(k,j,i), 0 ) ) 9618 ENDDO 9619 ENDDO 9620 ENDDO 9621 ENDIF 9622 9553 9554 IF ( mode == 'xy' ) grid = 'zu' 9555 9623 9556 CASE ( 'LDSA' ) 9624 9557 IF ( av == 0 ) THEN … … 9627 9560 DO k = nzb_do, nzt_do 9628 9561 temp_bin = 0.0_wp 9629 DO b = 1, nbins9630 ! 9562 DO ib = 1, nbins_aerosol 9563 ! 9631 9564 !-- Diameter in micrometres 9632 mean_d = 1.0E+6_wp * Ra_dry(k,j,i,b) * 2.0_wp 9633 ! 9634 !-- Deposition factor: alveolar 9635 df = ( 0.01555_wp / mean_d ) * ( EXP( -0.416_wp * & 9636 ( LOG( mean_d ) + 2.84_wp )**2.0_wp ) + 19.11_wp & 9637 * EXP( -0.482_wp * ( LOG( mean_d ) - 1.362_wp & 9638 )**2.0_wp ) ) 9639 ! 9565 mean_d = 1.0E+6_wp * ra_dry(k,j,i,ib) * 2.0_wp 9566 ! 9567 !-- Deposition factor: alveolar 9568 df = ( 0.01555_wp / mean_d ) * ( EXP( -0.416_wp * ( LOG( mean_d ) + & 9569 2.84_wp )**2 ) + 19.11_wp * EXP( -0.482_wp * ( LOG( mean_d ) - & 9570 1.362_wp )**2 ) ) 9571 ! 9640 9572 !-- Number concentration in 1/cm3 9641 nc = 1.0E-6_wp * aerosol_number( b)%conc(k,j,i)9642 ! 9573 nc = 1.0E-6_wp * aerosol_number(ib)%conc(k,j,i) 9574 ! 9643 9575 !-- Lung-deposited surface area LDSA (units mum2/cm3) 9644 temp_bin = temp_bin + pi * mean_d**2 .0_wp * df * nc9576 temp_bin = temp_bin + pi * mean_d**2 * df * nc 9645 9577 ENDDO 9646 local_pf(i,j,k) = MERGE( temp_bin, & 9647 REAL( fill_value, KIND = wp ), & 9578 9579 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = wp ), & 9580 BTEST( wall_flags_0(k,j,i), 0 ) ) 9581 ENDDO 9582 ENDDO 9583 ENDDO 9584 ELSE 9585 DO i = nxl, nxr 9586 DO j = nys, nyn 9587 DO k = nzb_do, nzt_do 9588 local_pf(i,j,k) = MERGE( ldsa_av(k,j,i), REAL( fill_value, KIND = wp ), & 9589 BTEST( wall_flags_0(k,j,i), 0 ) ) 9590 ENDDO 9591 ENDDO 9592 ENDDO 9593 ENDIF 9594 9595 IF ( mode == 'xy' ) grid = 'zu' 9596 9597 CASE ( 'N_bin1', 'N_bin2', 'N_bin3', 'N_bin4', 'N_bin5', 'N_bin6', 'N_bin7', 'N_bin8', & 9598 'N_bin9', 'N_bin10' , 'N_bin11', 'N_bin12' ) 9599 vari = TRIM( variable( 6:LEN( TRIM( variable ) ) - 3 ) ) 9600 9601 IF ( vari == '1' ) ib = 1 9602 IF ( vari == '2' ) ib = 2 9603 IF ( vari == '3' ) ib = 3 9604 IF ( vari == '4' ) ib = 4 9605 IF ( vari == '5' ) ib = 5 9606 IF ( vari == '6' ) ib = 6 9607 IF ( vari == '7' ) ib = 7 9608 IF ( vari == '8' ) ib = 8 9609 IF ( vari == '9' ) ib = 9 9610 IF ( vari == '10' ) ib = 10 9611 IF ( vari == '11' ) ib = 11 9612 IF ( vari == '12' ) ib = 12 9613 9614 IF ( av == 0 ) THEN 9615 DO i = nxl, nxr 9616 DO j = nys, nyn 9617 DO k = nzb_do, nzt_do 9618 local_pf(i,j,k) = MERGE( aerosol_number(ib)%conc(k,j,i), REAL( fill_value, & 9619 KIND = wp ), BTEST( wall_flags_0(k,j,i), 0 ) ) 9620 ENDDO 9621 ENDDO 9622 ENDDO 9623 ELSE 9624 DO i = nxl, nxr 9625 DO j = nys, nyn 9626 DO k = nzb_do, nzt_do 9627 local_pf(i,j,k) = MERGE( nbins_av(k,j,i,ib), REAL( fill_value, KIND = wp ), & 9628 BTEST( wall_flags_0(k,j,i), 0 ) ) 9629 ENDDO 9630 ENDDO 9631 ENDDO 9632 ENDIF 9633 9634 IF ( mode == 'xy' ) grid = 'zu' 9635 9636 CASE ( 'Ntot' ) 9637 9638 IF ( av == 0 ) THEN 9639 DO i = nxl, nxr 9640 DO j = nys, nyn 9641 DO k = nzb_do, nzt_do 9642 temp_bin = 0.0_wp 9643 DO ib = 1, nbins_aerosol 9644 temp_bin = temp_bin + aerosol_number(ib)%conc(k,j,i) 9645 ENDDO 9646 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = wp ), & 9647 BTEST( wall_flags_0(k,j,i), 0 ) ) 9648 ENDDO 9649 ENDDO 9650 ENDDO 9651 ELSE 9652 DO i = nxl, nxr 9653 DO j = nys, nyn 9654 DO k = nzb_do, nzt_do 9655 local_pf(i,j,k) = MERGE( ntot_av(k,j,i), REAL( fill_value, KIND = wp ), & 9656 BTEST( wall_flags_0(k,j,i), 0 ) ) 9657 ENDDO 9658 ENDDO 9659 ENDDO 9660 ENDIF 9661 9662 IF ( mode == 'xy' ) grid = 'zu' 9663 9664 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6', 'm_bin7', 'm_bin8', & 9665 'm_bin9', 'm_bin10' , 'm_bin11', 'm_bin12' ) 9666 vari = TRIM( variable( 6:LEN( TRIM( variable ) ) - 3 ) ) 9667 9668 IF ( vari == '1' ) ib = 1 9669 IF ( vari == '2' ) ib = 2 9670 IF ( vari == '3' ) ib = 3 9671 IF ( vari == '4' ) ib = 4 9672 IF ( vari == '5' ) ib = 5 9673 IF ( vari == '6' ) ib = 6 9674 IF ( vari == '7' ) ib = 7 9675 IF ( vari == '8' ) ib = 8 9676 IF ( vari == '9' ) ib = 9 9677 IF ( vari == '10' ) ib = 10 9678 IF ( vari == '11' ) ib = 11 9679 IF ( vari == '12' ) ib = 12 9680 9681 IF ( av == 0 ) THEN 9682 DO i = nxl, nxr 9683 DO j = nys, nyn 9684 DO k = nzb_do, nzt_do 9685 temp_bin = 0.0_wp 9686 DO ic = ib, ncomponents_mass * nbins_aerosol, nbins_aerosol 9687 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 9688 ENDDO 9689 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = wp ), & 9690 BTEST( wall_flags_0(k,j,i), 0 ) ) 9691 ENDDO 9692 ENDDO 9693 ENDDO 9694 ELSE 9695 DO i = nxl, nxr 9696 DO j = nys, nyn 9697 DO k = nzb_do, nzt_do 9698 local_pf(i,j,k) = MERGE( mbins_av(k,j,i,ib), REAL( fill_value, KIND = wp ), & 9699 BTEST( wall_flags_0(k,j,i), 0 ) ) 9700 ENDDO 9701 ENDDO 9702 ENDDO 9703 ENDIF 9704 9705 IF ( mode == 'xy' ) grid = 'zu' 9706 9707 CASE ( 'PM2.5' ) 9708 IF ( av == 0 ) THEN 9709 DO i = nxl, nxr 9710 DO j = nys, nyn 9711 DO k = nzb_do, nzt_do 9712 temp_bin = 0.0_wp 9713 DO ib = 1, nbins_aerosol 9714 IF ( 2.0_wp * ra_dry(k,j,i,ib) <= 2.5E-6_wp ) THEN 9715 DO ic = ib, nbins_aerosol * ncc, nbins_aerosol 9716 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 9717 ENDDO 9718 ENDIF 9719 ENDDO 9720 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = wp ), & 9721 BTEST( wall_flags_0(k,j,i), 0 ) ) 9722 ENDDO 9723 ENDDO 9724 ENDDO 9725 ELSE 9726 DO i = nxl, nxr 9727 DO j = nys, nyn 9728 DO k = nzb_do, nzt_do 9729 local_pf(i,j,k) = MERGE( pm25_av(k,j,i), REAL( fill_value, KIND = wp ), & 9730 BTEST( wall_flags_0(k,j,i), 0 ) ) 9731 ENDDO 9732 ENDDO 9733 ENDDO 9734 ENDIF 9735 9736 IF ( mode == 'xy' ) grid = 'zu' 9737 9738 CASE ( 'PM10' ) 9739 IF ( av == 0 ) THEN 9740 DO i = nxl, nxr 9741 DO j = nys, nyn 9742 DO k = nzb_do, nzt_do 9743 temp_bin = 0.0_wp 9744 DO ib = 1, nbins_aerosol 9745 IF ( 2.0_wp * ra_dry(k,j,i,ib) <= 10.0E-6_wp ) THEN 9746 DO ic = ib, nbins_aerosol * ncc, nbins_aerosol 9747 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 9748 ENDDO 9749 ENDIF 9750 ENDDO 9751 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = wp ), & 9752 BTEST( wall_flags_0(k,j,i), 0 ) ) 9753 ENDDO 9754 ENDDO 9755 ENDDO 9756 ELSE 9757 DO i = nxl, nxr 9758 DO j = nys, nyn 9759 DO k = nzb_do, nzt_do 9760 local_pf(i,j,k) = MERGE( pm10_av(k,j,i), REAL( fill_value, KIND = wp ), & 9761 BTEST( wall_flags_0(k,j,i), 0 ) ) 9762 ENDDO 9763 ENDDO 9764 ENDDO 9765 ENDIF 9766 9767 IF ( mode == 'xy' ) grid = 'zu' 9768 9769 CASE ( 's_BC', 's_DU', 's_H2O', 's_NH', 's_NO', 's_OC', 's_SO4', 's_SS' ) 9770 vari = TRIM( variable( 3:LEN( TRIM( variable ) ) - 3 ) ) 9771 IF ( is_used( prtcl, vari ) ) THEN 9772 found_index = get_index( prtcl, vari ) 9773 IF ( av == 0 ) THEN 9774 DO i = nxl, nxr 9775 DO j = nys, nyn 9776 DO k = nzb_do, nzt_do 9777 temp_bin = 0.0_wp 9778 DO ic = ( found_index-1 ) * nbins_aerosol+1, found_index * nbins_aerosol 9779 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 9780 ENDDO 9781 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = wp ), & 9782 BTEST( wall_flags_0(k,j,i), 0 ) ) 9783 ENDDO 9784 ENDDO 9785 ENDDO 9786 ELSE 9787 IF ( vari == 'BC' ) to_be_resorted => s_bc_av 9788 IF ( vari == 'DU' ) to_be_resorted => s_du_av 9789 IF ( vari == 'NH' ) to_be_resorted => s_nh_av 9790 IF ( vari == 'NO' ) to_be_resorted => s_no_av 9791 IF ( vari == 'OC' ) to_be_resorted => s_oc_av 9792 IF ( vari == 'SO4' ) to_be_resorted => s_so4_av 9793 IF ( vari == 'SS' ) to_be_resorted => s_ss_av 9794 DO i = nxl, nxr 9795 DO j = nys, nyn 9796 DO k = nzb_do, nzt_do 9797 local_pf(i,j,k) = MERGE( to_be_resorted(k,j,i), REAL( fill_value, & 9798 KIND = wp ), BTEST( wall_flags_0(k,j,i), 0 ) ) 9799 ENDDO 9800 ENDDO 9801 ENDDO 9802 ENDIF 9803 ELSE 9804 local_pf = fill_value 9805 ENDIF 9806 9807 IF ( mode == 'xy' ) grid = 'zu' 9808 9809 CASE DEFAULT 9810 found = .FALSE. 9811 grid = 'none' 9812 9813 END SELECT 9814 9815 END SUBROUTINE salsa_data_output_2d 9816 9817 !------------------------------------------------------------------------------! 9818 ! 9819 ! Description: 9820 ! ------------ 9821 !> Subroutine defining 3D output variables 9822 !------------------------------------------------------------------------------! 9823 SUBROUTINE salsa_data_output_3d( av, variable, found, local_pf, nzb_do, nzt_do ) 9824 9825 USE indices 9826 9827 USE kinds 9828 9829 9830 IMPLICIT NONE 9831 9832 CHARACTER(LEN=*), INTENT(in) :: variable !< 9833 9834 INTEGER(iwp) :: av !< 9835 INTEGER(iwp) :: found_index !< index of a chemical compound 9836 INTEGER(iwp) :: ib !< running index: size bins 9837 INTEGER(iwp) :: ic !< running index: mass bins 9838 INTEGER(iwp) :: i !< 9839 INTEGER(iwp) :: j !< 9840 INTEGER(iwp) :: k !< 9841 INTEGER(iwp) :: nzb_do !< 9842 INTEGER(iwp) :: nzt_do !< 9843 9844 LOGICAL :: found !< 9845 9846 REAL(wp) :: df !< For calculating LDSA: fraction of particles 9847 !< depositing in the alveolar (or tracheobronchial) 9848 !< region of the lung. Depends on the particle size 9849 REAL(wp) :: fill_value = -9999.0_wp !< value for the _FillValue attribute 9850 REAL(wp) :: mean_d !< Particle diameter in micrometres 9851 REAL(wp) :: nc !< Particle number concentration in units 1/cm**3 9852 REAL(wp) :: temp_bin !< temporary array for calculating output variables 9853 9854 REAL(sp), DIMENSION(nxl:nxr,nys:nyn,nzb_do:nzt_do) :: local_pf !< local 9855 9856 REAL(wp), DIMENSION(:,:,:), POINTER :: to_be_resorted !< pointer 9857 9858 found = .TRUE. 9859 temp_bin = 0.0_wp 9860 9861 SELECT CASE ( TRIM( variable ) ) 9862 9863 CASE ( 'g_H2SO4', 'g_HNO3', 'g_NH3', 'g_OCNV', 'g_OCSV' ) 9864 IF ( av == 0 ) THEN 9865 IF ( TRIM( variable ) == 'g_H2SO4') found_index = 1 9866 IF ( TRIM( variable ) == 'g_HNO3') found_index = 2 9867 IF ( TRIM( variable ) == 'g_NH3') found_index = 3 9868 IF ( TRIM( variable ) == 'g_OCNV') found_index = 4 9869 IF ( TRIM( variable ) == 'g_OCSV') found_index = 5 9870 9871 DO i = nxl, nxr 9872 DO j = nys, nyn 9873 DO k = nzb_do, nzt_do 9874 local_pf(i,j,k) = MERGE( salsa_gas(found_index)%conc(k,j,i), & 9875 REAL( fill_value, KIND = wp ), & 9876 BTEST( wall_flags_0(k,j,i), 0 ) ) 9877 ENDDO 9878 ENDDO 9879 ENDDO 9880 ELSE 9881 IF ( TRIM( variable(3:) ) == 'H2SO4' ) to_be_resorted => g_h2so4_av 9882 IF ( TRIM( variable(3:) ) == 'HNO3' ) to_be_resorted => g_hno3_av 9883 IF ( TRIM( variable(3:) ) == 'NH3' ) to_be_resorted => g_nh3_av 9884 IF ( TRIM( variable(3:) ) == 'OCNV' ) to_be_resorted => g_ocnv_av 9885 IF ( TRIM( variable(3:) ) == 'OCSV' ) to_be_resorted => g_ocsv_av 9886 DO i = nxl, nxr 9887 DO j = nys, nyn 9888 DO k = nzb_do, nzt_do 9889 local_pf(i,j,k) = MERGE( to_be_resorted(k,j,i), REAL( fill_value, & 9890 KIND = wp ), BTEST( wall_flags_0(k,j,i), 0 ) ) 9891 ENDDO 9892 ENDDO 9893 ENDDO 9894 ENDIF 9895 9896 CASE ( 'LDSA' ) 9897 IF ( av == 0 ) THEN 9898 DO i = nxl, nxr 9899 DO j = nys, nyn 9900 DO k = nzb_do, nzt_do 9901 temp_bin = 0.0_wp 9902 DO ib = 1, nbins_aerosol 9903 ! 9904 !-- Diameter in micrometres 9905 mean_d = 1.0E+6_wp * ra_dry(k,j,i,ib) * 2.0_wp 9906 ! 9907 !-- Deposition factor: alveolar 9908 df = ( 0.01555_wp / mean_d ) * ( EXP( -0.416_wp * ( LOG( mean_d ) + & 9909 2.84_wp )**2 ) + 19.11_wp * EXP( -0.482_wp * ( LOG( mean_d ) - & 9910 1.362_wp )**2 ) ) 9911 ! 9912 !-- Number concentration in 1/cm3 9913 nc = 1.0E-6_wp * aerosol_number(ib)%conc(k,j,i) 9914 ! 9915 !-- Lung-deposited surface area LDSA (units mum2/cm3) 9916 temp_bin = temp_bin + pi * mean_d**2 * df * nc 9917 ENDDO 9918 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = wp ), & 9919 BTEST( wall_flags_0(k,j,i), 0 ) ) 9920 ENDDO 9921 ENDDO 9922 ENDDO 9923 ELSE 9924 DO i = nxl, nxr 9925 DO j = nys, nyn 9926 DO k = nzb_do, nzt_do 9927 local_pf(i,j,k) = MERGE( ldsa_av(k,j,i), REAL( fill_value, KIND = wp ), & 9928 BTEST( wall_flags_0(k,j,i), 0 ) ) 9929 ENDDO 9930 ENDDO 9931 ENDDO 9932 ENDIF 9933 9934 CASE ( 'N_bin1', 'N_bin2', 'N_bin3', 'N_bin4', 'N_bin5', 'N_bin6', 'N_bin7', 'N_bin8', & 9935 'N_bin9', 'N_bin10', 'N_bin11', 'N_bin12' ) 9936 IF ( TRIM( variable(6:) ) == '1' ) ib = 1 9937 IF ( TRIM( variable(6:) ) == '2' ) ib = 2 9938 IF ( TRIM( variable(6:) ) == '3' ) ib = 3 9939 IF ( TRIM( variable(6:) ) == '4' ) ib = 4 9940 IF ( TRIM( variable(6:) ) == '5' ) ib = 5 9941 IF ( TRIM( variable(6:) ) == '6' ) ib = 6 9942 IF ( TRIM( variable(6:) ) == '7' ) ib = 7 9943 IF ( TRIM( variable(6:) ) == '8' ) ib = 8 9944 IF ( TRIM( variable(6:) ) == '9' ) ib = 9 9945 IF ( TRIM( variable(6:) ) == '10' ) ib = 10 9946 IF ( TRIM( variable(6:) ) == '11' ) ib = 11 9947 IF ( TRIM( variable(6:) ) == '12' ) ib = 12 9948 9949 IF ( av == 0 ) THEN 9950 DO i = nxl, nxr 9951 DO j = nys, nyn 9952 DO k = nzb_do, nzt_do 9953 local_pf(i,j,k) = MERGE( aerosol_number(ib)%conc(k,j,i), REAL( fill_value, & 9954 KIND = wp ), BTEST( wall_flags_0(k,j,i), 0 ) ) 9955 ENDDO 9956 ENDDO 9957 ENDDO 9958 ELSE 9959 DO i = nxl, nxr 9960 DO j = nys, nyn 9961 DO k = nzb_do, nzt_do 9962 local_pf(i,j,k) = MERGE( nbins_av(k,j,i,ib), REAL( fill_value, KIND = wp ), & 9963 BTEST( wall_flags_0(k,j,i), 0 ) ) 9964 ENDDO 9965 ENDDO 9966 ENDDO 9967 ENDIF 9968 9969 CASE ( 'Ntot' ) 9970 IF ( av == 0 ) THEN 9971 DO i = nxl, nxr 9972 DO j = nys, nyn 9973 DO k = nzb_do, nzt_do 9974 temp_bin = 0.0_wp 9975 DO ib = 1, nbins_aerosol 9976 temp_bin = temp_bin + aerosol_number(ib)%conc(k,j,i) 9977 ENDDO 9978 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = wp ), & 9979 BTEST( wall_flags_0(k,j,i), 0 ) ) 9980 ENDDO 9981 ENDDO 9982 ENDDO 9983 ELSE 9984 DO i = nxl, nxr 9985 DO j = nys, nyn 9986 DO k = nzb_do, nzt_do 9987 local_pf(i,j,k) = MERGE( ntot_av(k,j,i), REAL( fill_value, KIND = wp ), & 9988 BTEST( wall_flags_0(k,j,i), 0 ) ) 9989 ENDDO 9990 ENDDO 9991 ENDDO 9992 ENDIF 9993 9994 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6', 'm_bin7', 'm_bin8', & 9995 'm_bin9', 'm_bin10' , 'm_bin11', 'm_bin12' ) 9996 IF ( TRIM( variable(6:) ) == '1' ) ib = 1 9997 IF ( TRIM( variable(6:) ) == '2' ) ib = 2 9998 IF ( TRIM( variable(6:) ) == '3' ) ib = 3 9999 IF ( TRIM( variable(6:) ) == '4' ) ib = 4 10000 IF ( TRIM( variable(6:) ) == '5' ) ib = 5 10001 IF ( TRIM( variable(6:) ) == '6' ) ib = 6 10002 IF ( TRIM( variable(6:) ) == '7' ) ib = 7 10003 IF ( TRIM( variable(6:) ) == '8' ) ib = 8 10004 IF ( TRIM( variable(6:) ) == '9' ) ib = 9 10005 IF ( TRIM( variable(6:) ) == '10' ) ib = 10 10006 IF ( TRIM( variable(6:) ) == '11' ) ib = 11 10007 IF ( TRIM( variable(6:) ) == '12' ) ib = 12 10008 10009 IF ( av == 0 ) THEN 10010 DO i = nxl, nxr 10011 DO j = nys, nyn 10012 DO k = nzb_do, nzt_do 10013 temp_bin = 0.0_wp 10014 DO ic = ib, ncomponents_mass * nbins_aerosol, nbins_aerosol 10015 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 10016 ENDDO 10017 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = wp ), & 10018 BTEST( wall_flags_0(k,j,i), 0 ) ) 10019 ENDDO 10020 ENDDO 10021 ENDDO 10022 ELSE 10023 DO i = nxl, nxr 10024 DO j = nys, nyn 10025 DO k = nzb_do, nzt_do 10026 local_pf(i,j,k) = MERGE( mbins_av(k,j,i,ib), REAL( fill_value, KIND = wp ), & 10027 BTEST( wall_flags_0(k,j,i), 0 ) ) 10028 ENDDO 10029 ENDDO 10030 ENDDO 10031 ENDIF 10032 10033 CASE ( 'PM2.5' ) 10034 IF ( av == 0 ) THEN 10035 DO i = nxl, nxr 10036 DO j = nys, nyn 10037 DO k = nzb_do, nzt_do 10038 temp_bin = 0.0_wp 10039 DO ib = 1, nbins_aerosol 10040 IF ( 2.0_wp * ra_dry(k,j,i,ib) <= 2.5E-6_wp ) THEN 10041 DO ic = ib, nbins_aerosol * ncc, nbins_aerosol 10042 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 10043 ENDDO 10044 ENDIF 10045 ENDDO 10046 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = wp ), & 9648 10047 BTEST( wall_flags_0(k,j,i), 0 ) ) 9649 10048 ENDDO … … 9654 10053 DO j = nys, nyn 9655 10054 DO k = nzb_do, nzt_do 9656 local_pf(i,j,k) = MERGE( LDSA_av(k,j,i), & 9657 REAL( fill_value, KIND = wp ), & 10055 local_pf(i,j,k) = MERGE( pm25_av(k,j,i), REAL( fill_value, KIND = wp ), & 9658 10056 BTEST( wall_flags_0(k,j,i), 0 ) ) 9659 10057 ENDDO … … 9661 10059 ENDDO 9662 10060 ENDIF 9663 9664 CASE ( 'N_bin1', 'N_bin2', 'N_bin3', 'N_bin4', 'N_bin5', 'N_bin6', & 9665 'N_bin7', 'N_bin8', 'N_bin9', 'N_bin10' , 'N_bin11', 'N_bin12' ) 9666 IF ( TRIM( variable(6:) ) == '1' ) b = 1 9667 IF ( TRIM( variable(6:) ) == '2' ) b = 2 9668 IF ( TRIM( variable(6:) ) == '3' ) b = 3 9669 IF ( TRIM( variable(6:) ) == '4' ) b = 4 9670 IF ( TRIM( variable(6:) ) == '5' ) b = 5 9671 IF ( TRIM( variable(6:) ) == '6' ) b = 6 9672 IF ( TRIM( variable(6:) ) == '7' ) b = 7 9673 IF ( TRIM( variable(6:) ) == '8' ) b = 8 9674 IF ( TRIM( variable(6:) ) == '9' ) b = 9 9675 IF ( TRIM( variable(6:) ) == '10' ) b = 10 9676 IF ( TRIM( variable(6:) ) == '11' ) b = 11 9677 IF ( TRIM( variable(6:) ) == '12' ) b = 12 9678 9679 IF ( av == 0 ) THEN 9680 DO i = nxl, nxr 9681 DO j = nys, nyn 9682 DO k = nzb_do, nzt_do 9683 local_pf(i,j,k) = MERGE( aerosol_number(b)%conc(k,j,i), & 9684 REAL( fill_value, KIND = wp ), & 9685 BTEST( wall_flags_0(k,j,i), 0 ) ) 9686 ENDDO 9687 ENDDO 9688 ENDDO 9689 ELSE 9690 DO i = nxl, nxr 9691 DO j = nys, nyn 9692 DO k = nzb_do, nzt_do 9693 local_pf(i,j,k) = MERGE( Nbins_av(k,j,i,b), & 9694 REAL( fill_value, KIND = wp ), & 9695 BTEST( wall_flags_0(k,j,i), 0 ) ) 9696 ENDDO 9697 ENDDO 9698 ENDDO 9699 ENDIF 9700 9701 CASE ( 'Ntot' ) 10061 10062 CASE ( 'PM10' ) 9702 10063 IF ( av == 0 ) THEN 9703 10064 DO i = nxl, nxr … … 9705 10066 DO k = nzb_do, nzt_do 9706 10067 temp_bin = 0.0_wp 9707 DO b = 1, nbins 9708 temp_bin = temp_bin + aerosol_number(b)%conc(k,j,i) 10068 DO ib = 1, nbins_aerosol 10069 IF ( 2.0_wp * ra_dry(k,j,i,ib) <= 10.0E-6_wp ) THEN 10070 DO ic = ib, nbins_aerosol * ncc, nbins_aerosol 10071 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 10072 ENDDO 10073 ENDIF 9709 10074 ENDDO 9710 local_pf(i,j,k) = MERGE( temp_bin, & 9711 REAL( fill_value, KIND = wp ), & 10075 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = wp ), & 9712 10076 BTEST( wall_flags_0(k,j,i), 0 ) ) 9713 10077 ENDDO … … 9718 10082 DO j = nys, nyn 9719 10083 DO k = nzb_do, nzt_do 9720 local_pf(i,j,k) = MERGE( Ntot_av(k,j,i), & 9721 REAL( fill_value, KIND = wp ), & 9722 BTEST( wall_flags_0(k,j,i), 0 ) ) 10084 local_pf(i,j,k) = MERGE( pm10_av(k,j,i), REAL( fill_value, KIND = wp ), & 10085 BTEST( wall_flags_0(k,j,i), 0 ) ) 9723 10086 ENDDO 9724 10087 ENDDO 9725 10088 ENDDO 9726 10089 ENDIF 9727 9728 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6', & 9729 'm_bin7', 'm_bin8', 'm_bin9', 'm_bin10' , 'm_bin11', 'm_bin12' ) 9730 IF ( TRIM( variable(6:) ) == '1' ) b = 1 9731 IF ( TRIM( variable(6:) ) == '2' ) b = 2 9732 IF ( TRIM( variable(6:) ) == '3' ) b = 3 9733 IF ( TRIM( variable(6:) ) == '4' ) b = 4 9734 IF ( TRIM( variable(6:) ) == '5' ) b = 5 9735 IF ( TRIM( variable(6:) ) == '6' ) b = 6 9736 IF ( TRIM( variable(6:) ) == '7' ) b = 7 9737 IF ( TRIM( variable(6:) ) == '8' ) b = 8 9738 IF ( TRIM( variable(6:) ) == '9' ) b = 9 9739 IF ( TRIM( variable(6:) ) == '10' ) b = 10 9740 IF ( TRIM( variable(6:) ) == '11' ) b = 11 9741 IF ( TRIM( variable(6:) ) == '12' ) b = 12 9742 9743 IF ( av == 0 ) THEN 9744 DO i = nxl, nxr 9745 DO j = nys, nyn 9746 DO k = nzb_do, nzt_do 9747 temp_bin = 0.0_wp 9748 DO c = b, ncc_tot * nbins, nbins 9749 temp_bin = temp_bin + aerosol_mass(c)%conc(k,j,i) 9750 ENDDO 9751 local_pf(i,j,k) = MERGE( temp_bin, & 9752 REAL( fill_value, KIND = wp ), & 9753 BTEST( wall_flags_0(k,j,i), 0 ) ) 9754 ENDDO 9755 ENDDO 9756 ENDDO 9757 ELSE 9758 DO i = nxl, nxr 9759 DO j = nys, nyn 9760 DO k = nzb_do, nzt_do 9761 local_pf(i,j,k) = MERGE( mbins_av(k,j,i,b), & 9762 REAL( fill_value, KIND = wp ), & 9763 BTEST( wall_flags_0(k,j,i), 0 ) ) 9764 ENDDO 9765 ENDDO 9766 ENDDO 9767 ENDIF 9768 9769 CASE ( 'PM2.5' ) 9770 IF ( av == 0 ) THEN 9771 DO i = nxl, nxr 9772 DO j = nys, nyn 9773 DO k = nzb_do, nzt_do 9774 temp_bin = 0.0_wp 9775 DO b = 1, nbins 9776 IF ( 2.0_wp * Ra_dry(k,j,i,b) <= 2.5E-6_wp ) THEN 9777 DO c = b, nbins * ncc, nbins 9778 temp_bin = temp_bin + aerosol_mass(c)%conc(k,j,i) 9779 ENDDO 9780 ENDIF 9781 ENDDO 9782 local_pf(i,j,k) = MERGE( temp_bin, & 9783 REAL( fill_value, KIND = wp ), & 9784 BTEST( wall_flags_0(k,j,i), 0 ) ) 9785 ENDDO 9786 ENDDO 9787 ENDDO 9788 ELSE 9789 DO i = nxl, nxr 9790 DO j = nys, nyn 9791 DO k = nzb_do, nzt_do 9792 local_pf(i,j,k) = MERGE( PM25_av(k,j,i), & 9793 REAL( fill_value, KIND = wp ), & 9794 BTEST( wall_flags_0(k,j,i), 0 ) ) 9795 ENDDO 9796 ENDDO 9797 ENDDO 9798 ENDIF 9799 9800 CASE ( 'PM10' ) 9801 IF ( av == 0 ) THEN 9802 DO i = nxl, nxr 9803 DO j = nys, nyn 9804 DO k = nzb_do, nzt_do 9805 temp_bin = 0.0_wp 9806 DO b = 1, nbins 9807 IF ( 2.0_wp * Ra_dry(k,j,i,b) <= 10.0E-6_wp ) THEN 9808 DO c = b, nbins * ncc, nbins 9809 temp_bin = temp_bin + aerosol_mass(c)%conc(k,j,i) 9810 ENDDO 9811 ENDIF 9812 ENDDO 9813 local_pf(i,j,k) = MERGE( temp_bin, & 9814 REAL( fill_value, KIND = wp ), & 9815 BTEST( wall_flags_0(k,j,i), 0 ) ) 9816 ENDDO 9817 ENDDO 9818 ENDDO 9819 ELSE 9820 DO i = nxl, nxr 9821 DO j = nys, nyn 9822 DO k = nzb_do, nzt_do 9823 local_pf(i,j,k) = MERGE( PM10_av(k,j,i), & 9824 REAL( fill_value, KIND = wp ), & 9825 BTEST( wall_flags_0(k,j,i), 0 ) ) 9826 ENDDO 9827 ENDDO 9828 ENDDO 9829 ENDIF 9830 10090 9831 10091 CASE ( 's_BC', 's_DU', 's_H2O', 's_NH', 's_NO', 's_OC', 's_SO4', 's_SS' ) 9832 10092 IF ( is_used( prtcl, TRIM( variable(3:) ) ) ) THEN 9833 icc= get_index( prtcl, TRIM( variable(3:) ) )10093 found_index = get_index( prtcl, TRIM( variable(3:) ) ) 9834 10094 IF ( av == 0 ) THEN 9835 10095 DO i = nxl, nxr … … 9837 10097 DO k = nzb_do, nzt_do 9838 10098 temp_bin = 0.0_wp 9839 DO c = ( icc-1 )*nbins+1, icc*nbins9840 temp_bin = temp_bin + aerosol_mass( c)%conc(k,j,i)10099 DO ic = ( found_index-1 ) * nbins_aerosol + 1, found_index * nbins_aerosol 10100 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 9841 10101 ENDDO 9842 local_pf(i,j,k) = MERGE( temp_bin, & 9843 REAL( fill_value, KIND = wp ), & 9844 BTEST( wall_flags_0(k,j,i), 0 ) ) 10102 local_pf(i,j,k) = MERGE( temp_bin, REAL( fill_value, KIND = wp ), & 10103 BTEST( wall_flags_0(k,j,i), 0 ) ) 9845 10104 ENDDO 9846 10105 ENDDO 9847 10106 ENDDO 9848 10107 ELSE 9849 IF ( TRIM( variable(3:) ) == 'BC' ) to_be_resorted => s_ BC_av9850 IF ( TRIM( variable(3:) ) == 'DU' ) to_be_resorted => s_ DU_av9851 IF ( TRIM( variable(3:) ) == 'NH' ) to_be_resorted => s_ NH_av9852 IF ( TRIM( variable(3:) ) == 'NO' ) to_be_resorted => s_ NO_av9853 IF ( TRIM( variable(3:) ) == 'OC' ) to_be_resorted => s_ OC_av9854 IF ( TRIM( variable(3:) ) == 'SO4' ) to_be_resorted => s_ SO4_av9855 IF ( TRIM( variable(3:) ) == 'SS' ) to_be_resorted => s_ SS_av10108 IF ( TRIM( variable(3:) ) == 'BC' ) to_be_resorted => s_bc_av 10109 IF ( TRIM( variable(3:) ) == 'DU' ) to_be_resorted => s_du_av 10110 IF ( TRIM( variable(3:) ) == 'NH' ) to_be_resorted => s_nh_av 10111 IF ( TRIM( variable(3:) ) == 'NO' ) to_be_resorted => s_no_av 10112 IF ( TRIM( variable(3:) ) == 'OC' ) to_be_resorted => s_oc_av 10113 IF ( TRIM( variable(3:) ) == 'SO4' ) to_be_resorted => s_so4_av 10114 IF ( TRIM( variable(3:) ) == 'SS' ) to_be_resorted => s_ss_av 9856 10115 DO i = nxl, nxr 9857 10116 DO j = nys, nyn 9858 DO k = nzb_do, nzt_do 9859 local_pf(i,j,k) = MERGE( to_be_resorted(k,j,i), & 9860 REAL( fill_value, KIND = wp ), & 9861 BTEST( wall_flags_0(k,j,i), 0 ) ) 10117 DO k = nzb_do, nzt_do 10118 local_pf(i,j,k) = MERGE( to_be_resorted(k,j,i), REAL( fill_value, & 10119 KIND = wp ), BTEST( wall_flags_0(k,j,i), 0 ) ) 9862 10120 ENDDO 9863 10121 ENDDO … … 9865 10123 ENDIF 9866 10124 ENDIF 10125 9867 10126 CASE DEFAULT 9868 10127 found = .FALSE. … … 9879 10138 !------------------------------------------------------------------------------! 9880 10139 SUBROUTINE salsa_data_output_mask( av, variable, found, local_pf ) 9881 9882 USE arrays_3d, &10140 10141 USE arrays_3d, & 9883 10142 ONLY: tend 9884 9885 USE control_parameters, &10143 10144 USE control_parameters, & 9886 10145 ONLY: mask_size_l, mask_surface, mid 9887 9888 USE surface_mod, &9889 ONLY: get_topography_top_index_ji 9890 10146 10147 USE surface_mod, & 10148 ONLY: get_topography_top_index_ji 10149 9891 10150 IMPLICIT NONE 9892 10151 9893 10152 CHARACTER(LEN=5) :: grid !< flag to distinquish between staggered grid 9894 CHARACTER(LEN=*) :: variable !< 10153 CHARACTER(LEN=*) :: variable !< 9895 10154 CHARACTER(LEN=7) :: vari !< trimmed format of variable 9896 10155 9897 INTEGER(iwp) :: av !< 9898 INTEGER(iwp) :: b !< loop index for aerosol size number bins 9899 INTEGER(iwp) :: c !< loop index for chemical components 10156 INTEGER(iwp) :: av !< 10157 INTEGER(iwp) :: found_index !< index of a chemical compound 10158 INTEGER(iwp) :: ib !< loop index for aerosol size number bins 10159 INTEGER(iwp) :: ic !< loop index for chemical components 9900 10160 INTEGER(iwp) :: i !< loop index in x-direction 9901 INTEGER(iwp) :: icc !< index of a chemical compound9902 10161 INTEGER(iwp) :: j !< loop index in y-direction 9903 10162 INTEGER(iwp) :: k !< loop index in z-direction 9904 10163 INTEGER(iwp) :: topo_top_ind !< k index of highest horizontal surface 9905 9906 LOGICAL :: found !< 10164 10165 LOGICAL :: found !< 9907 10166 LOGICAL :: resorted !< 9908 10167 9909 10168 REAL(wp) :: df !< For calculating LDSA: fraction of particles 9910 10169 !< depositing in the alveolar (or tracheobronchial) … … 9912 10171 REAL(wp) :: mean_d !< Particle diameter in micrometres 9913 10172 REAL(wp) :: nc !< Particle number concentration in units 1/cm**3 9914 REAL(wp) :: temp_bin !< temporary array for calculating output variables 9915 9916 REAL(wp), DIMENSION(mask_size_l(mid,1),mask_size_l(mid,2),mask_size_l(mid,3)) :: local_pf !< 9917 10173 REAL(wp) :: temp_bin !< temporary array for calculating output variables 10174 10175 REAL(wp), DIMENSION(mask_size_l(mid,1),mask_size_l(mid,2),mask_size_l(mid,3)) :: local_pf !< 10176 9918 10177 REAL(wp), DIMENSION(:,:,:), POINTER :: to_be_resorted !< pointer 9919 10178 … … 9924 10183 9925 10184 SELECT CASE ( TRIM( variable ) ) 9926 10185 9927 10186 CASE ( 'g_H2SO4', 'g_HNO3', 'g_NH3', 'g_OCNV', 'g_OCSV' ) 9928 10187 vari = TRIM( variable ) … … 9932 10191 IF ( vari == 'g_NH3') to_be_resorted => salsa_gas(3)%conc 9933 10192 IF ( vari == 'g_OCNV') to_be_resorted => salsa_gas(4)%conc 9934 IF ( vari == 'g_OCSV') to_be_resorted => salsa_gas(5)%conc 10193 IF ( vari == 'g_OCSV') to_be_resorted => salsa_gas(5)%conc 9935 10194 ELSE 9936 IF ( vari == 'g_H2SO4') to_be_resorted => g_ H2SO4_av9937 IF ( vari == 'g_HNO3') to_be_resorted => g_ HNO3_av9938 IF ( vari == 'g_NH3') to_be_resorted => g_ NH3_av9939 IF ( vari == 'g_OCNV') to_be_resorted => g_ OCNV_av9940 IF ( vari == 'g_OCSV') to_be_resorted => g_ OCSV_av10195 IF ( vari == 'g_H2SO4') to_be_resorted => g_h2so4_av 10196 IF ( vari == 'g_HNO3') to_be_resorted => g_hno3_av 10197 IF ( vari == 'g_NH3') to_be_resorted => g_nh3_av 10198 IF ( vari == 'g_OCNV') to_be_resorted => g_ocnv_av 10199 IF ( vari == 'g_OCSV') to_be_resorted => g_ocsv_av 9941 10200 ENDIF 9942 10201 9943 10202 CASE ( 'LDSA' ) 9944 10203 IF ( av == 0 ) THEN … … 9947 10206 DO k = nzb, nz_do3d 9948 10207 temp_bin = 0.0_wp 9949 DO b = 1, nbins9950 ! 10208 DO ib = 1, nbins_aerosol 10209 ! 9951 10210 !-- Diameter in micrometres 9952 mean_d = 1.0E+6_wp * Ra_dry(k,j,i,b) * 2.0_wp 9953 ! 9954 !-- Deposition factor: alveolar 9955 df = ( 0.01555_wp / mean_d ) * ( EXP( -0.416_wp * & 9956 ( LOG( mean_d ) + 2.84_wp )**2.0_wp ) + 19.11_wp & 9957 * EXP( -0.482_wp * ( LOG( mean_d ) - 1.362_wp & 9958 )**2.0_wp ) ) 9959 ! 10211 mean_d = 1.0E+6_wp * ra_dry(k,j,i,ib) * 2.0_wp 10212 ! 10213 !-- Deposition factor: alveolar 10214 df = ( 0.01555_wp / mean_d ) * ( EXP( -0.416_wp * ( LOG( mean_d ) + & 10215 2.84_wp )**2 ) + 19.11_wp * EXP( -0.482_wp * ( LOG( mean_d ) - & 10216 1.362_wp )**2 ) ) 10217 ! 9960 10218 !-- Number concentration in 1/cm3 9961 nc = 1.0E-6_wp * aerosol_number( b)%conc(k,j,i)9962 ! 10219 nc = 1.0E-6_wp * aerosol_number(ib)%conc(k,j,i) 10220 ! 9963 10221 !-- Lung-deposited surface area LDSA (units mum2/cm3) 9964 temp_bin = temp_bin + pi * mean_d**2 .0_wp * df * nc10222 temp_bin = temp_bin + pi * mean_d**2 * df * nc 9965 10223 ENDDO 9966 10224 tend(k,j,i) = temp_bin … … 9972 10230 DO j = 1, mask_size_l(mid,2) 9973 10231 DO k = 1, mask_size_l(mid,3) 9974 local_pf(i,j,k) = tend( mask_k(mid,k), mask_j(mid,j),& 9975 mask_i(mid,i) ) 10232 local_pf(i,j,k) = tend( mask_k(mid,k), mask_j(mid,j), mask_i(mid,i) ) 9976 10233 ENDDO 9977 10234 ENDDO … … 9980 10237 DO i = 1, mask_size_l(mid,1) 9981 10238 DO j = 1, mask_size_l(mid,2) 9982 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j),& 9983 mask_i(mid,i),& 10239 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j), mask_i(mid,i), & 9984 10240 grid ) 9985 10241 DO k = 1, mask_size_l(mid,3) 9986 local_pf(i,j,k) = tend( MIN( topo_top_ind+mask_k(mid,k),& 9987 nzt+1 ), & 10242 local_pf(i,j,k) = tend( MIN( topo_top_ind+mask_k(mid,k), nzt+1 ), & 9988 10243 mask_j(mid,j), mask_i(mid,i) ) 9989 10244 ENDDO … … 9993 10248 resorted = .TRUE. 9994 10249 ELSE 9995 to_be_resorted => LDSA_av10250 to_be_resorted => ldsa_av 9996 10251 ENDIF 9997 9998 CASE ( 'N_bin1', 'N_bin2', 'N_bin3', 'N_bin4', 'N_bin5', 'N_bin6', &9999 'N_bin 7', 'N_bin8', 'N_bin9', 'N_bin10' , 'N_bin11', 'N_bin12' )10000 IF ( TRIM( variable(6:) ) == '1' ) b = 110001 IF ( TRIM( variable(6:) ) == '2' ) b = 210002 IF ( TRIM( variable(6:) ) == '3' ) b = 310003 IF ( TRIM( variable(6:) ) == '4' ) b = 410004 IF ( TRIM( variable(6:) ) == '5' ) b = 510005 IF ( TRIM( variable(6:) ) == '6' ) b = 610006 IF ( TRIM( variable(6:) ) == '7' ) b = 710007 IF ( TRIM( variable(6:) ) == '8' ) b = 810008 IF ( TRIM( variable(6:) ) == '9' ) b = 910009 IF ( TRIM( variable(6:) ) == '10' ) b = 1010010 IF ( TRIM( variable(6:) ) == '11' ) b = 1110011 IF ( TRIM( variable(6:) ) == '12' ) b = 1210012 10252 10253 CASE ( 'N_bin1', 'N_bin2', 'N_bin3', 'N_bin4', 'N_bin5', 'N_bin6', 'N_bin7', 'N_bin8', & 10254 'N_bin9', 'N_bin10' , 'N_bin11', 'N_bin12' ) 10255 IF ( TRIM( variable(6:) ) == '1' ) ib = 1 10256 IF ( TRIM( variable(6:) ) == '2' ) ib = 2 10257 IF ( TRIM( variable(6:) ) == '3' ) ib = 3 10258 IF ( TRIM( variable(6:) ) == '4' ) ib = 4 10259 IF ( TRIM( variable(6:) ) == '5' ) ib = 5 10260 IF ( TRIM( variable(6:) ) == '6' ) ib = 6 10261 IF ( TRIM( variable(6:) ) == '7' ) ib = 7 10262 IF ( TRIM( variable(6:) ) == '8' ) ib = 8 10263 IF ( TRIM( variable(6:) ) == '9' ) ib = 9 10264 IF ( TRIM( variable(6:) ) == '10' ) ib = 10 10265 IF ( TRIM( variable(6:) ) == '11' ) ib = 11 10266 IF ( TRIM( variable(6:) ) == '12' ) ib = 12 10267 10013 10268 IF ( av == 0 ) THEN 10014 IF ( .NOT. mask_surface(mid) ) THEN 10269 IF ( .NOT. mask_surface(mid) ) THEN 10015 10270 DO i = 1, mask_size_l(mid,1) 10016 10271 DO j = 1, mask_size_l(mid,2) 10017 10272 DO k = 1, mask_size_l(mid,3) 10018 local_pf(i,j,k) = aerosol_number(b)%conc( mask_k(mid,k),& 10019 mask_j(mid,j),& 10020 mask_i(mid,i) ) 10273 local_pf(i,j,k) = aerosol_number(ib)%conc( mask_k(mid,k), mask_j(mid,j), & 10274 mask_i(mid,i) ) 10021 10275 ENDDO 10022 10276 ENDDO 10023 10277 ENDDO 10024 ELSE 10278 ELSE 10025 10279 DO i = 1, mask_size_l(mid,1) 10026 10280 DO j = 1, mask_size_l(mid,2) 10027 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j),& 10028 mask_i(mid,i),& 10281 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j), mask_i(mid,i), & 10029 10282 grid ) 10030 10283 DO k = 1, mask_size_l(mid,3) 10031 local_pf(i,j,k) = aerosol_number(b)%conc( & 10032 MIN( topo_top_ind+mask_k(mid,k), & 10033 nzt+1 ), & 10034 mask_j(mid,j), mask_i(mid,i) ) 10284 local_pf(i,j,k) = aerosol_number(ib)%conc(MIN( topo_top_ind+mask_k(mid,k),& 10285 nzt+1 ), & 10286 mask_j(mid,j), mask_i(mid,i) ) 10035 10287 ENDDO 10036 10288 ENDDO … … 10039 10291 resorted = .TRUE. 10040 10292 ELSE 10041 to_be_resorted => Nbins_av(:,:,:,b)10293 to_be_resorted => nbins_av(:,:,:,ib) 10042 10294 ENDIF 10043 10295 10044 10296 CASE ( 'Ntot' ) 10045 10297 IF ( av == 0 ) THEN … … 10048 10300 DO k = nzb, nz_do3d 10049 10301 temp_bin = 0.0_wp 10050 DO b = 1, nbins10051 temp_bin = temp_bin + aerosol_number( b)%conc(k,j,i)10302 DO ib = 1, nbins_aerosol 10303 temp_bin = temp_bin + aerosol_number(ib)%conc(k,j,i) 10052 10304 ENDDO 10053 10305 tend(k,j,i) = temp_bin … … 10059 10311 DO j = 1, mask_size_l(mid,2) 10060 10312 DO k = 1, mask_size_l(mid,3) 10061 local_pf(i,j,k) = tend( mask_k(mid,k), mask_j(mid,j),& 10062 mask_i(mid,i) ) 10313 local_pf(i,j,k) = tend( mask_k(mid,k), mask_j(mid,j), mask_i(mid,i) ) 10063 10314 ENDDO 10064 10315 ENDDO … … 10067 10318 DO i = 1, mask_size_l(mid,1) 10068 10319 DO j = 1, mask_size_l(mid,2) 10069 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j),& 10070 mask_i(mid,i),& 10320 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j), mask_i(mid,i), & 10071 10321 grid ) 10072 10322 DO k = 1, mask_size_l(mid,3) 10073 local_pf(i,j,k) = tend( MIN( topo_top_ind+mask_k(mid,k),& 10074 nzt+1 ), & 10323 local_pf(i,j,k) = tend( MIN( topo_top_ind+mask_k(mid,k), nzt+1 ), & 10075 10324 mask_j(mid,j), mask_i(mid,i) ) 10076 10325 ENDDO … … 10080 10329 resorted = .TRUE. 10081 10330 ELSE 10082 to_be_resorted => Ntot_av10331 to_be_resorted => ntot_av 10083 10332 ENDIF 10084 10085 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6',&10086 'm_bin 7', 'm_bin8', 'm_bin9', 'm_bin10', 'm_bin11', 'm_bin12' )10087 IF ( TRIM( variable(6:) ) == '1' ) b = 110088 IF ( TRIM( variable(6:) ) == '2' ) b = 210089 IF ( TRIM( variable(6:) ) == '3' ) b = 310090 IF ( TRIM( variable(6:) ) == '4' ) b = 410091 IF ( TRIM( variable(6:) ) == '5' ) b = 510092 IF ( TRIM( variable(6:) ) == '6' ) b = 610093 IF ( TRIM( variable(6:) ) == '7' ) b = 710094 IF ( TRIM( variable(6:) ) == '8' ) b = 810095 IF ( TRIM( variable(6:) ) == '9' ) b = 910096 IF ( TRIM( variable(6:) ) == '10' ) b = 1010097 IF ( TRIM( variable(6:) ) == '11' ) b = 1110098 IF ( TRIM( variable(6:) ) == '12' ) b = 1210099 10333 10334 CASE ( 'm_bin1', 'm_bin2', 'm_bin3', 'm_bin4', 'm_bin5', 'm_bin6', 'm_bin7', 'm_bin8', & 10335 'm_bin9', 'm_bin10', 'm_bin11', 'm_bin12' ) 10336 IF ( TRIM( variable(6:) ) == '1' ) ib = 1 10337 IF ( TRIM( variable(6:) ) == '2' ) ib = 2 10338 IF ( TRIM( variable(6:) ) == '3' ) ib = 3 10339 IF ( TRIM( variable(6:) ) == '4' ) ib = 4 10340 IF ( TRIM( variable(6:) ) == '5' ) ib = 5 10341 IF ( TRIM( variable(6:) ) == '6' ) ib = 6 10342 IF ( TRIM( variable(6:) ) == '7' ) ib = 7 10343 IF ( TRIM( variable(6:) ) == '8' ) ib = 8 10344 IF ( TRIM( variable(6:) ) == '9' ) ib = 9 10345 IF ( TRIM( variable(6:) ) == '10' ) ib = 10 10346 IF ( TRIM( variable(6:) ) == '11' ) ib = 11 10347 IF ( TRIM( variable(6:) ) == '12' ) ib = 12 10348 10100 10349 IF ( av == 0 ) THEN 10101 10350 DO i = nxl, nxr … … 10103 10352 DO k = nzb, nz_do3d 10104 10353 temp_bin = 0.0_wp 10105 DO c = b, ncc_tot*nbins, nbins10106 temp_bin = temp_bin + aerosol_mass( c)%conc(k,j,i)10354 DO ic = ib, ncomponents_mass * nbins_aerosol, nbins_aerosol 10355 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 10107 10356 ENDDO 10108 10357 tend(k,j,i) = temp_bin 10109 10358 ENDDO 10110 10359 ENDDO 10111 ENDDO 10112 IF ( .NOT. mask_surface(mid) ) THEN 10360 ENDDO 10361 IF ( .NOT. mask_surface(mid) ) THEN 10113 10362 DO i = 1, mask_size_l(mid,1) 10114 10363 DO j = 1, mask_size_l(mid,2) 10115 10364 DO k = 1, mask_size_l(mid,3) 10116 local_pf(i,j,k) = tend( mask_k(mid,k), mask_j(mid,j),& 10117 mask_i(mid,i) ) 10365 local_pf(i,j,k) = tend( mask_k(mid,k), mask_j(mid,j), mask_i(mid,i) ) 10118 10366 ENDDO 10119 10367 ENDDO … … 10122 10370 DO i = 1, mask_size_l(mid,1) 10123 10371 DO j = 1, mask_size_l(mid,2) 10124 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j),& 10125 mask_i(mid,i),& 10372 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j), mask_i(mid,i), & 10126 10373 grid ) 10127 10374 DO k = 1, mask_size_l(mid,3) 10128 local_pf(i,j,k) = tend( MIN( topo_top_ind+mask_k(mid,k),& 10129 nzt+1 ), & 10375 local_pf(i,j,k) = tend( MIN( topo_top_ind+mask_k(mid,k), nzt+1 ), & 10130 10376 mask_j(mid,j), mask_i(mid,i) ) 10131 10377 ENDDO … … 10135 10381 resorted = .TRUE. 10136 10382 ELSE 10137 to_be_resorted => mbins_av(:,:,:, b)10383 to_be_resorted => mbins_av(:,:,:,ib) 10138 10384 ENDIF 10139 10385 10140 10386 CASE ( 'PM2.5' ) 10141 10387 IF ( av == 0 ) THEN … … 10144 10390 DO k = nzb, nz_do3d 10145 10391 temp_bin = 0.0_wp 10146 DO b = 1, nbins10147 IF ( 2.0_wp * Ra_dry(k,j,i,b) <= 2.5E-6_wp ) THEN10148 DO c = b, nbins * ncc, nbins10149 temp_bin = temp_bin + aerosol_mass( c)%conc(k,j,i)10392 DO ib = 1, nbins_aerosol 10393 IF ( 2.0_wp * ra_dry(k,j,i,ib) <= 2.5E-6_wp ) THEN 10394 DO ic = ib, nbins_aerosol * ncc, nbins_aerosol 10395 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 10150 10396 ENDDO 10151 10397 ENDIF … … 10155 10401 ENDDO 10156 10402 ENDDO 10157 IF ( .NOT. mask_surface(mid) ) THEN 10403 IF ( .NOT. mask_surface(mid) ) THEN 10158 10404 DO i = 1, mask_size_l(mid,1) 10159 10405 DO j = 1, mask_size_l(mid,2) 10160 10406 DO k = 1, mask_size_l(mid,3) 10161 local_pf(i,j,k) = tend( mask_k(mid,k), mask_j(mid,j),& 10162 mask_i(mid,i) ) 10407 local_pf(i,j,k) = tend( mask_k(mid,k), mask_j(mid,j), mask_i(mid,i) ) 10163 10408 ENDDO 10164 10409 ENDDO … … 10167 10412 DO i = 1, mask_size_l(mid,1) 10168 10413 DO j = 1, mask_size_l(mid,2) 10169 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j),& 10170 mask_i(mid,i),& 10414 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j), mask_i(mid,i), & 10171 10415 grid ) 10172 10416 DO k = 1, mask_size_l(mid,3) 10173 local_pf(i,j,k) = tend( MIN( topo_top_ind+mask_k(mid,k),& 10174 nzt+1 ), & 10417 local_pf(i,j,k) = tend( MIN( topo_top_ind+mask_k(mid,k), nzt+1 ), & 10175 10418 mask_j(mid,j), mask_i(mid,i) ) 10176 10419 ENDDO … … 10180 10423 resorted = .TRUE. 10181 10424 ELSE 10182 to_be_resorted => PM25_av10425 to_be_resorted => pm25_av 10183 10426 ENDIF 10184 10427 10185 10428 CASE ( 'PM10' ) 10186 10429 IF ( av == 0 ) THEN … … 10189 10432 DO k = nzb, nz_do3d 10190 10433 temp_bin = 0.0_wp 10191 DO b = 1, nbins10192 IF ( 2.0_wp * Ra_dry(k,j,i,b) <= 10.0E-6_wp ) THEN10193 DO c = b, nbins * ncc, nbins10194 temp_bin = temp_bin + aerosol_mass( c)%conc(k,j,i)10434 DO ib = 1, nbins_aerosol 10435 IF ( 2.0_wp * ra_dry(k,j,i,ib) <= 10.0E-6_wp ) THEN 10436 DO ic = ib, nbins_aerosol * ncc, nbins_aerosol 10437 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 10195 10438 ENDDO 10196 10439 ENDIF … … 10200 10443 ENDDO 10201 10444 ENDDO 10202 IF ( .NOT. mask_surface(mid) ) THEN 10445 IF ( .NOT. mask_surface(mid) ) THEN 10203 10446 DO i = 1, mask_size_l(mid,1) 10204 10447 DO j = 1, mask_size_l(mid,2) 10205 10448 DO k = 1, mask_size_l(mid,3) 10206 local_pf(i,j,k) = tend( mask_k(mid,k), mask_j(mid,j),& 10207 mask_i(mid,i) ) 10449 local_pf(i,j,k) = tend( mask_k(mid,k), mask_j(mid,j), mask_i(mid,i) ) 10208 10450 ENDDO 10209 10451 ENDDO … … 10212 10454 DO i = 1, mask_size_l(mid,1) 10213 10455 DO j = 1, mask_size_l(mid,2) 10214 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j),& 10215 mask_i(mid,i),& 10456 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j), mask_i(mid,i), & 10216 10457 grid ) 10217 10458 DO k = 1, mask_size_l(mid,3) 10218 local_pf(i,j,k) = tend( MIN( topo_top_ind+mask_k(mid,k),& 10219 nzt+1 ), & 10459 local_pf(i,j,k) = tend( MIN( topo_top_ind+mask_k(mid,k), nzt+1 ), & 10220 10460 mask_j(mid,j), mask_i(mid,i) ) 10221 10461 ENDDO … … 10225 10465 resorted = .TRUE. 10226 10466 ELSE 10227 to_be_resorted => PM10_av10467 to_be_resorted => pm10_av 10228 10468 ENDIF 10229 10469 10230 10470 CASE ( 's_BC', 's_DU', 's_NH', 's_NO', 's_OC', 's_SO4', 's_SS' ) 10231 10471 IF ( av == 0 ) THEN 10232 10472 IF ( is_used( prtcl, TRIM( variable(3:) ) ) ) THEN 10233 icc= get_index( prtcl, TRIM( variable(3:) ) )10473 found_index = get_index( prtcl, TRIM( variable(3:) ) ) 10234 10474 DO i = nxl, nxr 10235 10475 DO j = nys, nyn 10236 10476 DO k = nzb, nz_do3d 10237 10477 temp_bin = 0.0_wp 10238 DO c = ( icc-1 )*nbins+1, icc*nbins10239 temp_bin = temp_bin + aerosol_mass( c)%conc(k,j,i)10478 DO ic = ( found_index-1 ) * nbins_aerosol + 1, found_index * nbins_aerosol 10479 temp_bin = temp_bin + aerosol_mass(ic)%conc(k,j,i) 10240 10480 ENDDO 10241 10481 tend(k,j,i) = temp_bin … … 10246 10486 tend = 0.0_wp 10247 10487 ENDIF 10248 IF ( .NOT. mask_surface(mid) ) THEN 10488 IF ( .NOT. mask_surface(mid) ) THEN 10249 10489 DO i = 1, mask_size_l(mid,1) 10250 10490 DO j = 1, mask_size_l(mid,2) 10251 10491 DO k = 1, mask_size_l(mid,3) 10252 local_pf(i,j,k) = tend( mask_k(mid,k), mask_j(mid,j), & 10253 mask_i(mid,i) ) 10492 local_pf(i,j,k) = tend( mask_k(mid,k), mask_j(mid,j), mask_i(mid,i) ) 10254 10493 ENDDO 10255 10494 ENDDO 10256 10495 ENDDO 10257 ELSE 10496 ELSE 10258 10497 DO i = 1, mask_size_l(mid,1) 10259 10498 DO j = 1, mask_size_l(mid,2) 10260 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j),& 10261 mask_i(mid,i),& 10499 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j), mask_i(mid,i), & 10262 10500 grid ) 10263 10501 DO k = 1, mask_size_l(mid,3) 10264 local_pf(i,j,k) = tend( MIN( topo_top_ind+mask_k(mid,k),& 10265 nzt+1 ),& 10502 local_pf(i,j,k) = tend( MIN( topo_top_ind+mask_k(mid,k), nzt+1 ), & 10266 10503 mask_j(mid,j), mask_i(mid,i) ) 10267 10504 ENDDO … … 10271 10508 resorted = .TRUE. 10272 10509 ELSE 10273 IF ( TRIM( variable(3:) ) == 'BC' ) to_be_resorted => s_ BC_av10274 IF ( TRIM( variable(3:) ) == 'DU' ) to_be_resorted => s_ DU_av10275 IF ( TRIM( variable(3:) ) == 'NH' ) to_be_resorted => s_ NH_av10276 IF ( TRIM( variable(3:) ) == 'NO' ) to_be_resorted => s_ NO_av10277 IF ( TRIM( variable(3:) ) == 'OC' ) to_be_resorted => s_ OC_av10278 IF ( TRIM( variable(3:) ) == 'SO4' ) to_be_resorted => s_ SO4_av10279 IF ( TRIM( variable(3:) ) == 'SS' ) to_be_resorted => s_ SS_av10510 IF ( TRIM( variable(3:) ) == 'BC' ) to_be_resorted => s_bc_av 10511 IF ( TRIM( variable(3:) ) == 'DU' ) to_be_resorted => s_du_av 10512 IF ( TRIM( variable(3:) ) == 'NH' ) to_be_resorted => s_nh_av 10513 IF ( TRIM( variable(3:) ) == 'NO' ) to_be_resorted => s_no_av 10514 IF ( TRIM( variable(3:) ) == 'OC' ) to_be_resorted => s_oc_av 10515 IF ( TRIM( variable(3:) ) == 'SO4' ) to_be_resorted => s_so4_av 10516 IF ( TRIM( variable(3:) ) == 'SS' ) to_be_resorted => s_ss_av 10280 10517 ENDIF 10281 10518 10282 10519 CASE DEFAULT 10283 10520 found = .FALSE. 10284 10521 10285 10522 END SELECT 10286 10287 10523 10288 10524 IF ( .NOT. resorted ) THEN 10289 10525 IF ( .NOT. mask_surface(mid) ) THEN 10290 10526 ! 10291 !-- Default masked output 10527 !-- Default masked output 10292 10528 DO i = 1, mask_size_l(mid,1) 10293 10529 DO j = 1, mask_size_l(mid,2) 10294 10530 DO k = 1, mask_size_l(mid,3) 10295 local_pf(i,j,k) = to_be_resorted( mask_k(mid,k), & 10296 mask_j(mid,j),mask_i(mid,i) ) 10531 local_pf(i,j,k) = to_be_resorted( mask_k(mid,k), mask_j(mid,j),mask_i(mid,i) ) 10297 10532 ENDDO 10298 10533 ENDDO … … 10300 10535 ELSE 10301 10536 ! 10302 !-- Terrain-following masked output 10537 !-- Terrain-following masked output 10303 10538 DO i = 1, mask_size_l(mid,1) 10304 10539 DO j = 1, mask_size_l(mid,2) 10305 10540 ! 10306 10541 !-- Get k index of highest horizontal surface 10307 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j), & 10308 mask_i(mid,i), grid ) 10542 topo_top_ind = get_topography_top_index_ji( mask_j(mid,j), mask_i(mid,i), grid ) 10309 10543 ! 10310 10544 !-- Save output array 10311 10545 DO k = 1, mask_size_l(mid,3) 10312 local_pf(i,j,k) = to_be_resorted( MIN( topo_top_ind+mask_k(mid,k),& 10313 nzt+1 ), & 10546 local_pf(i,j,k) = to_be_resorted( MIN( topo_top_ind+mask_k(mid,k), nzt+1 ), & 10314 10547 mask_j(mid,j), mask_i(mid,i) ) 10315 10548 ENDDO … … 10318 10551 ENDIF 10319 10552 ENDIF 10320 10553 10321 10554 END SUBROUTINE salsa_data_output_mask 10322 10323 10555 10324 10556 END MODULE salsa_mod -
palm/trunk/SOURCE/salsa_util_mod.f90
r3655 r3864 25 25 ! ----------------- 26 26 ! $Id$ 27 ! Formatting changes 28 ! 29 ! 3845 2019-04-01 13:41:55Z monakurppa 27 30 ! Initial revision 28 ! 29 ! 31 ! 32 ! 30 33 ! 31 34 ! Authors: … … 39 42 !------------------------------------------------------------------------------! 40 43 MODULE salsa_util_mod 41 44 45 USE control_parameters, & 46 ONLY: message_string 47 42 48 USE kinds 43 49 44 50 USE pegrid 45 51 46 52 IMPLICIT NONE 47 48 REAL(wp), DIMENSION(:,:), ALLOCATABLE :: sums_salsa_ws_l !< subdomain sum49 !< of vertical passive salsa flux w's'50 !< (5th-order advection scheme only)51 53 54 REAL(wp), DIMENSION(:,:), ALLOCATABLE :: sums_salsa_ws_l !< subdomain sum of vertical salsa 55 !< flux w's' (5th-order advection 56 !< scheme only) 57 ! 52 58 !-- Component index 53 59 TYPE component_index 54 INTEGER(iwp) :: ncomp !< Number of components55 INTEGER(iwp), ALLOCATABLE :: ind(:) !< Component index56 CHARACTER(len=3), ALLOCATABLE :: comp(:) !< Component name57 END TYPE component_index 58 60 INTEGER(iwp) :: ncomp !< Number of components 61 INTEGER(iwp), ALLOCATABLE :: ind(:) !< Component index 62 CHARACTER(len=3), ALLOCATABLE :: comp(:) !< Component name 63 END TYPE component_index 64 59 65 SAVE 60 66 61 67 INTERFACE component_index_constructor 62 68 MODULE PROCEDURE component_index_constructor 63 69 END INTERFACE component_index_constructor 64 70 65 71 INTERFACE get_index 66 72 MODULE PROCEDURE get_index 67 73 END INTERFACE get_index 68 69 INTERFACE get_n_comp 70 MODULE PROCEDURE get_n_comp 71 END INTERFACE get_n_comp 72 74 73 75 INTERFACE is_used 74 76 MODULE PROCEDURE is_used 75 77 END INTERFACE is_used 76 78 77 79 PRIVATE 78 PUBLIC component_index, component_index_constructor, get_index, get_n_comp,& 79 is_used, sums_salsa_ws_l 80 80 PUBLIC component_index, component_index_constructor, get_index, is_used, sums_salsa_ws_l 81 81 82 CONTAINS 82 83 !------------------------------------------------------------------------------! 83 84 !------------------------------------------------------------------------------! 84 85 ! Description: 85 86 ! ------------ 86 87 !> Creates index tables for different (aerosol) components 87 88 !------------------------------------------------------------------------------! 88 SUBROUTINE component_index_constructor( SELF, ncomp, nlist, listcomp )89 SUBROUTINE component_index_constructor( self, ncomp, nlist, listcomp ) 89 90 90 91 IMPLICIT NONE 91 92 TYPE(component_index), INTENT(inout) :: SELF !< Object containing the indices 93 !< of different aerosol components 94 INTEGER(iwp), INTENT(inout) :: ncomp !< Number of components 95 INTEGER(iwp), INTENT(in) :: nlist !< Maximum number of components 96 CHARACTER(len=3), INTENT(in) :: listcomp(nlist) !< List cof component 97 !< names 98 INTEGER(iwp) :: i, jj 99 92 93 INTEGER(iwp) :: i !< 94 INTEGER(iwp) :: jj !< 95 96 INTEGER(iwp), INTENT(in) :: nlist ! < Maximum number of components 97 98 INTEGER(iwp), INTENT(inout) :: ncomp !< Number of components 99 100 TYPE(component_index), INTENT(inout) :: self !< Object containing the indices of different 101 !< aerosol components 102 CHARACTER(len=3), INTENT(in) :: listcomp(nlist) !< List cof component names 103 100 104 ncomp = 0 101 102 DO 105 106 DO WHILE ( listcomp(ncomp+1) /= ' ' .AND. ncomp < nlist ) 103 107 ncomp = ncomp + 1 104 108 ENDDO 105 106 SELF%ncomp = ncomp107 ALLOCATE( SELF%ind(ncomp), SELF%comp(ncomp) )108 109 DO i = 1, ncomp110 SELF%ind(i) = i109 110 self%ncomp = ncomp 111 ALLOCATE( self%ind(ncomp), self%comp(ncomp) ) 112 113 DO i = 1, ncomp 114 self%ind(i) = i 111 115 ENDDO 112 116 113 117 jj = 1 114 DO i = 1, nlist118 DO i = 1, nlist 115 119 IF ( listcomp(i) == '') CYCLE 116 SELF%comp(jj) = listcomp(i)117 jj = jj +1120 self%comp(jj) = listcomp(i) 121 jj = jj + 1 118 122 ENDDO 119 123 120 124 END SUBROUTINE component_index_constructor 121 125 … … 125 129 !> Gives the index of a component in the component list 126 130 !------------------------------------------------------------------------------! 127 INTEGER FUNCTION get_index( SELF, incomp )131 INTEGER FUNCTION get_index( self, incomp ) 128 132 129 133 IMPLICIT NONE 130 131 TYPE(component_index), INTENT(in) :: SELF !< Object containing the 132 !< indices of different 133 !< aerosol components 134 134 135 CHARACTER(len=*), INTENT(in) :: incomp !< Component name 135 136 INTEGER(iwp) :: i 136 137 IF ( ANY(SELF%comp == incomp) ) THEN 137 138 TYPE(component_index), INTENT(in) :: self !< Object containing the indices of different 139 !< aerosol components 140 IF ( ANY( self%comp == incomp ) ) THEN 138 141 i = 1 139 DO WHILE ( ( SELF%comp(i) /= incomp) )140 i = i +1142 DO WHILE ( (self%comp(i) /= incomp) ) 143 i = i + 1 141 144 ENDDO 142 145 get_index = i 143 146 ELSEIF ( incomp == 'H2O' ) THEN 144 get_index = SELF%ncomp + 1147 get_index = self%ncomp + 1 145 148 ELSE 146 STOP 1 ! "INFO for Developer: please use the message routine to pass the output string" get_index: FAILED, no such component - 149 WRITE( message_string, * ) 'Incorrect component name given!' 150 CALL message( 'get_index', 'PA0591', 1, 2, 0, 6, 0 ) 147 151 ENDIF 148 152 149 153 RETURN 150 154 151 155 END FUNCTION get_index 152 153 !------------------------------------------------------------------------------!154 ! Description:155 ! ------------156 !> Get the number of (aerosol) components used157 !------------------------------------------------------------------------------!158 INTEGER FUNCTION get_n_comp( SELF )159 160 IMPLICIT NONE161 162 TYPE(component_index), INTENT(in) :: SELF !< Object containing the163 !< indices of different164 !< aerosol components165 get_n_comp = SELF%ncomp166 RETURN167 168 END FUNCTION169 156 170 157 !------------------------------------------------------------------------------! … … 173 160 !> Tells if the (aerosol) component is being used in the simulation 174 161 !------------------------------------------------------------------------------! 175 LOGICAL FUNCTION is_used( SELF, icomp )162 LOGICAL FUNCTION is_used( self, icomp ) 176 163 177 164 IMPLICIT NONE 178 179 TYPE(component_index), INTENT(in) :: SELF !< Object containing the 180 !< indices of different 181 !< aerosol components 165 182 166 CHARACTER(len=*), INTENT(in) :: icomp !< Component name 183 184 IF ( ANY(SELF%comp == icomp) ) THEN 167 168 TYPE(component_index), INTENT(in) :: self !< Object containing the indices of different 169 !< aerosol components 170 171 IF ( ANY(self%comp == icomp) ) THEN 185 172 is_used = .TRUE. 186 173 ELSE 187 174 is_used = .FALSE. 188 175 ENDIF 189 190 RETURN 191 176 192 177 END FUNCTION 193 178 -
palm/trunk/SOURCE/time_integration.f90
r3833 r3864 25 25 ! ----------------- 26 26 ! $Id$ 27 ! Modifications made for salsa: 28 ! - Call salsa_emission_update at each time step but do the checks within 29 ! salsa_emission_update (i.e. skip_time_do_salsa >= time_since_reference_point 30 ! and next_aero_emission_update <= time_since_reference_point ). 31 ! - Renamed nbins --> nbins_aerosol, ncc_tot --> ncomponents_mass and 32 ! ngast --> ngases_salsa and loop indices b, c and sg to ib, ic and ig 33 ! - Apply nesting for salsa variables 34 ! - Removed cpu_log calls speciffic for salsa. 35 ! 36 ! 3833 2019-03-28 15:04:04Z forkel 27 37 ! added USE chem_gasphase_mod, replaced nspec by nvar since fixed compounds are not integrated 28 38 ! … … 567 577 USE nesting_offl_mod, & 568 578 ONLY: nesting_offl_bc, nesting_offl_mass_conservation 569 579 570 580 USE netcdf_data_input_mod, & 571 581 ONLY: chem_emis, chem_emis_att, nest_offl, netcdf_data_input_offline_nesting … … 591 601 ONLY: dt_radiation, force_radiation_call, radiation, radiation_control, & 592 602 radiation_interaction, radiation_interactions, skip_time_do_radiation, time_radiation 593 603 594 604 USE salsa_mod, & 595 ONLY: aerosol_number, aerosol_mass, nbins, ncc_tot, ngast, salsa_boundary_conds, & 596 salsa_gas, salsa_gases_from_chem, skip_time_do_salsa 605 ONLY: aerosol_number, aerosol_mass, bc_am_t_val, bc_an_t_val, bc_gt_t_val, & 606 nbins_aerosol, ncomponents_mass, ngases_salsa, salsa_boundary_conds, & 607 salsa_emission_update, salsa_gas, salsa_gases_from_chem, skip_time_do_salsa 597 608 598 609 USE spectra_mod, & … … 629 640 vnest_boundary_conds_khkm, vnest_deallocate, vnest_init, vnest_init_fine, & 630 641 vnest_start_time 631 642 632 643 USE virtual_measurement_mod, & 633 644 ONLY: vm_data_output, vm_sampling, vm_time_start … … 667 678 668 679 CHARACTER (LEN=9) :: time_to_string !< 669 670 INTEGER(iwp) :: b !< index for aerosol size bins 671 INTEGER(iwp) :: c !< index for chemical compounds in aerosol size bins 672 INTEGER(iwp) :: g !< index for gaseous compounds 680 681 INTEGER(iwp) :: ib !< index for aerosol size bins 682 INTEGER(iwp) :: ic !< index for aerosol mass bins 683 INTEGER(iwp) :: icc !< additional index for aerosol mass bins 684 INTEGER(iwp) :: ig !< index for salsa gases 673 685 INTEGER(iwp) :: lsp 674 686 INTEGER(iwp) :: lsp_usr !< … … 856 868 ENDDO 857 869 ENDIF 870 IF ( salsa .AND. time_since_reference_point >= skip_time_do_salsa ) THEN 871 DO ib = 1, nbins_aerosol 872 bc_an_t_val = ( aerosol_number(ib)%init(nzt+1) - aerosol_number(ib)%init(nzt) ) / & 873 dzu(nzt+1) 874 DO ic = 1, ncomponents_mass 875 icc = ( ic - 1 ) * nbins_aerosol + ib 876 bc_am_t_val = ( aerosol_mass(icc)%init(nzt+1) - aerosol_mass(icc)%init(nzt) ) /& 877 dzu(nzt+1) 878 ENDDO 879 ENDDO 880 IF ( .NOT. salsa_gases_from_chem ) THEN 881 DO ig = 1, ngases_salsa 882 bc_gt_t_val = ( salsa_gas(ig)%init(nzt+1) - salsa_gas(ig)%init(nzt) ) / & 883 dzu(nzt+1) 884 ENDDO 885 ENDIF 886 ENDIF 858 887 ENDIF 859 888 ! … … 1028 1057 ENDIF 1029 1058 1030 IF ( salsa .AND. time_since_reference_point >= skip_time_do_salsa )& 1031 THEN 1032 CALL cpu_log( log_point_s(91), 'salsa exch-horiz ', 'start' ) 1033 DO b = 1, nbins 1034 CALL exchange_horiz( aerosol_number(b)%conc_p, nbgp ) 1035 CALL cpu_log( log_point_s(93), 'salsa decycle', 'start' ) 1036 CALL salsa_boundary_conds( aerosol_number(b)%conc_p, aerosol_number(b)%init ) 1037 CALL cpu_log( log_point_s(93), 'salsa decycle', 'stop' ) 1038 DO c = 1, ncc_tot 1039 CALL exchange_horiz( aerosol_mass((c-1)*nbins+b)%conc_p, nbgp ) 1040 CALL cpu_log( log_point_s(93), 'salsa decycle', 'start' ) 1041 CALL salsa_boundary_conds( aerosol_mass((c-1)*nbins+b)%conc_p, & 1042 aerosol_mass((c-1)*nbins+b)%init ) 1043 CALL cpu_log( log_point_s(93), 'salsa decycle', 'stop' ) 1059 IF ( salsa .AND. time_since_reference_point >= skip_time_do_salsa ) THEN 1060 ! 1061 !-- Exchange ghost points and decycle boundary concentrations if needed 1062 DO ib = 1, nbins_aerosol 1063 CALL exchange_horiz( aerosol_number(ib)%conc_p, nbgp ) 1064 CALL salsa_boundary_conds( aerosol_number(ib)%conc_p, aerosol_number(ib)%init ) 1065 DO ic = 1, ncomponents_mass 1066 icc = ( ic - 1 ) * nbins_aerosol + ib 1067 CALL exchange_horiz( aerosol_mass(icc)%conc_p, nbgp ) 1068 CALL salsa_boundary_conds( aerosol_mass(icc)%conc_p, aerosol_mass(icc)%init ) 1044 1069 ENDDO 1045 1070 ENDDO 1046 1071 IF ( .NOT. salsa_gases_from_chem ) THEN 1047 DO g = 1, ngast 1048 CALL exchange_horiz( salsa_gas(g)%conc_p, nbgp ) 1049 CALL cpu_log( log_point_s(93), 'salsa decycle', 'start' ) 1050 CALL salsa_boundary_conds( salsa_gas(g)%conc_p, salsa_gas(g)%init ) 1051 CALL cpu_log( log_point_s(93), 'salsa decycle', 'stop' ) 1052 ENDDO 1072 DO ig = 1, ngases_salsa 1073 CALL exchange_horiz( salsa_gas(ig)%conc_p, nbgp ) 1074 CALL salsa_boundary_conds( salsa_gas(ig)%conc_p, salsa_gas(ig)%init ) 1075 ENDDO 1053 1076 ENDIF 1054 CALL cpu_log( log_point_s(91), 'salsa exch-horiz ', 'stop' ) 1055 ENDIF 1077 ENDIF 1056 1078 CALL cpu_log( log_point(26), 'exchange-horiz-progn', 'stop' ) 1057 1079 … … 1108 1130 1109 1131 IF ( passive_scalar ) CALL exchange_horiz( s, nbgp ) 1110 1132 1111 1133 IF ( .NOT. constant_diffusion ) CALL exchange_horiz( e, nbgp ) 1112 1134 … … 1120 1142 ENDDO 1121 1143 ENDIF 1144 1145 IF ( salsa .AND. time_since_reference_point >= skip_time_do_salsa ) THEN 1146 DO ib = 1, nbins_aerosol 1147 CALL exchange_horiz( aerosol_number(ib)%conc, nbgp ) 1148 CALL salsa_boundary_conds( aerosol_number(ib)%conc, aerosol_number(ib)%init ) 1149 DO ic = 1, ncomponents_mass 1150 icc = ( ic - 1 ) * nbins_aerosol + ib 1151 CALL exchange_horiz( aerosol_mass(icc)%conc, nbgp ) 1152 CALL salsa_boundary_conds( aerosol_mass(icc)%conc, aerosol_mass(icc)%init ) 1153 ENDDO 1154 ENDDO 1155 IF ( .NOT. salsa_gases_from_chem ) THEN 1156 DO ig = 1, ngases_salsa 1157 CALL exchange_horiz( salsa_gas(ig)%conc, nbgp ) 1158 CALL salsa_boundary_conds( salsa_gas(ig)%conc, salsa_gas(ig)%init ) 1159 ENDDO 1160 ENDIF 1161 ENDIF 1162 CALL cpu_log( log_point(26), 'exchange-horiz-progn', 'stop' ) 1122 1163 1123 1164 ENDIF … … 1407 1448 ENDIF 1408 1449 ENDIF 1409 1450 ! 1451 !-- If required, consider aerosol emissions for the salsa model 1452 IF ( salsa ) THEN 1453 ! 1454 !-- Call emission routine to update emissions if needed 1455 CALL salsa_emission_update 1456 1457 ENDIF 1410 1458 ! 1411 1459 !-- If required, calculate indoor temperature, waste heat, heat flux
Note: See TracChangeset
for help on using the changeset viewer.