The TELEMAC-MASCARET system  trunk
bnd_spectra.f
Go to the documentation of this file.
1 ! ******************
2  MODULE bnd_spectra
3 ! ******************
4 !
5 !
6 !***********************************************************************
7 ! TOMAWAC V7P3 23/02/2017
8 !***********************************************************************
9 !
10 !brief MODULE TO IMPOSE SPECTRA ON OPEN BOUNDARIES FROM AN
11 ! EXTERNAL MESH FILE
12 !
13 ! history A. JOLY (EDF - LNHE)
14 ! + 23/02/2017
15 ! + V7P3
16 ! + CREATED
17 !
18 !~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
19 !
20 !
21  IMPLICIT NONE
22 !
23  PRIVATE
24 !
25 !~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
26 !
27  PUBLIC :: impose_bnd_spectra
28 !
29 !~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
30 !
31 !+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
32 !
33  ! TIME VARIABLES
34  DOUBLE PRECISION :: tv1,tv2
35  INTEGER :: record1,record2
36  DOUBLE PRECISION :: time1,time2
37  !ERROR INTEGER WHEN READING THE MESH
38  INTEGER :: ierr
39  ! BOUNDARY SPECTRA VARIABLES
40  CHARACTER(LEN=80) :: bc_title ! TITLE
41  INTEGER :: bc_nvar ! NUMBER OF VARIABLES
42  INTEGER :: bc_npoin ! NUMBER OF MESH NODES
43  INTEGER :: bc_typ_elem ! TYPE OF ELEMENT
44  INTEGER :: bc_nelem ! NUMBER OF ELEMENTS
45  INTEGER :: bc_ndp ! NUMBER OF ELEMENT FACES
46  INTEGER :: bc_nptfr ! NUMBER OF BOUNDARY NODES
47  INTEGER :: bc_nptir ! NUMBER OF INTERFACES
48  INTEGER :: bc_ndim ! DIMENSION OF THE MESH
49  CHARACTER(LEN=16), ALLOCATABLE :: bc_varlist(:)
50  CHARACTER(LEN=16), ALLOCATABLE :: bc_unitlist(:)
51  INTEGER :: bc_nt ! NUMBER TIME STEPS
52  DOUBLE PRECISION, ALLOCATABLE :: bc_x(:),bc_y(:) !X AND Y COORDINATES ON SPE MESH
53  DOUBLE PRECISION, ALLOCATABLE :: bc_freq(:),bc_teta(:) !F AND THETA COORDINATES OF SPECTRUM
54  DOUBLE PRECISION, ALLOCATABLE :: bc_val(:) ! TEMPORY DATA FOR READING
55  DOUBLE PRECISION, ALLOCATABLE :: bc_all1(:,:), bc_all2(:,:) !VALUES A TIME TV1 AND TV2
56  !FOR POINT OF THE SPECTRA FILE
57  INTEGER, ALLOCATABLE :: bc_corr(:) ! INDEX OF THE CLOSEST SPECTRUM TO A LIQUID BOUNDARY NODE
58  ! OPTIONAL ARGUMENTS
59  INTEGER nnelebd, typ_bnd
60 !
61 
62  INTEGER :: nptfr_loc
63  INTEGER, ALLOCATABLE :: ind_ptfr(:) ! INDEX INTO VARLIST AND BOUNDARY NUMBER
64 !
65  SAVE
66 !
67 !+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
68 !
69 !***********************************************************************
70  CONTAINS
71 !***********************************************************************
72 
73 ! *****************************
74  SUBROUTINE impose_bnd_spectra
75 ! *****************************
76 !
77  & (imp_file,lt,at,fbor,nptfr,ndire,nf)
78 !
79 !***********************************************************************
80 ! TOMAWAC V7P3 23/02/2017
81 !***********************************************************************
82 !
83 ! brief READS SPECTRA SAVED IN A MESH FILE AND IMPOSES THEM ON
84 ! + OPEN BOUNDARY POINTS
85 !
86 ! history A. JOLY (EDF - LNHE)
87 ! + 23/02/2017
88 ! + V7P3
89 ! + CREATED
90 !
91 !~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
92 !| IMP_FILE |-->| MESH FILE WITH THE IMPOSED SPECTRA
93 !| LT |-->| NUMBER OF THE TIME STEP CURRENTLY SOLVED
94 !| AT |-->| COMPUTATION TIME
95 !| FBOR |<->| SPECTRAL VARIANCE DENSITY AT THE BOUNDARIES
96 !| NPTFR |-->| NUMBER OF BOUNDARY POINTS
97 !| NDIRE |-->| NUMBER OF DIRECTIONS
98 !| NF |-->| NUMBER OF FREQUENCIES
99 !~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
100 !
101  USE interface_hermes
104  USE bief_def, ONLY : bief_file
106  & x,y,nbor,lifbor,f1,raisf
107 !
108  IMPLICIT NONE
109 !
110 !+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
111 !
112  TYPE(bief_file), INTENT(IN) :: IMP_FILE
113  INTEGER, INTENT(IN) :: LT
114  DOUBLE PRECISION, INTENT(IN) :: AT
115  INTEGER, INTENT(IN) :: NPTFR,NDIRE,NF
116  DOUBLE PRECISION, INTENT(INOUT):: FBOR(nptfr,ndire,nf)
117 !
118 !+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
119 !
120  INTEGER IPTFR, ISPE, IPOIN, IDIR, IFF,ITMP
121  INTEGER X_ORIG, Y_ORIG
122  DOUBLE PRECISION DIST_SPE,DIST
123  DOUBLE PRECISION COEFT
124  DOUBLE PRECISION FCL1,FCL2
125  INTEGER BC_NF,BC_NDIRE,ITRAV
126  DOUBLE PRECISION BC_F1,BC_F2,BC_RAISF
127  DOUBLE PRECISION F_TEMP
128  DOUBLE PRECISION, PARAMETER :: EPS = 1.d-6
129 !
130 !-----------------------------------------------------------------------
131 ! DURING THE FIRST TIME STEP
132 !-----------------------------------------------------------------------
133  IF(lt.EQ.0)THEN
134 ! 1/ FIND THE CLOSEST SPECTRUM FOR EACH LIQUID BOUNDARY NODE
135  IF(ALLOCATED(bc_corr))DEALLOCATE(bc_corr)
136  ALLOCATE(bc_corr(nptfr))
137  DO iptfr=1,nptfr
138  IF(lifbor(iptfr).EQ.kent)THEN
139  dist_spe=1.d99
140  DO ispe=1,npspe
141  dist=sqrt((xspe(ispe)-x(nbor(iptfr)))**2+
142  & (yspe(ispe)-y(nbor(iptfr)))**2)
143  IF(dist.LE.dist_spe)THEN
144  bc_corr(iptfr)=ispe
145  dist_spe=dist
146  ENDIF
147  ENDDO
148  ELSE
149  bc_corr(iptfr)=0
150  ENDIF
151  END DO
152 ! 2/ READ THE MESH THE SPECTRA TO BE IMPOSED ON THE BOUNDARY
153  ! MESH INFO
154  CALL read_mesh_info(imp_file%FMT,imp_file%LU,
155  & bc_title,bc_nvar,
157  & bc_ndp,itrav,x_orig,y_orig,typ_bnd,nnelebd)
158  CALL get_mesh_dimension(imp_file%FMT,imp_file%LU,
159  & bc_ndim,ierr)
160  ! READ THE NAME OF THE VARIABLES
161  IF(ALLOCATED(bc_varlist))DEALLOCATE(bc_varlist)
162  IF(ALLOCATED(bc_unitlist))DEALLOCATE(bc_unitlist)
163  ALLOCATE(bc_varlist(bc_nvar))
164  ALLOCATE(bc_unitlist(bc_nvar))
165  CALL get_data_var_list(imp_file%FMT,imp_file%LU,
167 ! 3/ READ THE NUMBER OF TIME STEPS AND THE FIRST TIME
168  ! GET NUMBER OF TIME STEPS
169  CALL get_data_ntimestep(imp_file%FMT,imp_file%LU,
170  & bc_nt,ierr)
171  ! READ THE FIRST TIME
172  record1 = 0
173  record2 = 1
174  CALL get_data_time(imp_file%FMT,imp_file%LU,
175  & record1,time1,ierr)
177 
178  IF(tv1.GT.at) THEN
179  WRITE(lu,*)'*********************************************'
180  WRITE(lu,*)'THE FIRST RECORDING OF THE FILE'
181  WRITE(lu,*)' ',tv1,' IS OLDER THAN THE BEGINNING'
182  WRITE(lu,*)' OF THE COMPUTATION',at
183  WRITE(lu,*)'*********************************************'
184  CALL plante(1)
185  stop
186  ENDIF
187 
188  DO
189  CALL get_data_time(imp_file%FMT,imp_file%LU,
190  & record2,time2,ierr)
192  IF(tv2.LT.at) THEN
193  record1 = record2
194  record2 = record2 + 1
195  tv1 = tv2
196  IF (record2.GT.bc_nt) THEN
197  WRITE(lu,*)'*****************************************'
198  IF(lng.EQ.1) THEN
199  WRITE(lu,*)'LA FIN DU FICHIER DE CONDITION LIMITE'
200  WRITE(lu,*)'EST ATTEINTE AU TEMPS : ',at
201  ELSE
202  WRITE(lu,*)'THE END OF THE BOUNDARY CONDITION FILE'
203  WRITE(lu,*)'IS REACHED AT TIME: ',at
204  ENDIF
205  WRITE(lu,*)'*****************************************'
206  CALL plante(1)
207  stop
208  ENDIF
209  ELSE
210  EXIT
211  ENDIF
212  ENDDO
213 
214 
215 ! 4/ READ X AND Y COORDINATES
216  IF(ALLOCATED(bc_x))DEALLOCATE(bc_x)
217  IF(ALLOCATED(bc_y))DEALLOCATE(bc_y)
218  IF(ALLOCATED(bc_freq))DEALLOCATE(bc_freq)
219  IF(ALLOCATED(bc_teta))DEALLOCATE(bc_teta)
220  ALLOCATE(bc_x(bc_npoin))
221  ALLOCATE(bc_y(bc_npoin))
222  ALLOCATE(bc_freq(bc_npoin))
223  ALLOCATE(bc_teta(bc_npoin))
224 !
225  CALL get_mesh_coord(imp_file%FMT,imp_file%LU,
227  CALL get_mesh_coord(imp_file%FMT,imp_file%LU,
229 ! 5/ CHECK THAT THE MESH READ HAS THE SAME THE FREQUENCIES AND
230 ! DIRECTIONS AS IN THE SIMULATION
231  bc_nf=0
232  bc_ndire=0
233  bc_f1=10.d10
234  bc_f2=10.d10
235  bc_raisf=0.d0
236  DO ipoin=1,bc_npoin
237  IF((abs(bc_x(ipoin)).LE.eps).AND.(bc_y(ipoin).GE.0.0))THEN
238  bc_nf=bc_nf+1
239  f_temp=bc_y(ipoin)
240  IF(f_temp.LT.bc_f1)THEN
241  bc_f2=bc_f1
242  bc_f1=f_temp
243  ELSEIF(f_temp.LT.bc_f2)THEN
244  bc_f2=f_temp
245  ENDIF
246  ENDIF
247  END DO
248  bc_raisf=bc_f2/bc_f1
249  bc_ndire=bc_npoin/bc_nf
250  IF(abs(bc_f1-f1).GT.1.d-6) THEN
251  WRITE(lu,*)'*********************************************'
252  WRITE(lu,*)'THE MINIMAL FREQUENCY OF THE SPECTRA READ'
253  WRITE(lu,*)'IS NOT EQUAL TO THE FREQUENCY OF THE'
254  WRITE(lu,*)'SIMULATION.'
255  WRITE(lu,*)'- FREQUENCY OF THE SIMULATION:',f1
256  WRITE(lu,*)'- FREQUENCY READ:',bc_f1
257  WRITE(lu,*)'*********************************************'
258  CALL plante(1)
259  stop
260  ENDIF
261  IF(abs(bc_raisf-raisf).GT.1.d-6) THEN
262  WRITE(lu,*)'*********************************************'
263  WRITE(lu,*)'THE FREQUENTIAL RATIO OF THE SPECTRA READ'
264  WRITE(lu,*)'IS NOT EQUAL TO THE RATIO OF THE SIMULATION.'
265  WRITE(lu,*)'- FREQUENTIAL RATIO OF THE SIMULATION:',raisf
266  WRITE(lu,*)'- FREQUENTIAL RATIO READ:',bc_raisf
267  WRITE(lu,*)'*********************************************'
268  CALL plante(1)
269  stop
270  ENDIF
271  IF(bc_nf.NE.nf) THEN
272  WRITE(lu,*)'*********************************************'
273  WRITE(lu,*)'THE NUMBER OF FREQUENCY OF THE SPECTRA READ'
274  WRITE(lu,*)'IS NOT EQUAL TO THE NUMBER OF FREQUENCY OF THE'
275  WRITE(lu,*)'SIMULATION.'
276  WRITE(lu,*)'- NUMBER OF FREQUENCY OF THE SIMULATION:',nf
277  WRITE(lu,*)'- NUMBER OF FREQUENCY READ:',bc_nf
278  WRITE(lu,*)'*********************************************'
279  CALL plante(1)
280  stop
281  ENDIF
282  IF(bc_ndire.NE.ndire) THEN
283  WRITE(lu,*)'*********************************************'
284  WRITE(lu,*)'THE NUMBER OF DIRECTIONS OF THE SPECTRA READ'
285  WRITE(lu,*)'IS NOT EQUAL TO THE NUMBER OF DIRECTIONS OF THE'
286  WRITE(lu,*)'SIMULATION.'
287  WRITE(lu,*)'- NUMBER OF DIRECTIONS OF THE SIMULATION:',ndire
288  WRITE(lu,*)'- NUMBER OF DIRECTIONS READ:',bc_ndire
289  WRITE(lu,*)'*********************************************'
290  CALL plante(1)
291  stop
292  ENDIF
293 ! 6/ CALCULATE FREQ AND DIR
294  DO ipoin=1,bc_npoin
295  bc_teta(ipoin)=atan2(bc_x(ipoin),bc_y(ipoin))+atan(1.d0)*8.d0
296  bc_teta(ipoin)=mod(bc_teta(ipoin),atan(1.d0)*8.d0)
297  IF(sin(bc_teta(ipoin)).NE.0.d0)THEN
298  bc_freq(ipoin)=bc_x(ipoin)/sin(bc_teta(ipoin))
299  ELSE
300  bc_freq(ipoin)=bc_y(ipoin)/cos(bc_teta(ipoin))
301  ENDIF
302  ENDDO
303 ! 6.5/ CHECK NUMBER OF POINTS ON PROCESS
304  nptfr_loc = 0
305  ALLOCATE(ind_ptfr(nptfr))
306  DO iptfr=1,nptfr
307  IF(lifbor(iptfr).EQ.kent)THEN
308  nptfr_loc = nptfr_loc+1
309  ind_ptfr(nptfr_loc) = iptfr
310  ENDIF
311  ENDDO
312 
313 
314 ! 7/ ALLOCATE THE TEMPORARY SPECTRUM AT THE TWO TIME STEPS
315  IF(ALLOCATED(bc_val))DEALLOCATE(bc_val)
316  ALLOCATE(bc_val(bc_npoin))
317 
318  IF(ALLOCATED(bc_all1))DEALLOCATE(bc_all1)
319  IF(ALLOCATED(bc_all2))DEALLOCATE(bc_all2)
320  ALLOCATE(bc_all1(bc_npoin,nptfr_loc))
321  ALLOCATE(bc_all2(bc_npoin,nptfr_loc))
322 
323 ! 8/ READ FIRST TIME
324  DO iptfr=1,nptfr_loc
325  itmp = ind_ptfr(iptfr)
326  ! READ DATA BEFORE
327  CALL get_data_value(imp_file%FMT,imp_file%LU,
329  DO ipoin = 1,bc_npoin
330  bc_all1(ipoin,iptfr)= bc_val(ipoin)
331  ENDDO
332  ! READ DATA AFTER
333  CALL get_data_value(imp_file%FMT,imp_file%LU,
335  DO ipoin = 1,bc_npoin
336  bc_all2(ipoin,iptfr)= bc_val(ipoin)
337  ENDDO
338  ENDDO
339 
340 
341 !-----------------------------------------------------------------------
342  ENDIF
343 !-----------------------------------------------------------------------
344 ! FOR ALL TIME STEPS
345 !-----------------------------------------------------------------------
346 ! 8/ READ THE SECOND TIME STEP
347 
348  ! RETURN IF NO BOUNDARY DATA
349  IF (nptfr_loc.EQ.0) THEN
350  RETURN
351  ENDIF
352 
353 ! 8.5/ UPDATE DATA IF NEEDED
354  IF (at.GT.tv2) THEN
355  DO
356  record2 = record2+1
357  tv1 = tv2
358  CALL get_data_time(imp_file%FMT,imp_file%LU,
359  & record2,time2,ierr)
361  IF(tv2.LT.at) THEN
362  IF (record2.GT.bc_nt) THEN
363  WRITE(lu,*)'*****************************************'
364  IF(lng.EQ.1) THEN
365  WRITE(lu,*)'LA FIN DU FICHIER DE CONDITION LIMITE'
366  WRITE(lu,*)'EST ATTEINTE AU TEMPS : ',at
367  ELSE
368  WRITE(lu,*)'THE END OF THE BOUNDARY CONDITION FILE'
369  WRITE(lu,*)'IS REACHED AT TIME: ',at
370  ENDIF
371  WRITE(lu,*)'*****************************************'
372  CALL plante(1)
373  stop
374  ENDIF
375  ELSE
376  EXIT
377  ENDIF
378  ENDDO
379 
380  IF (record1.LT.record2-1) THEN
381  ! IN CASE TIME STEP IN SPECTRAL FILE IS SMALLER THAN MODEL TIME STEP
382  ! ALSO UPDATE RECORD 1
383  record1 = record2-1
384  DO iptfr=1,nptfr_loc
385  itmp = ind_ptfr(iptfr)
386  CALL get_data_value(imp_file%FMT,imp_file%LU,
387  & record1,bc_varlist(bc_corr(itmp)),bc_val,
388  & bc_npoin,ierr)
389  DO ipoin = 1,bc_npoin
390  bc_all1(ipoin,iptfr)= bc_val(ipoin)
391  ENDDO
392  ENDDO
393  ELSE
394  ! COPY DATA
395  record1 = record2
396  DO ipoin = 1,bc_npoin
397  bc_all2(ipoin,iptfr)= bc_val(ipoin)
398  ENDDO
399  ENDIF
400  ! UPDATE NEW TIME
401  DO iptfr=1,nptfr_loc
402  itmp = ind_ptfr(iptfr)
403  CALL get_data_value(imp_file%FMT,imp_file%LU,
405  DO ipoin = 1,bc_npoin
406  bc_all2(ipoin,iptfr)= bc_val(ipoin)
407  ENDDO
408  ENDDO
409  ENDIF
410 !
411  coeft=(at-tv1)/(tv2-tv1)
412 ! 9/ IMPOSE THE SPECTRA
413  !TODO; USE BETTER INTERPOLATION
414  DO iptfr=1,nptfr_loc
415  itmp = ind_ptfr(iptfr)
416  DO idir=1,ndire
417  DO iff=1,nf
418  ipoin=(idir+ndire*(iff-1))
419  fcl1=bc_all1(ipoin,iptfr)
420  fcl2=bc_all2(ipoin,iptfr)
421  fbor(itmp,idir,iff)=fcl1+(fcl2-fcl1)*coeft
422  ENDDO
423  ENDDO
424  ENDDO
425 
426 !
427  RETURN
428  END SUBROUTINE impose_bnd_spectra
429 !
430  END MODULE bnd_spectra
double precision, dimension(:), allocatable bc_y
Definition: bnd_spectra.f:53
integer bc_ndp
Definition: bnd_spectra.f:46
character(len=80) bc_title
Definition: bnd_spectra.f:41
double precision time1
Definition: bnd_spectra.f:37
subroutine get_data_var_list(FFORMAT, FID, NVAR, VARLIST, UNITLIST, IERR)
double precision, dimension(:), allocatable yspe
integer bc_nt
Definition: bnd_spectra.f:52
double precision tv2
Definition: bnd_spectra.f:35
integer bc_nptfr
Definition: bnd_spectra.f:47
integer bc_ndim
Definition: bnd_spectra.f:49
character(len=16), dimension(:), allocatable bc_unitlist
Definition: bnd_spectra.f:51
integer record2
Definition: bnd_spectra.f:36
double precision tv1
Definition: bnd_spectra.f:35
double precision, dimension(:,:), allocatable bc_all2
Definition: bnd_spectra.f:56
double precision, dimension(:), allocatable bc_x
Definition: bnd_spectra.f:53
integer bc_nptir
Definition: bnd_spectra.f:48
subroutine get_data_value(FFORMAT, FID, RECORD, VAR_NAME, RES_VALUE, N, IERR)
Definition: get_data_value.f:7
integer, parameter kent
subroutine read_mesh_info(FFORMAT, NFIC, TITLE, NVAR, NPOIN, TYP_ELEM, NELEM, NPTFR, NPTIR, NDP, NPLAN, X_ORIG, Y_ORIG, TYP_BND_ELEM, NELEBD)
Definition: read_mesh_info.f:8
integer ierr
Definition: bnd_spectra.f:39
integer nnelebd
Definition: bnd_spectra.f:60
character(len=16), dimension(:), allocatable bc_varlist
Definition: bnd_spectra.f:50
integer bc_typ_elem
Definition: bnd_spectra.f:44
integer, dimension(:), allocatable bc_corr
Definition: bnd_spectra.f:58
subroutine get_mesh_dimension(FFORMAT, FID, NDIM, IERR)
integer, dimension(:), allocatable ind_ptfr
Definition: bnd_spectra.f:64
integer record1
Definition: bnd_spectra.f:36
integer bc_nelem
Definition: bnd_spectra.f:45
double precision, dimension(:), allocatable xspe
subroutine, public impose_bnd_spectra(IMP_FILE, LT, AT, FBOR, NPTFR, NDIRE, NF)
Definition: bnd_spectra.f:79
integer bc_npoin
Definition: bnd_spectra.f:43
subroutine get_mesh_coord(FFORMAT, FID, JDIM, NDIM, NPOIN, COORD, IERR)
Definition: get_mesh_coord.f:7
double precision time2
Definition: bnd_spectra.f:37
double precision, dimension(:,:), allocatable bc_all1
Definition: bnd_spectra.f:56
integer bc_nvar
Definition: bnd_spectra.f:42
subroutine get_data_time(FFORMAT, FID, RECORD, TIME, IERR)
Definition: get_data_time.f:7
integer nptfr_loc
Definition: bnd_spectra.f:63
double precision, dimension(:), allocatable bc_teta
Definition: bnd_spectra.f:54
double precision, dimension(:), allocatable bc_freq
Definition: bnd_spectra.f:54
subroutine get_data_ntimestep(FFORMAT, FID, NTIMESTEP, IERR)
double precision, dimension(:), allocatable bc_val
Definition: bnd_spectra.f:55
integer typ_bnd
Definition: bnd_spectra.f:60