source: palm/trunk/SOURCE/lpm_advec.f90 @ 1359

Last change on this file since 1359 was 1359, checked in by hoffmann, 10 years ago

new Lagrangian particle structure integrated

  • Property svn:keywords set to Id
File size: 61.0 KB
Line 
1 SUBROUTINE lpm_advec (ip,jp,kp)
2
3!--------------------------------------------------------------------------------!
4! This file is part of PALM.
5!
6! PALM is free software: you can redistribute it and/or modify it under the terms
7! of the GNU General Public License as published by the Free Software Foundation,
8! either version 3 of the License, or (at your option) any later version.
9!
10! PALM is distributed in the hope that it will be useful, but WITHOUT ANY
11! WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
12! A PARTICULAR PURPOSE.  See the GNU General Public License for more details.
13!
14! You should have received a copy of the GNU General Public License along with
15! PALM. If not, see <http://www.gnu.org/licenses/>.
16!
17! Copyright 1997-2014 Leibniz Universitaet Hannover
18!--------------------------------------------------------------------------------!
19!
20! Current revisions:
21! ------------------
22! New particle structure integrated.
23! Kind definition added to all floating point numbers.
24!
25! Former revisions:
26! -----------------
27! $Id: lpm_advec.f90 1359 2014-04-11 17:15:14Z hoffmann $
28!
29! 1322 2014-03-20 16:38:49Z raasch
30! REAL constants defined as wp_kind
31!
32! 1320 2014-03-20 08:40:49Z raasch
33! ONLY-attribute added to USE-statements,
34! kind-parameters added to all INTEGER and REAL declaration statements,
35! kinds are defined in new module kinds,
36! revision history before 2012 removed,
37! comment fields (!:) to be used for variable explanations added to
38! all variable declaration statements
39!
40! 1314 2014-03-14 18:25:17Z suehring
41! Vertical logarithmic interpolation of horizontal particle speed for particles
42! between roughness height and first vertical grid level.
43!
44! 1036 2012-10-22 13:43:42Z raasch
45! code put under GPL (PALM 3.9)
46!
47! 849 2012-03-15 10:35:09Z raasch
48! initial revision (former part of advec_particles)
49!
50!
51! Description:
52! ------------
53! Calculation of new particle positions due to advection using a simple Euler
54! scheme. Particles may feel inertia effects. SGS transport can be included
55! using the stochastic model of Weil et al. (2004, JAS, 61, 2877-2887).
56!------------------------------------------------------------------------------!
57
58    USE arrays_3d,                                                             &
59        ONLY:  de_dx, de_dy, de_dz, diss, e, u, us, usws, v, vsws, w, z0, zu,  &
60               zw
61
62    USE cpulog
63
64    USE interfaces
65
66    USE pegrid
67
68    USE control_parameters,                                                    &
69        ONLY:  atmos_ocean_sign, cloud_droplets, dt_3d, dt_3d_reached_l, dz,   &
70               g, kappa, molecular_viscosity, prandtl_layer, topography,       &
71               u_gtrans, v_gtrans, simulated_time
72
73    USE grid_variables,                                                        &
74        ONLY:  ddx, dx, ddy, dy
75       
76    USE indices,                                                               &
77        ONLY:  nzb, nzb_s_inner, nzt
78       
79    USE kinds
80   
81    USE particle_attributes,                                                   &
82        ONLY:  block_offset, c_0, density_ratio, dt_min_part, grid_particles,  &
83               iran_part, log_z_z0, number_of_particles, number_of_sublayers,  &
84               particles, particle_groups, offset_ocean_nzt,                   &
85               offset_ocean_nzt_m1, sgs_wfu_part, sgs_wfv_part, sgs_wfw_part,  &
86               use_sgs_for_particles, vertical_particle_advection, z0_av_global
87       
88    USE statistics,                                                            &
89        ONLY:  hom
90
91    IMPLICIT NONE
92
93    INTEGER(iwp) ::  agp                         !:
94    INTEGER(iwp) ::  gp_outside_of_building(1:8) !:
95    INTEGER(iwp) ::  i                           !:
96    INTEGER(iwp) ::  ip                          !:
97    INTEGER(iwp) ::  j                           !:
98    INTEGER(iwp) ::  jp                          !:
99    INTEGER(iwp) ::  k                           !:
100    INTEGER(iwp) ::  kp                          !:
101    INTEGER(iwp) ::  kw                          !:
102    INTEGER(iwp) ::  n                           !:
103    INTEGER(iwp) ::  nb                          !:
104    INTEGER(iwp) ::  num_gp                      !:
105
106    INTEGER(iwp), DIMENSION(0:7) ::  start_index !:
107    INTEGER(iwp), DIMENSION(0:7) ::  end_index   !:
108
109    REAL(wp) ::  aa                 !:
110    REAL(wp) ::  bb                 !:
111    REAL(wp) ::  cc                 !:
112    REAL(wp) ::  d_sum              !:
113    REAL(wp) ::  d_z_p_z0           !:
114    REAL(wp) ::  dd                 !:
115    REAL(wp) ::  de_dx_int_l        !:
116    REAL(wp) ::  de_dx_int_u        !:
117    REAL(wp) ::  de_dy_int_l        !:
118    REAL(wp) ::  de_dy_int_u        !:
119    REAL(wp) ::  de_dt              !:
120    REAL(wp) ::  de_dt_min          !:
121    REAL(wp) ::  de_dz_int_l        !:
122    REAL(wp) ::  de_dz_int_u        !:
123    REAL(wp) ::  diss_int_l         !:
124    REAL(wp) ::  diss_int_u         !:
125    REAL(wp) ::  dt_gap             !:
126    REAL(wp) ::  dt_particle_m      !:
127    REAL(wp) ::  e_int_l            !:
128    REAL(wp) ::  e_int_u            !:
129    REAL(wp) ::  e_mean_int         !:
130    REAL(wp) ::  exp_arg            !:
131    REAL(wp) ::  exp_term           !:
132    REAL(wp) ::  gg                 !:
133    REAL(wp) ::  height_int         !:
134    REAL(wp) ::  height_p           !:
135    REAL(wp) ::  lagr_timescale     !:
136    REAL(wp) ::  location(1:30,1:3) !:
137    REAL(wp) ::  random_gauss       !:
138    REAL(wp) ::  u_int_l            !:
139    REAL(wp) ::  u_int_u            !:
140    REAL(wp) ::  us_int             !:
141    REAL(wp) ::  v_int_l            !:
142    REAL(wp) ::  v_int_u            !:
143    REAL(wp) ::  vv_int             !:
144    REAL(wp) ::  w_int_l            !:
145    REAL(wp) ::  w_int_u            !:
146    REAL(wp) ::  x                  !:
147    REAL(wp) ::  y                  !:
148    REAL(wp) ::  z_p                !:   
149
150    REAL(wp), DIMENSION(1:30) ::  d_gp_pl !:
151    REAL(wp), DIMENSION(1:30) ::  de_dxi  !:
152    REAL(wp), DIMENSION(1:30) ::  de_dyi  !:
153    REAL(wp), DIMENSION(1:30) ::  de_dzi  !:
154    REAL(wp), DIMENSION(1:30) ::  dissi   !:
155    REAL(wp), DIMENSION(1:30) ::  ei      !:
156
157    REAL(wp), DIMENSION(number_of_particles) ::  dens_ratio   !:
158    REAL(wp), DIMENSION(number_of_particles) ::  de_dx_int    !:
159    REAL(wp), DIMENSION(number_of_particles) ::  de_dy_int    !:
160    REAL(wp), DIMENSION(number_of_particles) ::  de_dz_int    !:
161    REAL(wp), DIMENSION(number_of_particles) ::  diss_int     !:
162    REAL(wp), DIMENSION(number_of_particles) ::  dt_particle  !:
163    REAL(wp), DIMENSION(number_of_particles) ::  e_int        !:
164    REAL(wp), DIMENSION(number_of_particles) ::  fs_int       !:
165    REAL(wp), DIMENSION(number_of_particles) ::  log_z_z0_int !:
166    REAL(wp), DIMENSION(number_of_particles) ::  u_int        !:
167    REAL(wp), DIMENSION(number_of_particles) ::  v_int        !:
168    REAL(wp), DIMENSION(number_of_particles) ::  w_int        !:
169    REAL(wp), DIMENSION(number_of_particles) ::  xv           !:
170    REAL(wp), DIMENSION(number_of_particles) ::  yv           !:
171    REAL(wp), DIMENSION(number_of_particles) ::  zv           !:
172
173    REAL(wp), DIMENSION(number_of_particles, 3) ::  rg !:
174
175    CALL cpu_log( log_point_s(44), 'lpm_advec', 'continue' )
176
177!
178!-- Determine height of Prandtl layer and distance between Prandtl-layer
179!-- height and horizontal mean roughness height, which are required for
180!-- vertical logarithmic interpolation of horizontal particle speeds
181!-- (for particles below first vertical grid level).
182    z_p      = zu(nzb+1) - zw(nzb)
183    d_z_p_z0 = 1.0_wp / ( z_p - z0_av_global )
184
185    start_index = grid_particles(kp,jp,ip)%start_index
186    end_index   = grid_particles(kp,jp,ip)%end_index
187
188    xv = particles(1:number_of_particles)%x
189    yv = particles(1:number_of_particles)%y
190    zv = particles(1:number_of_particles)%z
191
192    DO  nb = 0, 7
193
194       i = ip
195       j = jp + block_offset(nb)%j_off
196       k = kp + block_offset(nb)%k_off
197
198!
199!--    Interpolate u velocity-component
200       DO  n = start_index(nb), end_index(nb)
201!
202!--       Interpolation of the u velocity component onto particle position. 
203!--       Particles are interpolation bi-linearly in the horizontal and a
204!--       linearly in the vertical. An exception is made for particles below
205!--       the first vertical grid level in case of a prandtl layer. In this
206!--       case the horizontal particle velocity components are determined using
207!--       Monin-Obukhov relations (if branch).
208!--       First, check if particle is located below first vertical grid level
209!--       (Prandtl-layer height)
210          IF ( prandtl_layer  .AND.  particles(n)%z < z_p )  THEN
211!
212!--          Resolved-scale horizontal particle velocity is zero below z0.
213             IF ( particles(n)%z < z0_av_global )  THEN
214                u_int(n) = 0.0_wp
215             ELSE
216!
217!--             Determine the sublayer. Further used as index.
218                height_p     = ( particles(n)%z - z0_av_global )            &
219                                     * REAL( number_of_sublayers, KIND=wp ) &
220                                     * d_z_p_z0 
221!
222!--             Calculate LOG(z/z0) for exact particle height. Therefore,   
223!--             interpolate linearly between precalculated logarithm.
224                log_z_z0_int(n) = log_z_z0(INT(height_p))                      &
225                                 + ( height_p - INT(height_p) )                &
226                                 * ( log_z_z0(INT(height_p)+1)                 &
227                                      - log_z_z0(INT(height_p))                &
228                                   ) 
229!
230!--             Neutral solution is applied for all situations, e.g. also for
231!--             unstable and stable situations. Even though this is not exact
232!--             this saves a lot of CPU time since several calls of intrinsic
233!--             FORTRAN procedures (LOG, ATAN) are avoided, This is justified
234!--             as sensitivity studies revealed no significant effect of
235!--             using the neutral solution also for un/stable situations.
236!--             Calculated left and bottom index on u grid.
237                us_int = 0.5_wp * ( us(j,i) + us(j,i-1) ) 
238
239                u_int  = -usws(j,i) / ( us_int * kappa + 1E-10_wp )           & 
240                         * log_z_z0_int(n)
241
242             ENDIF
243!
244!--       Particle above the first grid level. Bi-linear interpolation in the
245!--       horizontal and linear interpolation in the vertical direction.
246          ELSE
247
248             x  = xv(n) + ( 0.5_wp - i ) * dx
249             y  = yv(n) - j * dy
250             aa = x**2          + y**2
251             bb = ( dx - x )**2 + y**2
252             cc = x**2          + ( dy - y )**2
253             dd = ( dx - x )**2 + ( dy - y )**2
254             gg = aa + bb + cc + dd
255
256             u_int_l = ( ( gg - aa ) * u(k,j,i)   + ( gg - bb ) * u(k,j,i+1)   &
257                         + ( gg - cc ) * u(k,j+1,i) + ( gg - dd ) *            &
258                         u(k,j+1,i+1) ) / ( 3.0_wp * gg ) - u_gtrans
259
260             IF ( k == nzt )  THEN
261                u_int(n) = u_int_l
262             ELSE
263                u_int_u = ( ( gg-aa ) * u(k+1,j,i) + ( gg-bb ) * u(k+1,j,i+1)  &
264                            + ( gg-cc ) * u(k+1,j+1,i) + ( gg-dd ) *           &
265                            u(k+1,j+1,i+1) ) / ( 3.0_wp * gg ) - u_gtrans
266                u_int(n) = u_int_l + ( zv(n) - zu(k) ) / dz *                  &
267                           ( u_int_u - u_int_l )
268             ENDIF
269          ENDIF
270
271       ENDDO
272
273       i = ip + block_offset(nb)%i_off
274       j = jp
275       k = kp + block_offset(nb)%k_off
276!
277!--    Same procedure for interpolation of the v velocity-component
278       DO  n = start_index(nb), end_index(nb)
279          IF ( prandtl_layer  .AND.  particles(n)%z < z_p )  THEN
280
281             IF ( particles(n)%z < z0_av_global )  THEN
282!
283!--             Resolved-scale horizontal particle velocity is zero below z0.
284                v_int(n) = 0.0_wp
285             ELSE       
286!
287!--             Neutral solution is applied for all situations, e.g. also for
288!--             unstable and stable situations. Even though this is not exact
289!--             this saves a lot of CPU time since several calls of intrinsic
290!--             FORTRAN procedures (LOG, ATAN) are avoided, This is justified
291!--             as sensitivity studies revealed no significant effect of
292!--             using the neutral solution also for un/stable situations.
293!--             Calculated left and bottom index on v grid.
294                us_int = 0.5_wp * ( us(j,i) + us(j-1,i) )   
295
296                v_int  = -vsws(j,i) / ( us_int * kappa + 1E-10_wp )             &
297                         * log_z_z0_int(n) 
298             ENDIF
299          ELSE
300             x  = xv(n) - i * dx
301             y  = yv(n) + ( 0.5_wp - j ) * dy
302             aa = x**2          + y**2
303             bb = ( dx - x )**2 + y**2
304             cc = x**2          + ( dy - y )**2
305             dd = ( dx - x )**2 + ( dy - y )**2
306             gg = aa + bb + cc + dd
307
308             v_int_l = ( ( gg - aa ) * v(k,j,i)   + ( gg - bb ) * v(k,j,i+1)   &
309                       + ( gg - cc ) * v(k,j+1,i) + ( gg - dd ) * v(k,j+1,i+1) &
310                       ) / ( 3.0_wp * gg ) - v_gtrans
311
312             IF ( k == nzt )  THEN
313                v_int(n) = v_int_l
314             ELSE
315                v_int_u = ( ( gg-aa ) * v(k+1,j,i)   + ( gg-bb ) * v(k+1,j,i+1)   &
316                          + ( gg-cc ) * v(k+1,j+1,i) + ( gg-dd ) * v(k+1,j+1,i+1) &
317                          ) / ( 3.0_wp * gg ) - v_gtrans
318                v_int(n) = v_int_l + ( zv(n) - zu(k) ) / dz * &
319                                  ( v_int_u - v_int_l )
320             ENDIF
321          ENDIF
322
323       ENDDO
324
325       i = ip + block_offset(nb)%i_off
326       j = jp + block_offset(nb)%j_off
327       k = kp-1
328!
329!--    Same procedure for interpolation of the w velocity-component
330       DO  n = start_index(nb), end_index(nb)
331
332          IF ( vertical_particle_advection(particles(n)%group) )  THEN
333
334             x  = xv(n) - i * dx
335             y  = yv(n) - j * dy
336             aa = x**2          + y**2
337             bb = ( dx - x )**2 + y**2
338             cc = x**2          + ( dy - y )**2
339             dd = ( dx - x )**2 + ( dy - y )**2
340             gg = aa + bb + cc + dd
341
342             w_int_l = ( ( gg - aa ) * w(k,j,i)   + ( gg - bb ) * w(k,j,i+1)   &
343                       + ( gg - cc ) * w(k,j+1,i) + ( gg - dd ) * w(k,j+1,i+1) &
344                       ) / ( 3.0_wp * gg )
345
346             IF ( k == nzt )  THEN
347                w_int(n) = w_int_l
348             ELSE
349                w_int_u = ( ( gg-aa ) * w(k+1,j,i)   + &
350                            ( gg-bb ) * w(k+1,j,i+1) + &
351                            ( gg-cc ) * w(k+1,j+1,i) + &
352                            ( gg-dd ) * w(k+1,j+1,i+1) &
353                          ) / ( 3.0_wp * gg )
354                w_int(n) = w_int_l + ( zv(n) - zw(k) ) / dz * &
355                           ( w_int_u - w_int_l )
356             ENDIF
357
358          ELSE
359
360             w_int(n) = 0.0_wp
361
362          ENDIF
363
364       ENDDO
365
366    ENDDO
367
368!-- Interpolate and calculate quantities needed for calculating the SGS
369!-- velocities
370    IF ( use_sgs_for_particles )  THEN
371
372       IF ( topography == 'flat' )  THEN
373
374          DO  nb = 0,7
375
376             i = ip + block_offset(nb)%i_off
377             j = jp + block_offset(nb)%j_off
378             k = kp + block_offset(nb)%k_off
379
380             DO  n = start_index(nb), end_index(nb)
381!
382!--             Interpolate TKE
383                x  = xv(n) - i * dx
384                y  = yv(n) - j * dy
385                aa = x**2          + y**2
386                bb = ( dx - x )**2 + y**2
387                cc = x**2          + ( dy - y )**2
388                dd = ( dx - x )**2 + ( dy - y )**2
389                gg = aa + bb + cc + dd
390
391                e_int_l = ( ( gg-aa ) * e(k,j,i)   + ( gg-bb ) * e(k,j,i+1)   &
392                          + ( gg-cc ) * e(k,j+1,i) + ( gg-dd ) * e(k,j+1,i+1) &
393                          ) / ( 3.0_wp * gg )
394
395                IF ( k+1 == nzt+1 )  THEN
396                   e_int(n) = e_int_l
397                ELSE
398                   e_int_u = ( ( gg - aa ) * e(k+1,j,i)   + &
399                               ( gg - bb ) * e(k+1,j,i+1) + &
400                               ( gg - cc ) * e(k+1,j+1,i) + &
401                               ( gg - dd ) * e(k+1,j+1,i+1) &
402                            ) / ( 3.0_wp * gg )
403                   e_int(n) = e_int_l + ( zv(n) - zu(k) ) / dz * &
404                                     ( e_int_u - e_int_l )
405                ENDIF
406!
407!--             Needed to avoid NaN particle velocities
408                IF ( e_int(n) == 0.0_wp )  THEN
409                   e_int(n) = 1.0E-20_wp
410                ENDIF
411!
412!--             Interpolate the TKE gradient along x (adopt incides i,j,k and
413!--             all position variables from above (TKE))
414                de_dx_int_l = ( ( gg - aa ) * de_dx(k,j,i)   + &
415                                ( gg - bb ) * de_dx(k,j,i+1) + &
416                                ( gg - cc ) * de_dx(k,j+1,i) + &
417                                ( gg - dd ) * de_dx(k,j+1,i+1) &
418                               ) / ( 3.0_wp * gg )
419
420                IF ( ( k+1 == nzt+1 )  .OR.  ( k == nzb ) )  THEN
421                   de_dx_int(n) = de_dx_int_l
422                ELSE
423                   de_dx_int_u = ( ( gg - aa ) * de_dx(k+1,j,i)   + &
424                                   ( gg - bb ) * de_dx(k+1,j,i+1) + &
425                                   ( gg - cc ) * de_dx(k+1,j+1,i) + &
426                                   ( gg - dd ) * de_dx(k+1,j+1,i+1) &
427                                  ) / ( 3.0_wp * gg )
428                   de_dx_int(n) = de_dx_int_l + ( zv(n) - zu(k) ) / dz * &
429                                              ( de_dx_int_u - de_dx_int_l )
430                ENDIF
431!
432!--             Interpolate the TKE gradient along y
433                de_dy_int_l = ( ( gg - aa ) * de_dy(k,j,i)   + &
434                                ( gg - bb ) * de_dy(k,j,i+1) + &
435                                ( gg - cc ) * de_dy(k,j+1,i) + &
436                                ( gg - dd ) * de_dy(k,j+1,i+1) &
437                               ) / ( 3.0_wp * gg )
438                IF ( ( k+1 == nzt+1 )  .OR.  ( k == nzb ) )  THEN
439                   de_dy_int(n) = de_dy_int_l
440                ELSE
441                   de_dy_int_u = ( ( gg - aa ) * de_dy(k+1,j,i)   + &
442                                  ( gg - bb ) * de_dy(k+1,j,i+1) + &
443                                  ( gg - cc ) * de_dy(k+1,j+1,i) + &
444                                  ( gg - dd ) * de_dy(k+1,j+1,i+1) &
445                                  ) / ( 3.0_wp * gg )
446                   de_dy_int(n) = de_dy_int_l + ( zv(n) - zu(k) ) / dz * &
447                                              ( de_dy_int_u - de_dy_int_l )
448                ENDIF
449
450!
451!--             Interpolate the TKE gradient along z
452                IF ( zv(n) < 0.5_wp * dz )  THEN
453                   de_dz_int(n) = 0.0_wp
454                ELSE
455                   de_dz_int_l = ( ( gg - aa ) * de_dz(k,j,i)   + &
456                                   ( gg - bb ) * de_dz(k,j,i+1) + &
457                                   ( gg - cc ) * de_dz(k,j+1,i) + &
458                                   ( gg - dd ) * de_dz(k,j+1,i+1) &
459                                  ) / ( 3.0_wp * gg )
460
461                   IF ( ( k+1 == nzt+1 )  .OR.  ( k == nzb ) )  THEN
462                      de_dz_int(n) = de_dz_int_l
463                   ELSE
464                      de_dz_int_u = ( ( gg - aa ) * de_dz(k+1,j,i)   + &
465                                      ( gg - bb ) * de_dz(k+1,j,i+1) + &
466                                      ( gg - cc ) * de_dz(k+1,j+1,i) + &
467                                      ( gg - dd ) * de_dz(k+1,j+1,i+1) &
468                                     ) / ( 3.0_wp * gg )
469                      de_dz_int(n) = de_dz_int_l + ( zv(n) - zu(k) ) / dz * &
470                                                 ( de_dz_int_u - de_dz_int_l )
471                   ENDIF
472                ENDIF
473
474!
475!--             Interpolate the dissipation of TKE
476                diss_int_l = ( ( gg - aa ) * diss(k,j,i)   + &
477                               ( gg - bb ) * diss(k,j,i+1) + &
478                               ( gg - cc ) * diss(k,j+1,i) + &
479                               ( gg - dd ) * diss(k,j+1,i+1) &
480                              ) / ( 3.0_wp * gg )
481
482                IF ( k == nzt )  THEN
483                   diss_int(n) = diss_int_l
484                ELSE
485                   diss_int_u = ( ( gg - aa ) * diss(k+1,j,i)   + &
486                                  ( gg - bb ) * diss(k+1,j,i+1) + &
487                                  ( gg - cc ) * diss(k+1,j+1,i) + &
488                                  ( gg - dd ) * diss(k+1,j+1,i+1) &
489                                 ) / ( 3.0_wp * gg )
490                   diss_int(n) = diss_int_l + ( zv(n) - zu(k) ) / dz * &
491                                           ( diss_int_u - diss_int_l )
492                ENDIF
493
494             ENDDO
495          ENDDO
496
497       ELSE ! non-flat topography, e.g., buildings
498
499          DO  n = 1, number_of_particles
500
501             i = particles(n)%x * ddx
502             j = particles(n)%y * ddy
503             k = ( zv(n) + 0.5_wp * dz * atmos_ocean_sign ) / dz  &
504                 + offset_ocean_nzt                      ! only exact if eq.dist
505!
506!--          In case that there are buildings it has to be determined
507!--          how many of the gridpoints defining the particle box are
508!--          situated within a building
509!--          gp_outside_of_building(1): i,j,k
510!--          gp_outside_of_building(2): i,j+1,k
511!--          gp_outside_of_building(3): i,j,k+1
512!--          gp_outside_of_building(4): i,j+1,k+1
513!--          gp_outside_of_building(5): i+1,j,k
514!--          gp_outside_of_building(6): i+1,j+1,k
515!--          gp_outside_of_building(7): i+1,j,k+1
516!--          gp_outside_of_building(8): i+1,j+1,k+1
517
518             gp_outside_of_building = 0
519             location = 0.0_wp
520             num_gp = 0
521
522             IF ( k > nzb_s_inner(j,i)  .OR.  nzb_s_inner(j,i) == 0 )  THEN
523                num_gp = num_gp + 1
524                gp_outside_of_building(1) = 1
525                location(num_gp,1) = i * dx
526                location(num_gp,2) = j * dy
527                location(num_gp,3) = k * dz - 0.5_wp * dz
528                ei(num_gp)     = e(k,j,i)
529                dissi(num_gp)  = diss(k,j,i)
530                de_dxi(num_gp) = de_dx(k,j,i)
531                de_dyi(num_gp) = de_dy(k,j,i)
532                de_dzi(num_gp) = de_dz(k,j,i)
533             ENDIF
534
535             IF ( k > nzb_s_inner(j+1,i)  .OR.  nzb_s_inner(j+1,i) == 0 ) &
536             THEN
537                num_gp = num_gp + 1
538                gp_outside_of_building(2) = 1
539                location(num_gp,1) = i * dx
540                location(num_gp,2) = (j+1) * dy
541                location(num_gp,3) = k * dz - 0.5_wp * dz
542                ei(num_gp)     = e(k,j+1,i)
543                dissi(num_gp)  = diss(k,j+1,i)
544                de_dxi(num_gp) = de_dx(k,j+1,i)
545                de_dyi(num_gp) = de_dy(k,j+1,i)
546                de_dzi(num_gp) = de_dz(k,j+1,i)
547             ENDIF
548
549             IF ( k+1 > nzb_s_inner(j,i)  .OR.  nzb_s_inner(j,i) == 0 )  THEN
550                num_gp = num_gp + 1
551                gp_outside_of_building(3) = 1
552                location(num_gp,1) = i * dx
553                location(num_gp,2) = j * dy
554                location(num_gp,3) = (k+1) * dz - 0.5_wp * dz
555                ei(num_gp)     = e(k+1,j,i)
556                dissi(num_gp)  = diss(k+1,j,i)
557                de_dxi(num_gp) = de_dx(k+1,j,i)
558                de_dyi(num_gp) = de_dy(k+1,j,i)
559                de_dzi(num_gp) = de_dz(k+1,j,i)
560             ENDIF
561
562             IF ( k+1 > nzb_s_inner(j+1,i)  .OR.  nzb_s_inner(j+1,i) == 0 ) &
563             THEN
564                num_gp = num_gp + 1
565                gp_outside_of_building(4) = 1
566                location(num_gp,1) = i * dx
567                location(num_gp,2) = (j+1) * dy
568                location(num_gp,3) = (k+1) * dz - 0.5_wp * dz
569                ei(num_gp)     = e(k+1,j+1,i)
570                dissi(num_gp)  = diss(k+1,j+1,i)
571                de_dxi(num_gp) = de_dx(k+1,j+1,i)
572                de_dyi(num_gp) = de_dy(k+1,j+1,i)
573                de_dzi(num_gp) = de_dz(k+1,j+1,i)
574             ENDIF
575
576             IF ( k > nzb_s_inner(j,i+1)  .OR.  nzb_s_inner(j,i+1) == 0 ) &
577             THEN
578                num_gp = num_gp + 1
579                gp_outside_of_building(5) = 1
580                location(num_gp,1) = (i+1) * dx
581                location(num_gp,2) = j * dy
582                location(num_gp,3) = k * dz - 0.5_wp * dz
583                ei(num_gp)     = e(k,j,i+1)
584                dissi(num_gp)  = diss(k,j,i+1)
585                de_dxi(num_gp) = de_dx(k,j,i+1)
586                de_dyi(num_gp) = de_dy(k,j,i+1)
587                de_dzi(num_gp) = de_dz(k,j,i+1)
588             ENDIF
589
590             IF ( k > nzb_s_inner(j+1,i+1)  .OR.  nzb_s_inner(j+1,i+1) == 0 ) &
591             THEN
592                num_gp = num_gp + 1
593                gp_outside_of_building(6) = 1
594                location(num_gp,1) = (i+1) * dx
595                location(num_gp,2) = (j+1) * dy
596                location(num_gp,3) = k * dz - 0.5_wp * dz
597                ei(num_gp)     = e(k,j+1,i+1)
598                dissi(num_gp)  = diss(k,j+1,i+1)
599                de_dxi(num_gp) = de_dx(k,j+1,i+1)
600                de_dyi(num_gp) = de_dy(k,j+1,i+1)
601                de_dzi(num_gp) = de_dz(k,j+1,i+1)
602             ENDIF
603
604             IF ( k+1 > nzb_s_inner(j,i+1)  .OR.  nzb_s_inner(j,i+1) == 0 ) &
605             THEN
606                num_gp = num_gp + 1
607                gp_outside_of_building(7) = 1
608                location(num_gp,1) = (i+1) * dx
609                location(num_gp,2) = j * dy
610                location(num_gp,3) = (k+1) * dz - 0.5_wp * dz
611                ei(num_gp)     = e(k+1,j,i+1)
612                dissi(num_gp)  = diss(k+1,j,i+1)
613                de_dxi(num_gp) = de_dx(k+1,j,i+1)
614                de_dyi(num_gp) = de_dy(k+1,j,i+1)
615                de_dzi(num_gp) = de_dz(k+1,j,i+1)
616             ENDIF
617
618             IF ( k+1 > nzb_s_inner(j+1,i+1)  .OR.  nzb_s_inner(j+1,i+1) == 0)&
619             THEN
620                num_gp = num_gp + 1
621                gp_outside_of_building(8) = 1
622                location(num_gp,1) = (i+1) * dx
623                location(num_gp,2) = (j+1) * dy
624                location(num_gp,3) = (k+1) * dz - 0.5_wp * dz
625                ei(num_gp)     = e(k+1,j+1,i+1)
626                dissi(num_gp)  = diss(k+1,j+1,i+1)
627                de_dxi(num_gp) = de_dx(k+1,j+1,i+1)
628                de_dyi(num_gp) = de_dy(k+1,j+1,i+1)
629                de_dzi(num_gp) = de_dz(k+1,j+1,i+1)
630             ENDIF
631
632!
633!--          If all gridpoints are situated outside of a building, then the
634!--          ordinary interpolation scheme can be used.
635             IF ( num_gp == 8 )  THEN
636
637                x  = particles(n)%x - i * dx
638                y  = particles(n)%y - j * dy
639                aa = x**2          + y**2
640                bb = ( dx - x )**2 + y**2
641                cc = x**2          + ( dy - y )**2
642                dd = ( dx - x )**2 + ( dy - y )**2
643                gg = aa + bb + cc + dd
644
645                e_int_l = ( ( gg - aa ) * e(k,j,i)   + ( gg - bb ) * e(k,j,i+1)   &
646                          + ( gg - cc ) * e(k,j+1,i) + ( gg - dd ) * e(k,j+1,i+1) &
647                          ) / ( 3.0_wp * gg )
648
649                IF ( k == nzt )  THEN
650                   e_int(n) = e_int_l
651                ELSE
652                   e_int_u = ( ( gg - aa ) * e(k+1,j,i)   + &
653                               ( gg - bb ) * e(k+1,j,i+1) + &
654                               ( gg - cc ) * e(k+1,j+1,i) + &
655                               ( gg - dd ) * e(k+1,j+1,i+1) &
656                             ) / ( 3.0_wp * gg )
657                   e_int(n) = e_int_l + ( zv(n) - zu(k) ) / dz * &
658                                     ( e_int_u - e_int_l )
659                ENDIF
660!
661!--             Needed to avoid NaN particle velocities
662                IF ( e_int(n) == 0.0_wp )  THEN
663                   e_int(n) = 1.0E-20_wp
664                ENDIF
665!
666!--             Interpolate the TKE gradient along x (adopt incides i,j,k
667!--             and all position variables from above (TKE))
668                de_dx_int_l = ( ( gg - aa ) * de_dx(k,j,i)   + &
669                                ( gg - bb ) * de_dx(k,j,i+1) + &
670                                ( gg - cc ) * de_dx(k,j+1,i) + &
671                                ( gg - dd ) * de_dx(k,j+1,i+1) &
672                              ) / ( 3.0_wp * gg )
673
674                IF ( ( k == nzt )  .OR.  ( k == nzb ) )  THEN
675                   de_dx_int(n) = de_dx_int_l
676                ELSE
677                   de_dx_int_u = ( ( gg - aa ) * de_dx(k+1,j,i)   + &
678                                   ( gg - bb ) * de_dx(k+1,j,i+1) + &
679                                   ( gg - cc ) * de_dx(k+1,j+1,i) + &
680                                   ( gg - dd ) * de_dx(k+1,j+1,i+1) &
681                                 ) / ( 3.0_wp * gg )
682                   de_dx_int(n) = de_dx_int_l + ( zv(n) - zu(k) ) / &
683                                           dz * ( de_dx_int_u - de_dx_int_l )
684                ENDIF
685
686!
687!--             Interpolate the TKE gradient along y
688                de_dy_int_l = ( ( gg - aa ) * de_dy(k,j,i)   + &
689                                ( gg - bb ) * de_dy(k,j,i+1) + &
690                                ( gg - cc ) * de_dy(k,j+1,i) + &
691                                ( gg - dd ) * de_dy(k,j+1,i+1) &
692                              ) / ( 3.0_wp * gg )
693                IF ( ( k+1 == nzt+1 )  .OR.  ( k == nzb ) )  THEN
694                   de_dy_int(n) = de_dy_int_l
695                ELSE
696                   de_dy_int_u = ( ( gg - aa ) * de_dy(k+1,j,i)   + &
697                                   ( gg - bb ) * de_dy(k+1,j,i+1) + &
698                                   ( gg - cc ) * de_dy(k+1,j+1,i) + &
699                                   ( gg - dd ) * de_dy(k+1,j+1,i+1) &
700                                 ) / ( 3.0_wp * gg )
701                   de_dy_int(n) = de_dy_int_l + ( zv(n) - zu(k) ) / &
702                                           dz * ( de_dy_int_u - de_dy_int_l )
703                ENDIF
704
705!
706!--             Interpolate the TKE gradient along z
707                IF ( zv(n) < 0.5_wp * dz )  THEN
708                   de_dz_int(n) = 0.0_wp
709                ELSE
710                   de_dz_int_l = ( ( gg - aa ) * de_dz(k,j,i)   + &
711                                   ( gg - bb ) * de_dz(k,j,i+1) + &
712                                   ( gg - cc ) * de_dz(k,j+1,i) + &
713                                   ( gg - dd ) * de_dz(k,j+1,i+1) &
714                                 ) / ( 3.0_wp * gg )
715
716                   IF ( ( k+1 == nzt+1 )  .OR.  ( k == nzb ) )  THEN
717                      de_dz_int(n) = de_dz_int_l
718                   ELSE
719                      de_dz_int_u = ( ( gg - aa ) * de_dz(k+1,j,i)   + &
720                                      ( gg - bb ) * de_dz(k+1,j,i+1) + &
721                                      ( gg - cc ) * de_dz(k+1,j+1,i) + &
722                                      ( gg - dd ) * de_dz(k+1,j+1,i+1) &
723                                    ) / ( 3.0_wp * gg )
724                      de_dz_int(n) = de_dz_int_l + ( zv(n) - zu(k) ) /&
725                                           dz * ( de_dz_int_u - de_dz_int_l )
726                   ENDIF
727                ENDIF
728
729!
730!--             Interpolate the dissipation of TKE
731                diss_int_l = ( ( gg - aa ) * diss(k,j,i)   + &
732                               ( gg - bb ) * diss(k,j,i+1) + &
733                               ( gg - cc ) * diss(k,j+1,i) + &
734                               ( gg - dd ) * diss(k,j+1,i+1) &
735                             ) / ( 3.0_wp * gg )
736
737                IF ( k == nzt )  THEN
738                   diss_int(n) = diss_int_l
739                ELSE
740                   diss_int_u = ( ( gg - aa ) * diss(k+1,j,i)   + &
741                                  ( gg - bb ) * diss(k+1,j,i+1) + &
742                                  ( gg - cc ) * diss(k+1,j+1,i) + &
743                                  ( gg - dd ) * diss(k+1,j+1,i+1) &
744                                ) / ( 3.0_wp * gg )
745                   diss_int(n) = diss_int_l + ( zv(n) - zu(k) ) / dz *&
746                                           ( diss_int_u - diss_int_l )
747                ENDIF
748
749             ELSE
750
751!
752!--             If wall between gridpoint 1 and gridpoint 5, then
753!--             Neumann boundary condition has to be applied
754                IF ( gp_outside_of_building(1) == 1  .AND. &
755                     gp_outside_of_building(5) == 0 )  THEN
756                   num_gp = num_gp + 1
757                   location(num_gp,1) = i * dx + 0.5_wp * dx
758                   location(num_gp,2) = j * dy
759                   location(num_gp,3) = k * dz - 0.5_wp * dz
760                   ei(num_gp)     = e(k,j,i)
761                   dissi(num_gp)  = diss(k,j,i)
762                   de_dxi(num_gp) = 0.0_wp
763                   de_dyi(num_gp) = de_dy(k,j,i)
764                   de_dzi(num_gp) = de_dz(k,j,i)
765                ENDIF
766
767                IF ( gp_outside_of_building(5) == 1  .AND. &
768                   gp_outside_of_building(1) == 0 )  THEN
769                   num_gp = num_gp + 1
770                   location(num_gp,1) = i * dx + 0.5_wp * dx
771                   location(num_gp,2) = j * dy
772                   location(num_gp,3) = k * dz - 0.5_wp * dz
773                   ei(num_gp)     = e(k,j,i+1)
774                   dissi(num_gp)  = diss(k,j,i+1)
775                   de_dxi(num_gp) = 0.0_wp
776                   de_dyi(num_gp) = de_dy(k,j,i+1)
777                   de_dzi(num_gp) = de_dz(k,j,i+1)
778                ENDIF
779
780!
781!--             If wall between gridpoint 5 and gridpoint 6, then
782!--             then Neumann boundary condition has to be applied
783                IF ( gp_outside_of_building(5) == 1  .AND. &
784                     gp_outside_of_building(6) == 0 )  THEN
785                   num_gp = num_gp + 1
786                   location(num_gp,1) = (i+1) * dx
787                   location(num_gp,2) = j * dy + 0.5_wp * dy
788                   location(num_gp,3) = k * dz - 0.5_wp * dz
789                   ei(num_gp)     = e(k,j,i+1)
790                   dissi(num_gp)  = diss(k,j,i+1)
791                   de_dxi(num_gp) = de_dx(k,j,i+1)
792                   de_dyi(num_gp) = 0.0_wp
793                   de_dzi(num_gp) = de_dz(k,j,i+1)
794                ENDIF
795
796                IF ( gp_outside_of_building(6) == 1  .AND. &
797                     gp_outside_of_building(5) == 0 )  THEN
798                   num_gp = num_gp + 1
799                   location(num_gp,1) = (i+1) * dx
800                   location(num_gp,2) = j * dy + 0.5_wp * dy
801                   location(num_gp,3) = k * dz - 0.5_wp * dz
802                   ei(num_gp)     = e(k,j+1,i+1)
803                   dissi(num_gp)  = diss(k,j+1,i+1)
804                   de_dxi(num_gp) = de_dx(k,j+1,i+1)
805                   de_dyi(num_gp) = 0.0_wp
806                   de_dzi(num_gp) = de_dz(k,j+1,i+1)
807                ENDIF
808
809!
810!--             If wall between gridpoint 2 and gridpoint 6, then
811!--             Neumann boundary condition has to be applied
812                IF ( gp_outside_of_building(2) == 1  .AND. &
813                     gp_outside_of_building(6) == 0 )  THEN
814                   num_gp = num_gp + 1
815                   location(num_gp,1) = i * dx + 0.5_wp * dx
816                   location(num_gp,2) = (j+1) * dy
817                   location(num_gp,3) = k * dz - 0.5_wp * dz
818                   ei(num_gp)     = e(k,j+1,i)
819                   dissi(num_gp)  = diss(k,j+1,i)
820                   de_dxi(num_gp) = 0.0_wp
821                   de_dyi(num_gp) = de_dy(k,j+1,i)
822                   de_dzi(num_gp) = de_dz(k,j+1,i)
823                ENDIF
824
825                IF ( gp_outside_of_building(6) == 1  .AND. &
826                     gp_outside_of_building(2) == 0 )  THEN
827                   num_gp = num_gp + 1
828                   location(num_gp,1) = i * dx + 0.5_wp * dx
829                   location(num_gp,2) = (j+1) * dy
830                   location(num_gp,3) = k * dz - 0.5_wp * dz
831                   ei(num_gp)     = e(k,j+1,i+1)
832                   dissi(num_gp)  = diss(k,j+1,i+1)
833                   de_dxi(num_gp) = 0.0_wp
834                   de_dyi(num_gp) = de_dy(k,j+1,i+1)
835                   de_dzi(num_gp) = de_dz(k,j+1,i+1)
836                ENDIF
837
838!
839!--             If wall between gridpoint 1 and gridpoint 2, then
840!--             Neumann boundary condition has to be applied
841                IF ( gp_outside_of_building(1) == 1  .AND. &
842                     gp_outside_of_building(2) == 0 )  THEN
843                   num_gp = num_gp + 1
844                   location(num_gp,1) = i * dx
845                   location(num_gp,2) = j * dy + 0.5_wp * dy
846                   location(num_gp,3) = k * dz - 0.5_wp * dz
847                   ei(num_gp)     = e(k,j,i)
848                   dissi(num_gp)  = diss(k,j,i)
849                   de_dxi(num_gp) = de_dx(k,j,i)
850                   de_dyi(num_gp) = 0.0_wp
851                   de_dzi(num_gp) = de_dz(k,j,i)
852                ENDIF
853
854                IF ( gp_outside_of_building(2) == 1  .AND. &
855                     gp_outside_of_building(1) == 0 )  THEN
856                   num_gp = num_gp + 1
857                   location(num_gp,1) = i * dx
858                   location(num_gp,2) = j * dy + 0.5_wp * dy
859                   location(num_gp,3) = k * dz - 0.5_wp * dz
860                   ei(num_gp)     = e(k,j+1,i)
861                   dissi(num_gp)  = diss(k,j+1,i)
862                   de_dxi(num_gp) = de_dx(k,j+1,i)
863                   de_dyi(num_gp) = 0.0_wp
864                   de_dzi(num_gp) = de_dz(k,j+1,i)
865                ENDIF
866
867!
868!--             If wall between gridpoint 3 and gridpoint 7, then
869!--             Neumann boundary condition has to be applied
870                IF ( gp_outside_of_building(3) == 1  .AND. &
871                     gp_outside_of_building(7) == 0 )  THEN
872                   num_gp = num_gp + 1
873                   location(num_gp,1) = i * dx + 0.5_wp * dx
874                   location(num_gp,2) = j * dy
875                   location(num_gp,3) = k * dz + 0.5_wp * dz
876                   ei(num_gp)     = e(k+1,j,i)
877                   dissi(num_gp)  = diss(k+1,j,i)
878                   de_dxi(num_gp) = 0.0_wp
879                   de_dyi(num_gp) = de_dy(k+1,j,i)
880                   de_dzi(num_gp) = de_dz(k+1,j,i) 
881                ENDIF
882
883                IF ( gp_outside_of_building(7) == 1  .AND. &
884                     gp_outside_of_building(3) == 0 )  THEN
885                   num_gp = num_gp + 1
886                   location(num_gp,1) = i * dx + 0.5_wp * dx
887                   location(num_gp,2) = j * dy
888                   location(num_gp,3) = k * dz + 0.5_wp * dz
889                   ei(num_gp)     = e(k+1,j,i+1)
890                   dissi(num_gp)  = diss(k+1,j,i+1)
891                   de_dxi(num_gp) = 0.0_wp
892                   de_dyi(num_gp) = de_dy(k+1,j,i+1)
893                   de_dzi(num_gp) = de_dz(k+1,j,i+1)
894                ENDIF
895
896!
897!--             If wall between gridpoint 7 and gridpoint 8, then
898!--             Neumann boundary condition has to be applied
899                IF ( gp_outside_of_building(7) == 1  .AND. &
900                     gp_outside_of_building(8) == 0 )  THEN
901                   num_gp = num_gp + 1
902                   location(num_gp,1) = (i+1) * dx
903                   location(num_gp,2) = j * dy + 0.5_wp * dy
904                   location(num_gp,3) = k * dz + 0.5_wp * dz
905                   ei(num_gp)     = e(k+1,j,i+1)
906                   dissi(num_gp)  = diss(k+1,j,i+1)
907                   de_dxi(num_gp) = de_dx(k+1,j,i+1)
908                   de_dyi(num_gp) = 0.0_wp
909                   de_dzi(num_gp) = de_dz(k+1,j,i+1)
910                ENDIF
911
912                IF ( gp_outside_of_building(8) == 1  .AND. &
913                     gp_outside_of_building(7) == 0 )  THEN
914                   num_gp = num_gp + 1
915                   location(num_gp,1) = (i+1) * dx
916                   location(num_gp,2) = j * dy + 0.5_wp * dy
917                   location(num_gp,3) = k * dz + 0.5_wp * dz
918                   ei(num_gp)     = e(k+1,j+1,i+1)
919                   dissi(num_gp)  = diss(k+1,j+1,i+1)
920                   de_dxi(num_gp) = de_dx(k+1,j+1,i+1)
921                   de_dyi(num_gp) = 0.0_wp
922                   de_dzi(num_gp) = de_dz(k+1,j+1,i+1)
923                ENDIF
924
925!
926!--             If wall between gridpoint 4 and gridpoint 8, then
927!--             Neumann boundary condition has to be applied
928                IF ( gp_outside_of_building(4) == 1  .AND. &
929                     gp_outside_of_building(8) == 0 )  THEN
930                   num_gp = num_gp + 1
931                   location(num_gp,1) = i * dx + 0.5_wp * dx
932                   location(num_gp,2) = (j+1) * dy
933                   location(num_gp,3) = k * dz + 0.5_wp * dz
934                   ei(num_gp)     = e(k+1,j+1,i)
935                   dissi(num_gp)  = diss(k+1,j+1,i)
936                   de_dxi(num_gp) = 0.0_wp
937                   de_dyi(num_gp) = de_dy(k+1,j+1,i)
938                   de_dzi(num_gp) = de_dz(k+1,j+1,i)
939                ENDIF
940
941                IF ( gp_outside_of_building(8) == 1  .AND. &
942                     gp_outside_of_building(4) == 0 )  THEN
943                   num_gp = num_gp + 1
944                   location(num_gp,1) = i * dx + 0.5_wp * dx
945                   location(num_gp,2) = (j+1) * dy
946                   location(num_gp,3) = k * dz + 0.5_wp * dz
947                   ei(num_gp)     = e(k+1,j+1,i+1)
948                   dissi(num_gp)  = diss(k+1,j+1,i+1)
949                   de_dxi(num_gp) = 0.0_wp
950                   de_dyi(num_gp) = de_dy(k+1,j+1,i+1)
951                   de_dzi(num_gp) = de_dz(k+1,j+1,i+1)
952                ENDIF
953
954!
955!--             If wall between gridpoint 3 and gridpoint 4, then
956!--             Neumann boundary condition has to be applied
957                IF ( gp_outside_of_building(3) == 1  .AND. &
958                     gp_outside_of_building(4) == 0 )  THEN
959                   num_gp = num_gp + 1
960                   location(num_gp,1) = i * dx
961                   location(num_gp,2) = j * dy + 0.5_wp * dy
962                   location(num_gp,3) = k * dz + 0.5_wp * dz
963                   ei(num_gp)     = e(k+1,j,i)
964                   dissi(num_gp)  = diss(k+1,j,i)
965                   de_dxi(num_gp) = de_dx(k+1,j,i)
966                   de_dyi(num_gp) = 0.0_wp
967                   de_dzi(num_gp) = de_dz(k+1,j,i)
968                ENDIF
969
970                IF ( gp_outside_of_building(4) == 1  .AND. &
971                     gp_outside_of_building(3) == 0 )  THEN
972                   num_gp = num_gp + 1
973                   location(num_gp,1) = i * dx
974                   location(num_gp,2) = j * dy + 0.5_wp * dy
975                   location(num_gp,3) = k * dz + 0.5_wp * dz
976                   ei(num_gp)     = e(k+1,j+1,i)
977                   dissi(num_gp)  = diss(k+1,j+1,i)
978                   de_dxi(num_gp) = de_dx(k+1,j+1,i)
979                   de_dyi(num_gp) = 0.0_wp
980                   de_dzi(num_gp) = de_dz(k+1,j+1,i)
981                ENDIF
982
983!
984!--             If wall between gridpoint 1 and gridpoint 3, then
985!--             Neumann boundary condition has to be applied
986!--             (only one case as only building beneath is possible)
987                IF ( gp_outside_of_building(1) == 0  .AND. &
988                     gp_outside_of_building(3) == 1 )  THEN
989                   num_gp = num_gp + 1
990                   location(num_gp,1) = i * dx
991                   location(num_gp,2) = j * dy
992                   location(num_gp,3) = k * dz
993                   ei(num_gp)     = e(k+1,j,i)
994                   dissi(num_gp)  = diss(k+1,j,i)
995                   de_dxi(num_gp) = de_dx(k+1,j,i)
996                   de_dyi(num_gp) = de_dy(k+1,j,i)
997                   de_dzi(num_gp) = 0.0_wp
998                ENDIF
999
1000!
1001!--             If wall between gridpoint 5 and gridpoint 7, then
1002!--             Neumann boundary condition has to be applied
1003!--             (only one case as only building beneath is possible)
1004                IF ( gp_outside_of_building(5) == 0  .AND. &
1005                     gp_outside_of_building(7) == 1 )  THEN
1006                   num_gp = num_gp + 1
1007                   location(num_gp,1) = (i+1) * dx
1008                   location(num_gp,2) = j * dy
1009                   location(num_gp,3) = k * dz
1010                   ei(num_gp)     = e(k+1,j,i+1)
1011                   dissi(num_gp)  = diss(k+1,j,i+1)
1012                   de_dxi(num_gp) = de_dx(k+1,j,i+1)
1013                   de_dyi(num_gp) = de_dy(k+1,j,i+1)
1014                   de_dzi(num_gp) = 0.0_wp
1015                ENDIF
1016
1017!
1018!--             If wall between gridpoint 2 and gridpoint 4, then
1019!--             Neumann boundary condition has to be applied
1020!--             (only one case as only building beneath is possible)
1021                IF ( gp_outside_of_building(2) == 0  .AND. &
1022                     gp_outside_of_building(4) == 1 )  THEN
1023                   num_gp = num_gp + 1
1024                   location(num_gp,1) = i * dx
1025                   location(num_gp,2) = (j+1) * dy
1026                   location(num_gp,3) = k * dz
1027                   ei(num_gp)     = e(k+1,j+1,i)
1028                   dissi(num_gp)  = diss(k+1,j+1,i)
1029                   de_dxi(num_gp) = de_dx(k+1,j+1,i)
1030                   de_dyi(num_gp) = de_dy(k+1,j+1,i)
1031                   de_dzi(num_gp) = 0.0_wp
1032                ENDIF
1033
1034!
1035!--             If wall between gridpoint 6 and gridpoint 8, then
1036!--             Neumann boundary condition has to be applied
1037!--             (only one case as only building beneath is possible)
1038                IF ( gp_outside_of_building(6) == 0  .AND. &
1039                     gp_outside_of_building(8) == 1 )  THEN
1040                   num_gp = num_gp + 1
1041                   location(num_gp,1) = (i+1) * dx
1042                   location(num_gp,2) = (j+1) * dy
1043                   location(num_gp,3) = k * dz
1044                   ei(num_gp)     = e(k+1,j+1,i+1)
1045                   dissi(num_gp)  = diss(k+1,j+1,i+1)
1046                   de_dxi(num_gp) = de_dx(k+1,j+1,i+1)
1047                   de_dyi(num_gp) = de_dy(k+1,j+1,i+1)
1048                   de_dzi(num_gp) = 0.0_wp
1049                ENDIF
1050
1051!
1052!--             Carry out the interpolation
1053                IF ( num_gp == 1 )  THEN
1054!
1055!--                If only one of the gridpoints is situated outside of the
1056!--                building, it follows that the values at the particle
1057!--                location are the same as the gridpoint values
1058                   e_int(n)     = ei(num_gp)
1059                   diss_int(n)  = dissi(num_gp)
1060                   de_dx_int(n) = de_dxi(num_gp)
1061                   de_dy_int(n) = de_dyi(num_gp)
1062                   de_dz_int(n) = de_dzi(num_gp)
1063                ELSE IF ( num_gp > 1 )  THEN
1064
1065                   d_sum = 0.0_wp
1066!
1067!--                Evaluation of the distances between the gridpoints
1068!--                contributing to the interpolated values, and the particle
1069!--                location
1070                   DO  agp = 1, num_gp
1071                      d_gp_pl(agp) = ( particles(n)%x-location(agp,1) )**2  &
1072                                   + ( particles(n)%y-location(agp,2) )**2  &
1073                                   + ( zv(n)-location(agp,3) )**2
1074                      d_sum        = d_sum + d_gp_pl(agp)
1075                   ENDDO
1076
1077!
1078!--                Finally the interpolation can be carried out
1079                   e_int(n)     = 0.0_wp 
1080                   diss_int(n)  = 0.0_wp 
1081                   de_dx_int(n) = 0.0_wp 
1082                   de_dy_int(n) = 0.0_wp 
1083                   de_dz_int(n) = 0.0_wp 
1084                   DO  agp = 1, num_gp
1085                      e_int(n)     = e_int(n)     + ( d_sum - d_gp_pl(agp) ) * &
1086                                             ei(agp) / ( (num_gp-1) * d_sum )
1087                      diss_int(n)  = diss_int(n)  + ( d_sum - d_gp_pl(agp) ) * &
1088                                          dissi(agp) / ( (num_gp-1) * d_sum )
1089                      de_dx_int(n) = de_dx_int(n) + ( d_sum - d_gp_pl(agp) ) * &
1090                                         de_dxi(agp) / ( (num_gp-1) * d_sum )
1091                      de_dy_int(n) = de_dy_int(n) + ( d_sum - d_gp_pl(agp) ) * &
1092                                         de_dyi(agp) / ( (num_gp-1) * d_sum )
1093                      de_dz_int(n) = de_dz_int(n) + ( d_sum - d_gp_pl(agp) ) * &
1094                                         de_dzi(agp) / ( (num_gp-1) * d_sum )
1095                   ENDDO
1096
1097                ENDIF
1098
1099             ENDIF
1100          ENDDO
1101       ENDIF
1102
1103       DO nb = 0,7
1104          i = ip + block_offset(nb)%i_off
1105          j = jp + block_offset(nb)%j_off
1106          k = kp + block_offset(nb)%k_off
1107
1108          DO  n = start_index(nb), end_index(nb)
1109!
1110!--          Vertical interpolation of the horizontally averaged SGS TKE and
1111!--          resolved-scale velocity variances and use the interpolated values
1112!--          to calculate the coefficient fs, which is a measure of the ratio
1113!--          of the subgrid-scale turbulent kinetic energy to the total amount
1114!--          of turbulent kinetic energy.
1115             IF ( k == 0 )  THEN
1116                e_mean_int = hom(0,1,8,0)
1117             ELSE
1118                e_mean_int = hom(k,1,8,0) +                                    &
1119                                           ( hom(k+1,1,8,0) - hom(k,1,8,0) ) / &
1120                                           ( zu(k+1) - zu(k) ) *               &
1121                                           ( zv(n) - zu(k) )
1122             ENDIF
1123
1124 !           kw = particles(n)%z / dz
1125             kw = kp-1                                    ! ok for ocean??? ( + offset_ocean_nzt_m1 ???)
1126
1127             IF ( k == 0 )  THEN
1128                aa  = hom(k+1,1,30,0)  * ( zv(n) / &
1129                                         ( 0.5_wp * ( zu(k+1) - zu(k) ) ) )
1130                bb  = hom(k+1,1,31,0)  * ( zv(n) / &
1131                                         ( 0.5_wp * ( zu(k+1) - zu(k) ) ) )
1132                cc  = hom(kw+1,1,32,0) * ( zv(n) / &
1133                                         ( 1.0_wp * ( zw(kw+1) - zw(kw) ) ) )
1134             ELSE
1135                aa  = hom(k,1,30,0) + ( hom(k+1,1,30,0) - hom(k,1,30,0) ) *    &
1136                           ( ( zv(n) - zu(k) ) / ( zu(k+1) - zu(k) ) )
1137                bb  = hom(k,1,31,0) + ( hom(k+1,1,31,0) - hom(k,1,31,0) ) *    &
1138                           ( ( zv(n) - zu(k) ) / ( zu(k+1) - zu(k) ) )
1139                cc  = hom(kw,1,32,0) + ( hom(kw+1,1,32,0)-hom(kw,1,32,0) ) *   &
1140                           ( ( zv(n) - zw(kw) ) / ( zw(kw+1)-zw(kw) ) )
1141             ENDIF
1142
1143             vv_int = ( 1.0_wp / 3.0_wp ) * ( aa + bb + cc )
1144!
1145!--          Needed to avoid NaN particle velocities. The value of 1.0 is just
1146!--          an educated guess for the given case.
1147             IF ( vv_int + ( 2.0_wp / 3.0_wp ) * e_mean_int == 0.0_wp )  THEN
1148                fs_int(n) = 1.0_wp
1149             ELSE
1150                fs_int(n) = ( 2.0_wp / 3.0_wp ) * e_mean_int /                 &
1151                            ( vv_int + ( 2.0_wp / 3.0_wp ) * e_mean_int )
1152             ENDIF
1153
1154          ENDDO
1155       ENDDO
1156
1157       DO  n = 1, number_of_particles
1158
1159         rg(n,1) = random_gauss( iran_part, 5.0_wp )
1160         rg(n,2) = random_gauss( iran_part, 5.0_wp )
1161         rg(n,3) = random_gauss( iran_part, 5.0_wp )
1162
1163       ENDDO
1164
1165       DO  n = 1, number_of_particles
1166!
1167!--       Calculate the Lagrangian timescale according to Weil et al. (2004).
1168          lagr_timescale = ( 4.0_wp * e_int(n) ) / &
1169                           ( 3.0_wp * fs_int(n) * c_0 * diss_int(n) )
1170
1171!
1172!--       Calculate the next particle timestep. dt_gap is the time needed to
1173!--       complete the current LES timestep.
1174          dt_gap = dt_3d - particles(n)%dt_sum
1175          dt_particle(n) = MIN( dt_3d, 0.025_wp * lagr_timescale, dt_gap )
1176
1177!
1178!--       The particle timestep should not be too small in order to prevent
1179!--       the number of particle timesteps of getting too large
1180          IF ( dt_particle(n) < dt_min_part  .AND.  dt_min_part < dt_gap )  THEN
1181             dt_particle(n) = dt_min_part
1182          ENDIF
1183
1184!
1185!--       Calculate the SGS velocity components
1186          IF ( particles(n)%age == 0.0_wp )  THEN
1187!
1188!--          For new particles the SGS components are derived from the SGS
1189!--          TKE. Limit the Gaussian random number to the interval
1190!--          [-5.0*sigma, 5.0*sigma] in order to prevent the SGS velocities
1191!--          from becoming unrealistically large.
1192             particles(n)%rvar1 = SQRT( 2.0_wp * sgs_wfu_part * e_int(n) ) *   &
1193                                  ( rg(n,1) - 1.0_wp )
1194             particles(n)%rvar2 = SQRT( 2.0_wp * sgs_wfv_part * e_int(n) ) *   &
1195                                  ( rg(n,2) - 1.0_wp )
1196             particles(n)%rvar3 = SQRT( 2.0_wp * sgs_wfw_part * e_int(n) ) *   &
1197                                  ( rg(n,3) - 1.0_wp )
1198
1199          ELSE
1200!
1201!--          Restriction of the size of the new timestep: compared to the
1202!--          previous timestep the increase must not exceed 200%
1203
1204             dt_particle_m = particles(n)%age - particles(n)%age_m
1205             IF ( dt_particle(n) > 2.0_wp * dt_particle_m )  THEN
1206                dt_particle(n) = 2.0_wp * dt_particle_m
1207             ENDIF
1208
1209!
1210!--          For old particles the SGS components are correlated with the
1211!--          values from the previous timestep. Random numbers have also to
1212!--          be limited (see above).
1213!--          As negative values for the subgrid TKE are not allowed, the
1214!--          change of the subgrid TKE with time cannot be smaller than
1215!--          -e_int(n)/dt_particle. This value is used as a lower boundary
1216!--          value for the change of TKE
1217
1218             de_dt_min = - e_int(n) / dt_particle(n)
1219
1220             de_dt = ( e_int(n) - particles(n)%e_m ) / dt_particle_m
1221
1222             IF ( de_dt < de_dt_min )  THEN
1223                de_dt = de_dt_min
1224             ENDIF
1225
1226             particles(n)%rvar1 = particles(n)%rvar1 - fs_int(n) * c_0 *       &
1227                           diss_int(n) * particles(n)%rvar1 * dt_particle(n) / &
1228                           ( 4.0_wp * sgs_wfu_part * e_int(n) ) +              &
1229                           ( 2.0_wp * sgs_wfu_part * de_dt *                   &
1230                             particles(n)%rvar1 /                              &
1231                             ( 2.0_wp * sgs_wfu_part * e_int(n) ) +            &
1232                             de_dx_int(n)                                      &
1233                           ) * dt_particle(n) / 2.0_wp          +              &
1234                           SQRT( fs_int(n) * c_0 * diss_int(n) ) *             &
1235                           ( rg(n,1) - 1.0_wp ) *                              &
1236                           SQRT( dt_particle(n) )
1237
1238             particles(n)%rvar2 = particles(n)%rvar2 - fs_int(n) * c_0 *       &
1239                           diss_int(n) * particles(n)%rvar2 * dt_particle(n) / &
1240                           ( 4.0_wp * sgs_wfv_part * e_int(n) ) +              &
1241                           ( 2.0_wp * sgs_wfv_part * de_dt *                   &
1242                             particles(n)%rvar2 /                              &
1243                             ( 2.0_wp * sgs_wfv_part * e_int(n) ) +            &
1244                             de_dy_int(n)                                      &
1245                           ) * dt_particle(n) / 2.0_wp          +              &
1246                           SQRT( fs_int(n) * c_0 * diss_int(n) ) *             &
1247                           ( rg(n,2) - 1.0_wp ) *                              &
1248                           SQRT( dt_particle(n) )
1249
1250             particles(n)%rvar3 = particles(n)%rvar3 - fs_int(n) * c_0 *       &
1251                           diss_int(n) * particles(n)%rvar3 * dt_particle(n) / &
1252                           ( 4.0_wp * sgs_wfw_part * e_int(n) ) +              &
1253                           ( 2.0_wp * sgs_wfw_part * de_dt *                   &
1254                             particles(n)%rvar3 /                              &
1255                             ( 2.0_wp * sgs_wfw_part * e_int(n) ) +            &
1256                             de_dz_int(n)                                      &
1257                           ) * dt_particle(n) / 2.0_wp          +              &
1258                           SQRT( fs_int(n) * c_0 * diss_int(n) ) *             &
1259                           ( rg(n,3) - 1.0_wp ) *                              &
1260                           SQRT( dt_particle(n) )
1261
1262          ENDIF
1263          u_int(n) = u_int(n) + particles(n)%rvar1
1264          v_int(n) = v_int(n) + particles(n)%rvar2
1265          w_int(n) = w_int(n) + particles(n)%rvar3
1266
1267!
1268!--       Store the SGS TKE of the current timelevel which is needed for
1269!--       for calculating the SGS particle velocities at the next timestep
1270          particles(n)%e_m = e_int(n)
1271       ENDDO
1272
1273    ELSE
1274!
1275!--    If no SGS velocities are used, only the particle timestep has to
1276!--    be set
1277       dt_particle = dt_3d
1278
1279    ENDIF
1280!
1281!-- Store the old age of the particle ( needed to prevent that a
1282!-- particle crosses several PEs during one timestep, and for the
1283!-- evaluation of the subgrid particle velocity fluctuations )
1284    particles(1:number_of_particles)%age_m = particles(1:number_of_particles)%age
1285
1286    dens_ratio = particle_groups(particles(1:number_of_particles)%group)%density_ratio
1287
1288    IF ( ANY( dens_ratio == 0.0_wp ) )  THEN
1289       DO  n = 1, number_of_particles
1290
1291!
1292!--       Particle advection
1293          IF ( dens_ratio(n) == 0.0_wp )  THEN
1294!
1295!--          Pure passive transport (without particle inertia)
1296             particles(n)%x = xv(n) + u_int(n) * dt_particle(n)
1297             particles(n)%y = yv(n) + v_int(n) * dt_particle(n)
1298             particles(n)%z = zv(n) + w_int(n) * dt_particle(n)
1299
1300             particles(n)%speed_x = u_int(n)
1301             particles(n)%speed_y = v_int(n)
1302             particles(n)%speed_z = w_int(n)
1303
1304          ELSE
1305!
1306!--          Transport of particles with inertia
1307             particles(n)%x = particles(n)%x + particles(n)%speed_x * &
1308                                               dt_particle(n)
1309             particles(n)%y = particles(n)%y + particles(n)%speed_y * &
1310                                               dt_particle(n)
1311             particles(n)%z = particles(n)%z + particles(n)%speed_z * &
1312                                               dt_particle(n)
1313
1314!
1315!--          Update of the particle velocity
1316             IF ( cloud_droplets )  THEN
1317                exp_arg  = 4.5_wp * dens_ratio(n) * molecular_viscosity /      &
1318                           ( particles(n)%radius )**2 *                        &
1319                           ( 1.0_wp + 0.15_wp * ( 2.0_wp * particles(n)%radius &
1320                             * SQRT( ( u_int(n) - particles(n)%speed_x )**2 +  &
1321                                     ( v_int(n) - particles(n)%speed_y )**2 +  &
1322                                     ( w_int(n) - particles(n)%speed_z )**2 )  &
1323                                          / molecular_viscosity )**0.687_wp    &
1324                           )
1325
1326                exp_term = EXP( -exp_arg * dt_particle(n) )
1327             ELSEIF ( use_sgs_for_particles )  THEN
1328                exp_arg  = particle_groups(particles(n)%group)%exp_arg
1329                exp_term = EXP( -exp_arg * dt_particle(n) )
1330             ELSE
1331                exp_arg  = particle_groups(particles(n)%group)%exp_arg
1332                exp_term = particle_groups(particles(n)%group)%exp_term
1333             ENDIF
1334             particles(n)%speed_x = particles(n)%speed_x * exp_term +          &
1335                                    u_int(n) * ( 1.0_wp - exp_term )
1336             particles(n)%speed_y = particles(n)%speed_y * exp_term +          &
1337                                    v_int(n) * ( 1.0_wp - exp_term )
1338             particles(n)%speed_z = particles(n)%speed_z * exp_term +          &
1339                                    ( w_int(n) - ( 1.0_wp - dens_ratio(n) ) *  &
1340                                    g / exp_arg ) * ( 1.0_wp - exp_term )
1341          ENDIF
1342
1343       ENDDO
1344   
1345    ELSE
1346
1347       DO  n = 1, number_of_particles
1348
1349!--       Transport of particles with inertia
1350          particles(n)%x = xv(n) + particles(n)%speed_x * dt_particle(n)
1351          particles(n)%y = yv(n) + particles(n)%speed_y * dt_particle(n)
1352          particles(n)%z = zv(n) + particles(n)%speed_z * dt_particle(n)
1353!
1354!--       Update of the particle velocity
1355          IF ( cloud_droplets )  THEN
1356
1357             exp_arg  = 4.5_wp * dens_ratio(n) * molecular_viscosity /         &
1358                        ( particles(n)%radius )**2 *                           &
1359                        ( 1.0_wp + 0.15_wp * ( 2.0_wp * particles(n)%radius *  &
1360                          SQRT( ( u_int(n) - particles(n)%speed_x )**2 +       &
1361                                ( v_int(n) - particles(n)%speed_y )**2 +       &
1362                                ( w_int(n) - particles(n)%speed_z )**2 ) /     &
1363                                         molecular_viscosity )**0.687_wp       &
1364                        )
1365
1366             exp_term = EXP( -exp_arg * dt_particle(n) )
1367          ELSEIF ( use_sgs_for_particles )  THEN
1368             exp_arg  = particle_groups(particles(n)%group)%exp_arg
1369             exp_term = EXP( -exp_arg * dt_particle(n) )
1370          ELSE
1371             exp_arg  = particle_groups(particles(n)%group)%exp_arg
1372             exp_term = particle_groups(particles(n)%group)%exp_term
1373          ENDIF
1374          particles(n)%speed_x = particles(n)%speed_x * exp_term +             &
1375                                 u_int(n) * ( 1.0_wp - exp_term )
1376          particles(n)%speed_y = particles(n)%speed_y * exp_term +             &
1377                                 v_int(n) * ( 1.0_wp - exp_term )
1378          particles(n)%speed_z = particles(n)%speed_z * exp_term +             &
1379                                 ( w_int(n) - ( 1.0_wp - dens_ratio(n) ) * g / &
1380                                 exp_arg ) * ( 1.0_wp - exp_term )
1381       ENDDO
1382
1383    ENDIF
1384
1385    DO  n = 1, number_of_particles
1386!
1387!--    Increment the particle age and the total time that the particle
1388!--    has advanced within the particle timestep procedure
1389       particles(n)%age    = particles(n)%age    + dt_particle(n)
1390       particles(n)%dt_sum = particles(n)%dt_sum + dt_particle(n)
1391
1392!
1393!--    Check whether there is still a particle that has not yet completed
1394!--    the total LES timestep
1395       IF ( ( dt_3d - particles(n)%dt_sum ) > 1E-8_wp )  THEN
1396          dt_3d_reached_l = .FALSE.
1397       ENDIF
1398
1399    ENDDO
1400
1401    CALL cpu_log( log_point_s(44), 'lpm_advec', 'pause' )
1402
1403 END SUBROUTINE lpm_advec
Note: See TracBrowser for help on using the repository browser.