libsim Versione 8.0.0

◆ vol7d_get_volanai()

subroutine vol7d_get_volanai ( type(vol7d), intent(in) this,
integer, dimension(:), intent(in) dimlist,
integer, dimension(:), optional, pointer vol1dp,
integer, dimension(:,:), optional, pointer vol2dp,
integer, dimension(:,:,:), optional, pointer vol3dp )

Crea una vista a dimensione ridotta di un volume di anagrafica di tipo INTEGER.

È necessario fornire uno solo dei parametri opzionali vol*dp corrispondente al numero di dimensioni richieste. L'ordine delle dimensioni nella vista è quello prefissato in vol7d indipendentemente dall'ordine delle dimensioni fornito in dimlist. In caso di fallimento, in particolare se dimlist non contiene tutte le dimensioni non degeneri del volume richiesto oppure se una delle dimensioni è =0, il puntatore vol*dp è restituito in uno stato disassociato, per cui è opportuno controllare sempre in uscita, lo stato del puntatore per evitare che il programma abortisca con un errore di sistema, ad esempio:

INTEGER, POINTER :: vol1d(:)
...
CALL vol7d_get_volanai(v7d1, (/vol7d_ana_d/), vol1d)
IF (ASSOCIATED(vol1d)) THEN
print*,vol1d
...
ENDIF
return
Parametri
[in]thisoggetto di cui creare la vista
[in]dimlistlista delle dimensioni da includere nella vista, attenzione tutte le dimensioni non degeneri (cioè con estensione >1) devono essere incluse nella lista; utilizzare le costanti vol7d_ana_a ... vol7d_attr_a, ecc.
vol1dparray che in uscita conterrà la vista 1d
vol2dparray che in uscita conterrà la vista 2d
vol3dparray che in uscita conterrà la vista 3d

Definizione alla linea 4893 del file vol7d_class.F90.

4895! Copyright (C) 2010 ARPA-SIM <urpsim@smr.arpa.emr.it>
4896! authors:
4897! Davide Cesari <dcesari@arpa.emr.it>
4898! Paolo Patruno <ppatruno@arpa.emr.it>
4899
4900! This program is free software; you can redistribute it and/or
4901! modify it under the terms of the GNU General Public License as
4902! published by the Free Software Foundation; either version 2 of
4903! the License, or (at your option) any later version.
4904
4905! This program is distributed in the hope that it will be useful,
4906! but WITHOUT ANY WARRANTY; without even the implied warranty of
4907! MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
4908! GNU General Public License for more details.
4909
4910! You should have received a copy of the GNU General Public License
4911! along with this program. If not, see <http://www.gnu.org/licenses/>.
4912#include "config.h"
4913
4914!> \defgroup vol7d Libsim package, vol7d library.
4915!! The libsim vol7d library contains classes for managing pointwise
4916!! data, tipically weather observations, and for their import from a
4917!! Db-All.e database or from a WMO BUFR file. In order to compile and
4918!! link programs using this library, you have to insert the required
4919!! \c USE statements in the program units involved, specify the
4920!! location of module files when compiling (tipically \c
4921!! -I/usr/lib/gfortran/modules or \c -I/usr/lib64/gfortran/modules or
4922!! \c -I/usr/include) and indicate the library name \c -lsim_vol7d
4923!! when linking, assuming that the library has been installed in a
4924!! default location.
4925
4926!> Classe per la gestione di un volume completo di dati osservati.
4927!! Questo modulo definisce gli oggetti e i metodi per gestire
4928!! volumi di dati meteorologici sparsi.
4929!! I volumi definiti sono principalmente di 4 categorie:
4930!! - volumi di anagrafica (vol7d::volanar & c.), hanno 3 dimensioni:
4931!! - anagrafica
4932!! - variabile di anagrafica
4933!! - rete
4934!! - volumi di attributi di anagrafica (vol7d::volanaattrr & c.), hanno 4 dimensioni:
4935!! - anagrafica
4936!! - variabile di anagrafica
4937!! - rete
4938!! - variabile di attributi delle variabili di anagrafica
4939!! - volumi di dati (vol7d::voldatir & c.), hanno 6 dimensioni:
4940!! - anagrafica
4941!! - tempo
4942!! - livello verticale
4943!! - intervallo temporale (timerange)
4944!! - variabile di dati
4945!! - rete
4946!! - volumi di attributi di dati (vol7d::voldatiattrr & c.), hanno 7 dimensioni:
4947!! - anagrafica
4948!! - tempo
4949!! - livello verticale
4950!! - intervallo temporale (timerange)
4951!! - variabile di dati
4952!! - rete
4953!! - variabile di attributi delle variabili di dati
4954!!
4955!! Tutte le variabili sono inoltre disponibil1 in 5 tipi diversi:
4956!! - reale (abbreviato r)
4957!! - doppia precisione (abbreviato d)
4958!! - intero (abbreviato i)
4959!! - byte (abbreviato b)
4960!! - carattere (abbreviato c)
4961!!
4962!! Per ognuna delle dimensioni possibili, incluse le variabili e gli
4963!! attributi con i loro diversi tipi,
4964!! è definito un cosiddetto "vettore di descrittori", con un
4965!! numero di elementi pari all'estensione della dimensione stessa,
4966!! che contiene le informazioni necessarie a descrivere
4967!! gli elementi di quella dimensione.
4968!! In realtà l'utente non dovrà generalmente occuparsi di costruire
4969!! un oggetto vol7d con le proprie mani ma utilizzerà nella maggior parte
4970!! dei casi i metodi di importazione preconfezionati che importano dati da
4971!! DB-All.e (vol7d_dballe_class) o dal DB Oracle del SIM (vol7d_oraclesim_class).
4972!!
4973!!
4974!! Il programma esempio_v7d.f90 contiene un esempio elementare di uso
4975!! della classe vol7d:
4976!! \include esempio_v7d.f90
4977!!
4978!! \ingroup vol7d
4979MODULE vol7d_class
4980USE kinds
4984USE log4fortran
4985USE err_handling
4986USE io_units
4993IMPLICIT NONE
4994
4995
4996INTEGER, PARAMETER :: vol7d_maxdim_a = 3, vol7d_maxdim_aa = 4, &
4997 vol7d_maxdim_d = 6, vol7d_maxdim_ad = 7
4998
4999INTEGER, PARAMETER :: vol7d_ana_a=1 !< indice della dimensione "anagrafica" nei volumi di anagrafica, da usare nei metodi vol7d_get_volana*
5000INTEGER, PARAMETER :: vol7d_var_a=2 !< indice della dimensione "variabile" nei volumi di anagrafica, da usare nei metodi vol7d_get_volana*
5001INTEGER, PARAMETER :: vol7d_network_a=3 !< indice della dimensione "rete" nei volumi di anagrafica, da usare nei metodi vol7d_get_volana*
5002INTEGER, PARAMETER :: vol7d_attr_a=4 !< indice della dimensione "attributo" nei volumi di anagrafica, da usare nei metodi vol7d_get_volana*
5003INTEGER, PARAMETER :: vol7d_ana_d=1 !< indice della dimensione "anagrafica" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
5004INTEGER, PARAMETER :: vol7d_time_d=2 !< indice della dimensione "tempo" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
5005INTEGER, PARAMETER :: vol7d_level_d=3 !< indice della dimensione "livello verticale" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
5006INTEGER, PARAMETER :: vol7d_timerange_d=4 !< indice della dimensione "intervallo temporale" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
5007INTEGER, PARAMETER :: vol7d_var_d=5 !< indice della dimensione "variabile" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
5008INTEGER, PARAMETER :: vol7d_network_d=6 !< indice della dimensione "rete" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
5009INTEGER, PARAMETER :: vol7d_attr_d=7 !< indice della dimensione "attributo" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
5010INTEGER, PARAMETER :: vol7d_cdatalen=32
5011
5012TYPE vol7d_varmap
5013 INTEGER :: r, d, i, b, c
5014END TYPE vol7d_varmap
5015
5016!> Definisce un oggetto contenente i volumi anagrafica e dati e tutti
5017!! i descrittori delle loro dimensioni.
5018TYPE vol7d
5019!> vettore descrittore della dimensione anagrafica
5020 TYPE(vol7d_ana),POINTER :: ana(:)
5021!> vettore descrittore della dimensione tempo
5022 TYPE(datetime),POINTER :: time(:)
5023!> vettore descrittore della dimensione livello verticale
5024 TYPE(vol7d_level),POINTER :: level(:)
5025!> vettore descrittore della dimensione intervallo temporale (timerange)
5026 TYPE(vol7d_timerange),POINTER :: timerange(:)
5027!> vettore descrittore della dimensione rete
5028 TYPE(vol7d_network),POINTER :: network(:)
5029!> vettore descrittore della dimensione variabile di anagrafica
5030 TYPE(vol7d_varvect) :: anavar
5031!> vettore descrittore della dimensione attributo delle variabili di anagrafica
5032 TYPE(vol7d_varvect) :: anaattr
5033!> vettore descrittore della dimensione variabile di anagrafica che ha tali attributi
5034 TYPE(vol7d_varvect) :: anavarattr
5035!> vettore descrittore della dimensione variabile di dati
5036 TYPE(vol7d_varvect) :: dativar
5037!> vettore descrittore della dimensione attributo delle variabili di dati
5038 TYPE(vol7d_varvect) :: datiattr
5039!> vettore descrittore della dimensione variabile di dati che ha tali attributi
5040 TYPE(vol7d_varvect) :: dativarattr
5041
5042!> volume di anagrafica a valori reali
5043 REAL,POINTER :: volanar(:,:,:)
5044!> volume di anagrafica a valori a doppia precisione
5045 DOUBLE PRECISION,POINTER :: volanad(:,:,:)
5046!> volume di anagrafica a valori interi
5047 INTEGER,POINTER :: volanai(:,:,:)
5048!> volume di anagrafica a valori byte
5049 INTEGER(kind=int_b),POINTER :: volanab(:,:,:)
5050!> volume di anagrafica a valori carattere
5051 CHARACTER(len=vol7d_cdatalen),POINTER :: volanac(:,:,:)
5052
5053!> volume di attributi di anagrafica a valori reali
5054 REAL,POINTER :: volanaattrr(:,:,:,:)
5055!> volume di attributi di anagrafica a valori a doppia precisione
5056 DOUBLE PRECISION,POINTER :: volanaattrd(:,:,:,:)
5057!> volume di attributi di anagrafica a valori interi
5058 INTEGER,POINTER :: volanaattri(:,:,:,:)
5059!> volume di attributi di anagrafica a valori byte
5060 INTEGER(kind=int_b),POINTER :: volanaattrb(:,:,:,:)
5061!> volume di attributi di anagrafica a valori carattere
5062 CHARACTER(len=vol7d_cdatalen),POINTER :: volanaattrc(:,:,:,:)
5063
5064!> volume di dati a valori reali
5065 REAL,POINTER :: voldatir(:,:,:,:,:,:) ! sono i dati
5066!> volume di dati a valori a doppia precisione
5067 DOUBLE PRECISION,POINTER :: voldatid(:,:,:,:,:,:)
5068!> volume di dati a valori interi
5069 INTEGER,POINTER :: voldatii(:,:,:,:,:,:)
5070!> volume di dati a valori byte
5071 INTEGER(kind=int_b),POINTER :: voldatib(:,:,:,:,:,:)
5072!> volume di dati a valori carattere
5073 CHARACTER(len=vol7d_cdatalen),POINTER :: voldatic(:,:,:,:,:,:)
5074
5075!> volume di attributi di dati a valori reali
5076 REAL,POINTER :: voldatiattrr(:,:,:,:,:,:,:)
5077!> volume di attributi di dati a valori a doppia precisione
5078 DOUBLE PRECISION,POINTER :: voldatiattrd(:,:,:,:,:,:,:)
5079!> volume di attributi di dati a valori interi
5080 INTEGER,POINTER :: voldatiattri(:,:,:,:,:,:,:)
5081!> volume di attributi di dati a valori byte
5082 INTEGER(kind=int_b),POINTER :: voldatiattrb(:,:,:,:,:,:,:)
5083!> volume di attributi di dati a valori carattere
5084 CHARACTER(len=vol7d_cdatalen),POINTER :: voldatiattrc(:,:,:,:,:,:,:)
5085
5086!> time definition; 0=time is reference time, 1=time is validity time
5087 integer :: time_definition
5088
5089END TYPE vol7d
5090
5091!> Costruttore per la classe vol7d.
5092!! Deve essere richiamato
5093!! per tutti gli oggetti di questo tipo definiti in un programma.
5094INTERFACE init
5095 MODULE PROCEDURE vol7d_init
5096END INTERFACE
5097
5098!> Distruttore per la classe vol7d.
5099INTERFACE delete
5100 MODULE PROCEDURE vol7d_delete
5101END INTERFACE
5102
5103!> Scrittura su file.
5104INTERFACE export
5105 MODULE PROCEDURE vol7d_write_on_file
5106END INTERFACE
5107
5108!> Lettura da file.
5109INTERFACE import
5110 MODULE PROCEDURE vol7d_read_from_file
5111END INTERFACE
5112
5113!>Print object
5114INTERFACE display
5115 MODULE PROCEDURE vol7d_display, dat_display, dat_vect_display
5116END INTERFACE
5117
5118!>Represent data in a pretty string
5119INTERFACE to_char
5120 MODULE PROCEDURE to_char_dat
5121END INTERFACE
5122
5123!>doubleprecision data conversion
5124INTERFACE doubledat
5125 MODULE PROCEDURE doubledatd,doubledatr,doubledati,doubledatb,doubledatc
5126END INTERFACE
5127
5128!>real data conversion
5129INTERFACE realdat
5130 MODULE PROCEDURE realdatd,realdatr,realdati,realdatb,realdatc
5131END INTERFACE
5132
5133!>integer data conversion
5134INTERFACE integerdat
5135 MODULE PROCEDURE integerdatd,integerdatr,integerdati,integerdatb,integerdatc
5136END INTERFACE
5137
5138!>copy object
5139INTERFACE copy
5140 MODULE PROCEDURE vol7d_copy
5141END INTERFACE
5142
5143!> Test for a missing volume
5144INTERFACE c_e
5145 MODULE PROCEDURE vol7d_c_e
5146END INTERFACE
5147
5148!> Check for problems
5149!! return 0 if all check passed
5150!! print diagnostics with log4f
5151INTERFACE check
5152 MODULE PROCEDURE vol7d_check
5153END INTERFACE
5154
5155!> Reduce some dimensions (level and timerage) for semplification (rounding).
5156!! You can use this for simplify and use variables in computation like alchimia
5157!! where fields have to be on the same coordinate
5158!! It return real or character data only: if input is charcter data only it return character otherwise il return
5159!! all the data converted to real.
5160!! examples:
5161!! means in time for short periods and istantaneous values
5162!! 2 meter and surface levels
5163!! If there are data on more then one almost equal levels or timeranges, the first var present (at least one point)
5164!! will be taken (order is by icreasing var index).
5165!! You can use predefined values for classic semplification
5166!! almost_equal_levels and almost_equal_timeranges
5167!! The level or timerange in output will be defined by the first element of level and timerange list
5168INTERFACE rounding
5169 MODULE PROCEDURE v7d_rounding
5170END INTERFACE
5171
5172!!$INTERFACE get_volana
5173!!$ MODULE PROCEDURE vol7d_get_volanar, vol7d_get_volanad, vol7d_get_volanai, &
5174!!$ vol7d_get_volanab, vol7d_get_volanac
5175!!$END INTERFACE
5176!!$
5177!!$INTERFACE get_voldati
5178!!$ MODULE PROCEDURE vol7d_get_voldatir, vol7d_get_voldatid, vol7d_get_voldatii, &
5179!!$ vol7d_get_voldatib, vol7d_get_voldatic
5180!!$END INTERFACE
5181!!$
5182!!$INTERFACE get_volanaattr
5183!!$ MODULE PROCEDURE vol7d_get_volanaattrr, vol7d_get_volanaattrd, &
5184!!$ vol7d_get_volanaattri, vol7d_get_volanaattrb, vol7d_get_volanaattrc
5185!!$END INTERFACE
5186!!$
5187!!$INTERFACE get_voldatiattr
5188!!$ MODULE PROCEDURE vol7d_get_voldatiattrr, vol7d_get_voldatiattrd, &
5189!!$ vol7d_get_voldatiattri, vol7d_get_voldatiattrb, vol7d_get_voldatiattrc
5190!!$END INTERFACE
5191
5192PRIVATE vol7d_get_volr, vol7d_get_vold, vol7d_get_voli, vol7d_get_volb, &
5193 vol7d_get_volc, &
5194 volptr1dr, volptr2dr, volptr3dr, volptr4dr, volptr5dr, volptr6dr, volptr7dr, &
5195 volptr1dd, volptr2dd, volptr3dd, volptr4dd, volptr5dd, volptr6dd, volptr7dd, &
5196 volptr1di, volptr2di, volptr3di, volptr4di, volptr5di, volptr6di, volptr7di, &
5197 volptr1db, volptr2db, volptr3db, volptr4db, volptr5db, volptr6db, volptr7db, &
5198 volptr1dc, volptr2dc, volptr3dc, volptr4dc, volptr5dc, volptr6dc, volptr7dc, &
5199 vol7d_nullifyr, vol7d_nullifyd, vol7d_nullifyi, vol7d_nullifyb, vol7d_nullifyc, &
5200 vol7d_init, vol7d_delete, vol7d_write_on_file, vol7d_read_from_file, &
5201 vol7d_check_alloc_ana, vol7d_force_alloc_ana, &
5202 vol7d_check_alloc_dati, vol7d_force_alloc_dati, vol7d_force_alloc, &
5203 vol7d_display, dat_display, dat_vect_display, &
5204 to_char_dat, vol7d_check
5205
5206PRIVATE doubledatd,doubledatr,doubledati,doubledatb,doubledatc
5207
5208PRIVATE vol7d_c_e
5209
5210CONTAINS
5211
5212
5213!> Inizializza un oggetto di tipo vol7d.
5214!! Non riceve alcun parametro tranne l'oggetto stesso. Attenzione, è necessario
5215!! comunque chiamare sempre il costruttore per evitare di avere dei puntatori in
5216!! uno stato indefinito.
5217SUBROUTINE vol7d_init(this,time_definition)
5218TYPE(vol7d),intent(out) :: this !< oggetto da inizializzare
5219INTEGER,INTENT(IN),OPTIONAL :: time_definition !< 0=time is reference time; 1=time is validity time; 2=time is validity time, forecast range forced to 0 (default=1)
5220
5221CALL init(this%anavar)
5222CALL init(this%anaattr)
5223CALL init(this%anavarattr)
5224CALL init(this%dativar)
5225CALL init(this%datiattr)
5226CALL init(this%dativarattr)
5227
5228NULLIFY(this%ana, this%time, this%level, this%timerange, this%network)
5229
5230NULLIFY(this%volanar, this%volanaattrr, this%voldatir, this%voldatiattrr)
5231NULLIFY(this%volanad, this%volanaattrd, this%voldatid, this%voldatiattrd)
5232NULLIFY(this%volanai, this%volanaattri, this%voldatii, this%voldatiattri)
5233NULLIFY(this%volanab, this%volanaattrb, this%voldatib, this%voldatiattrb)
5234NULLIFY(this%volanac, this%volanaattrc, this%voldatic, this%voldatiattrc)
5235
5236if(present(time_definition)) then
5237 this%time_definition=time_definition
5238else
5239 this%time_definition=1 !default to validity time
5240end if
5241
5242END SUBROUTINE vol7d_init
5243
5244
5245!> Distrugge l'oggetto in maniera pulita, liberando l'eventuale memoria
5246!! dinamicamente allocata. Permette di distruggere la sola parte di dati
5247!! mantenendo l'anagrafica.
5248ELEMENTAL SUBROUTINE vol7d_delete(this, dataonly)
5249TYPE(vol7d),intent(inout) :: this !< oggetto da distruggere
5250LOGICAL, INTENT(in), OPTIONAL :: dataonly !< dealloca solo i dati, tenendo l'anagrafica, (default \c .FALSE.)
5251
5252
5253IF (.NOT. optio_log(dataonly)) THEN
5254 IF (ASSOCIATED(this%volanar)) DEALLOCATE(this%volanar)
5255 IF (ASSOCIATED(this%volanad)) DEALLOCATE(this%volanad)
5256 IF (ASSOCIATED(this%volanai)) DEALLOCATE(this%volanai)
5257 IF (ASSOCIATED(this%volanab)) DEALLOCATE(this%volanab)
5258 IF (ASSOCIATED(this%volanac)) DEALLOCATE(this%volanac)
5259 IF (ASSOCIATED(this%volanaattrr)) DEALLOCATE(this%volanaattrr)
5260 IF (ASSOCIATED(this%volanaattrd)) DEALLOCATE(this%volanaattrd)
5261 IF (ASSOCIATED(this%volanaattri)) DEALLOCATE(this%volanaattri)
5262 IF (ASSOCIATED(this%volanaattrb)) DEALLOCATE(this%volanaattrb)
5263 IF (ASSOCIATED(this%volanaattrc)) DEALLOCATE(this%volanaattrc)
5264ENDIF
5265IF (ASSOCIATED(this%voldatir)) DEALLOCATE(this%voldatir)
5266IF (ASSOCIATED(this%voldatid)) DEALLOCATE(this%voldatid)
5267IF (ASSOCIATED(this%voldatii)) DEALLOCATE(this%voldatii)
5268IF (ASSOCIATED(this%voldatib)) DEALLOCATE(this%voldatib)
5269IF (ASSOCIATED(this%voldatic)) DEALLOCATE(this%voldatic)
5270IF (ASSOCIATED(this%voldatiattrr)) DEALLOCATE(this%voldatiattrr)
5271IF (ASSOCIATED(this%voldatiattrd)) DEALLOCATE(this%voldatiattrd)
5272IF (ASSOCIATED(this%voldatiattri)) DEALLOCATE(this%voldatiattri)
5273IF (ASSOCIATED(this%voldatiattrb)) DEALLOCATE(this%voldatiattrb)
5274IF (ASSOCIATED(this%voldatiattrc)) DEALLOCATE(this%voldatiattrc)
5275
5276IF (.NOT. optio_log(dataonly)) THEN
5277 IF (ASSOCIATED(this%ana)) DEALLOCATE(this%ana)
5278 IF (ASSOCIATED(this%network)) DEALLOCATE(this%network)
5279ENDIF
5280IF (ASSOCIATED(this%time)) DEALLOCATE(this%time)
5281IF (ASSOCIATED(this%level)) DEALLOCATE(this%level)
5282IF (ASSOCIATED(this%timerange)) DEALLOCATE(this%timerange)
5283
5284IF (.NOT. optio_log(dataonly)) THEN
5285 CALL delete(this%anavar)
5286 CALL delete(this%anaattr)
5287 CALL delete(this%anavarattr)
5288ENDIF
5289CALL delete(this%dativar)
5290CALL delete(this%datiattr)
5291CALL delete(this%dativarattr)
5292
5293END SUBROUTINE vol7d_delete
5294
5295
5296
5297integer function vol7d_check(this)
5298TYPE(vol7d),intent(in) :: this !< object to check
5299integer :: i,j,k,l,m,n
5300
5301vol7d_check=0
5302
5303if (associated(this%voldatii)) then
5304do i = 1,size(this%voldatii,1)
5305 do j = 1,size(this%voldatii,2)
5306 do k = 1,size(this%voldatii,3)
5307 do l = 1,size(this%voldatii,4)
5308 do m = 1,size(this%voldatii,5)
5309 do n = 1,size(this%voldatii,6)
5310 if (this%voldatii(i,j,k,l,m,n) /= this%voldatii(i,j,k,l,m,n) ) then
5311 CALL l4f_log(l4f_warn,"check: abnormal value at voldatii("&
5312 //t2c(i)//","//t2c(j)//","//t2c(k)//","//t2c(l)//","//t2c(m)//","//t2c(n)//",)")
5313 vol7d_check=1
5314 end if
5315 end do
5316 end do
5317 end do
5318 end do
5319 end do
5320end do
5321end if
5322
5323
5324if (associated(this%voldatir)) then
5325do i = 1,size(this%voldatir,1)
5326 do j = 1,size(this%voldatir,2)
5327 do k = 1,size(this%voldatir,3)
5328 do l = 1,size(this%voldatir,4)
5329 do m = 1,size(this%voldatir,5)
5330 do n = 1,size(this%voldatir,6)
5331 if (this%voldatir(i,j,k,l,m,n) /= this%voldatir(i,j,k,l,m,n) ) then
5332 CALL l4f_log(l4f_warn,"check: abnormal value at voldatir("&
5333 //t2c(i)//","//t2c(j)//","//t2c(k)//","//t2c(l)//","//t2c(m)//","//t2c(n)//",)")
5334 vol7d_check=2
5335 end if
5336 end do
5337 end do
5338 end do
5339 end do
5340 end do
5341end do
5342end if
5343
5344if (associated(this%voldatid)) then
5345do i = 1,size(this%voldatid,1)
5346 do j = 1,size(this%voldatid,2)
5347 do k = 1,size(this%voldatid,3)
5348 do l = 1,size(this%voldatid,4)
5349 do m = 1,size(this%voldatid,5)
5350 do n = 1,size(this%voldatid,6)
5351 if (this%voldatid(i,j,k,l,m,n) /= this%voldatid(i,j,k,l,m,n) ) then
5352 CALL l4f_log(l4f_warn,"check: abnormal value at voldatid("&
5353 //t2c(i)//","//t2c(j)//","//t2c(k)//","//t2c(l)//","//t2c(m)//","//t2c(n)//",)")
5354 vol7d_check=3
5355 end if
5356 end do
5357 end do
5358 end do
5359 end do
5360 end do
5361end do
5362end if
5363
5364if (associated(this%voldatib)) then
5365do i = 1,size(this%voldatib,1)
5366 do j = 1,size(this%voldatib,2)
5367 do k = 1,size(this%voldatib,3)
5368 do l = 1,size(this%voldatib,4)
5369 do m = 1,size(this%voldatib,5)
5370 do n = 1,size(this%voldatib,6)
5371 if (this%voldatib(i,j,k,l,m,n) /= this%voldatib(i,j,k,l,m,n) ) then
5372 CALL l4f_log(l4f_warn,"check: abnormal value at voldatib("&
5373 //t2c(i)//","//t2c(j)//","//t2c(k)//","//t2c(l)//","//t2c(m)//","//t2c(n)//",)")
5374 vol7d_check=4
5375 end if
5376 end do
5377 end do
5378 end do
5379 end do
5380 end do
5381end do
5382end if
5383
5384end function vol7d_check
5385
5386
5387
5388!TODO da completare ! aborta se i volumi sono allocati a dimensione 0
5389!> stampa a video una sintesi del contenuto
5390SUBROUTINE vol7d_display(this)
5391TYPE(vol7d),intent(in) :: this !< oggetto da visualizzare
5392integer :: i
5393
5394REAL :: rdat
5395DOUBLE PRECISION :: ddat
5396INTEGER :: idat
5397INTEGER(kind=int_b) :: bdat
5398CHARACTER(len=vol7d_cdatalen) :: cdat
5399
5400
5401print*,"<<<<<<<<<<<<<<<<<<< vol7d object >>>>>>>>>>>>>>>>>>>>"
5402if (this%time_definition == 0) then
5403 print*,"TIME DEFINITION: time is reference time"
5404else if (this%time_definition == 1) then
5405 print*,"TIME DEFINITION: time is validity time"
5406else if (this%time_definition == 2) then
5407 print*,"TIME DEFINITION: time is validity time, forecast range forced to 0"
5408else
5409 print*,"Time definition has a wrong walue:", this%time_definition
5410end if
5411
5412IF (ASSOCIATED(this%network))then
5413 print*,"---- network vector ----"
5414 print*,"elements=",size(this%network)
5415 do i=1, size(this%network)
5416 call display(this%network(i))
5417 end do
5418end IF
5419
5420IF (ASSOCIATED(this%ana))then
5421 print*,"---- ana vector ----"
5422 print*,"elements=",size(this%ana)
5423 do i=1, size(this%ana)
5424 call display(this%ana(i))
5425 end do
5426end IF
5427
5428IF (ASSOCIATED(this%time))then
5429 print*,"---- time vector ----"
5430 print*,"elements=",size(this%time)
5431 do i=1, size(this%time)
5432 call display(this%time(i))
5433 end do
5434end if
5435
5436IF (ASSOCIATED(this%level)) then
5437 print*,"---- level vector ----"
5438 print*,"elements=",size(this%level)
5439 do i =1,size(this%level)
5440 call display(this%level(i))
5441 end do
5442end if
5443
5444IF (ASSOCIATED(this%timerange))then
5445 print*,"---- timerange vector ----"
5446 print*,"elements=",size(this%timerange)
5447 do i =1,size(this%timerange)
5448 call display(this%timerange(i))
5449 end do
5450end if
5451
5452
5453print*,"---- ana vector ----"
5454print*,""
5455print*,"->>>>>>>>> anavar -"
5456call display(this%anavar)
5457print*,""
5458print*,"->>>>>>>>> anaattr -"
5459call display(this%anaattr)
5460print*,""
5461print*,"->>>>>>>>> anavarattr -"
5462call display(this%anavarattr)
5463
5464print*,"-- ana data section (first point) --"
5465
5466idat=imiss
5467rdat=rmiss
5468ddat=dmiss
5469bdat=ibmiss
5470cdat=cmiss
5471
5472!ntime = MIN(SIZE(this%time),nprint)
5473!ntimerange = MIN(SIZE(this%timerange),nprint)
5474!nlevel = MIN(SIZE(this%level),nprint)
5475!nnetwork = MIN(SIZE(this%network),nprint)
5476!nana = MIN(SIZE(this%ana),nprint)
5477
5478IF (SIZE(this%ana) > 0 .AND. SIZE(this%network) > 0) THEN
5479if (associated(this%volanai)) then
5480 do i=1,size(this%anavar%i)
5481 idat=this%volanai(1,i,1)
5482 if (associated(this%anavar%i)) call display(this%anavar%i(i),idat,rdat,ddat,bdat,cdat)
5483 end do
5484end if
5485idat=imiss
5486
5487if (associated(this%volanar)) then
5488 do i=1,size(this%anavar%r)
5489 rdat=this%volanar(1,i,1)
5490 if (associated(this%anavar%r)) call display(this%anavar%r(i),idat,rdat,ddat,bdat,cdat)
5491 end do
5492end if
5493rdat=rmiss
5494
5495if (associated(this%volanad)) then
5496 do i=1,size(this%anavar%d)
5497 ddat=this%volanad(1,i,1)
5498 if (associated(this%anavar%d)) call display(this%anavar%d(i),idat,rdat,ddat,bdat,cdat)
5499 end do
5500end if
5501ddat=dmiss
5502
5503if (associated(this%volanab)) then
5504 do i=1,size(this%anavar%b)
5505 bdat=this%volanab(1,i,1)
5506 if (associated(this%anavar%b)) call display(this%anavar%b(i),idat,rdat,ddat,bdat,cdat)
5507 end do
5508end if
5509bdat=ibmiss
5510
5511if (associated(this%volanac)) then
5512 do i=1,size(this%anavar%c)
5513 cdat=this%volanac(1,i,1)
5514 if (associated(this%anavar%c)) call display(this%anavar%c(i),idat,rdat,ddat,bdat,cdat)
5515 end do
5516end if
5517cdat=cmiss
5518ENDIF
5519
5520print*,"---- data vector ----"
5521print*,""
5522print*,"->>>>>>>>> dativar -"
5523call display(this%dativar)
5524print*,""
5525print*,"->>>>>>>>> datiattr -"
5526call display(this%datiattr)
5527print*,""
5528print*,"->>>>>>>>> dativarattr -"
5529call display(this%dativarattr)
5530
5531print*,"-- data data section (first point) --"
5532
5533idat=imiss
5534rdat=rmiss
5535ddat=dmiss
5536bdat=ibmiss
5537cdat=cmiss
5538
5539IF (SIZE(this%ana) > 0 .AND. SIZE(this%network) > 0 .AND. size(this%time) > 0 &
5540 .AND. size(this%level) > 0 .AND. size(this%timerange) > 0) THEN
5541if (associated(this%voldatii)) then
5542 do i=1,size(this%dativar%i)
5543 idat=this%voldatii(1,1,1,1,i,1)
5544 if (associated(this%dativar%i)) call display(this%dativar%i(i),idat,rdat,ddat,bdat,cdat)
5545 end do
5546end if
5547idat=imiss
5548
5549if (associated(this%voldatir)) then
5550 do i=1,size(this%dativar%r)
5551 rdat=this%voldatir(1,1,1,1,i,1)
5552 if (associated(this%dativar%r)) call display(this%dativar%r(i),idat,rdat,ddat,bdat,cdat)
5553 end do
5554end if
5555rdat=rmiss
5556
5557if (associated(this%voldatid)) then
5558 do i=1,size(this%dativar%d)
5559 ddat=this%voldatid(1,1,1,1,i,1)
5560 if (associated(this%dativar%d)) call display(this%dativar%d(i),idat,rdat,ddat,bdat,cdat)
5561 end do
5562end if
5563ddat=dmiss
5564
5565if (associated(this%voldatib)) then
5566 do i=1,size(this%dativar%b)
5567 bdat=this%voldatib(1,1,1,1,i,1)
5568 if (associated(this%dativar%b)) call display(this%dativar%b(i),idat,rdat,ddat,bdat,cdat)
5569 end do
5570end if
5571bdat=ibmiss
5572
5573if (associated(this%voldatic)) then
5574 do i=1,size(this%dativar%c)
5575 cdat=this%voldatic(1,1,1,1,i,1)
5576 if (associated(this%dativar%c)) call display(this%dativar%c(i),idat,rdat,ddat,bdat,cdat)
5577 end do
5578end if
5579cdat=cmiss
5580ENDIF
5581
5582print*,"<<<<<<<<<<<<<<<<<<< END vol7d object >>>>>>>>>>>>>>>>>>>>"
5583
5584END SUBROUTINE vol7d_display
5585
5586
5587!> stampa a video una sintesi del contenuto
5588SUBROUTINE dat_display(this,idat,rdat,ddat,bdat,cdat)
5589TYPE(vol7d_var),intent(in) :: this !< oggetto da visualizzare
5590!> real
5591REAL :: rdat
5592!> double precision
5593DOUBLE PRECISION :: ddat
5594!> integer
5595INTEGER :: idat
5596!> byte
5597INTEGER(kind=int_b) :: bdat
5598!> character
5599CHARACTER(len=*) :: cdat
5600
5601print *, to_char_dat(this,idat,rdat,ddat,bdat,cdat)
5602
5603end SUBROUTINE dat_display
5604
5605!> stampa a video una sintesi del contenuto
5606SUBROUTINE dat_vect_display(this,idat,rdat,ddat,bdat,cdat)
5607
5608TYPE(vol7d_var),intent(in) :: this(:) !< oggetto da visualizzare
5609!> real
5610REAL :: rdat(:)
5611!> double precision
5612DOUBLE PRECISION :: ddat(:)
5613!> integer
5614INTEGER :: idat(:)
5615!> byte
5616INTEGER(kind=int_b) :: bdat(:)
5617!> character
5618CHARACTER(len=*):: cdat(:)
5619
5620integer :: i
5621
5622do i =1,size(this)
5623 call display(this(i),idat(i),rdat(i),ddat(i),bdat(i),cdat(i))
5624end do
5625
5626end SUBROUTINE dat_vect_display
5627
5628
5629FUNCTION to_char_dat(this,idat,rdat,ddat,bdat,cdat)
5630#ifdef HAVE_DBALLE
5631USE dballef
5632#endif
5633TYPE(vol7d_var),INTENT(in) :: this
5634!> real
5635REAL :: rdat
5636!> double precision
5637DOUBLE PRECISION :: ddat
5638!> integer
5639INTEGER :: idat
5640!> byte
5641INTEGER(kind=int_b) :: bdat
5642!> character
5643CHARACTER(len=*) :: cdat
5644CHARACTER(len=80) :: to_char_dat
5645
5646CHARACTER(len=LEN(to_char_dat)) :: to_char_tmp
5647
5648
5649#ifdef HAVE_DBALLE
5650INTEGER :: handle, ier
5651
5652handle = 0
5653to_char_dat="VALUE: "
5654
5655if (c_e(idat)) to_char_dat=trim(to_char_dat)//" ;int> "//trim(to_char(idat))
5656if (c_e(rdat)) to_char_dat=trim(to_char_dat)//" ;real> "//trim(to_char(rdat))
5657if (c_e(ddat)) to_char_dat=trim(to_char_dat)//" ;double> "//trim(to_char(ddat))
5658if (c_e(bdat)) to_char_dat=trim(to_char_dat)//" ;byte> "//trim(to_char(bdat))
5659
5660if ( c_e(cdat))then
5661 ier = idba_messaggi(handle,"/dev/null", "w", "BUFR")
5662 ier = idba_spiegab(handle,this%btable,cdat,to_char_tmp)
5663 ier = idba_fatto(handle)
5664 to_char_dat=trim(to_char_dat)//" ;char> "//trim(to_char_tmp)
5665endif
5666
5667#else
5668
5669to_char_dat="VALUE: "
5670if (c_e(idat)) to_char_dat=trim(to_char_dat)//" ;int> "//trim(to_char(idat))
5671if (c_e(rdat)) to_char_dat=trim(to_char_dat)//" ;real> "//trim(to_char(rdat))
5672if (c_e(ddat)) to_char_dat=trim(to_char_dat)//" ;double> "//trim(to_char(ddat))
5673if (c_e(bdat)) to_char_dat=trim(to_char_dat)//" ;byte> "//trim(to_char(bdat))
5674if (c_e(cdat)) to_char_dat=trim(to_char_dat)//" ;char> "//trim(cdat)
5675
5676#endif
5677
5678END FUNCTION to_char_dat
5679
5680
5681!> Tests whether anything has ever been assigned to a vol7d object
5682!! (.TRUE.) or it is as clean as after an init (.FALSE.).
5683FUNCTION vol7d_c_e(this) RESULT(c_e)
5684TYPE(vol7d), INTENT(in) :: this
5685
5686LOGICAL :: c_e
5687
5688c_e = ASSOCIATED(this%ana) .OR. ASSOCIATED(this%time) .OR. &
5689 ASSOCIATED(this%level) .OR. ASSOCIATED(this%timerange) .OR. &
5690 ASSOCIATED(this%network) .OR. &
5691 ASSOCIATED(this%anavar%r) .OR. ASSOCIATED(this%anavar%d) .OR. &
5692 ASSOCIATED(this%anavar%i) .OR. ASSOCIATED(this%anavar%b) .OR. &
5693 ASSOCIATED(this%anavar%c) .OR. &
5694 ASSOCIATED(this%anaattr%r) .OR. ASSOCIATED(this%anaattr%d) .OR. &
5695 ASSOCIATED(this%anaattr%i) .OR. ASSOCIATED(this%anaattr%b) .OR. &
5696 ASSOCIATED(this%anaattr%c) .OR. &
5697 ASSOCIATED(this%dativar%r) .OR. ASSOCIATED(this%dativar%d) .OR. &
5698 ASSOCIATED(this%dativar%i) .OR. ASSOCIATED(this%dativar%b) .OR. &
5699 ASSOCIATED(this%dativar%c) .OR. &
5700 ASSOCIATED(this%datiattr%r) .OR. ASSOCIATED(this%datiattr%d) .OR. &
5701 ASSOCIATED(this%datiattr%i) .OR. ASSOCIATED(this%datiattr%b) .OR. &
5702 ASSOCIATED(this%datiattr%c)
5703
5704END FUNCTION vol7d_c_e
5705
5706
5707!> Metodo per allocare i descrittori delle 7 dimensioni.
5708!! Riceve un grande numero di parametri opzionali che
5709!! indicano quali descrittori allocare e con quale estensione;
5710!! i descrittori non specificati non vengono toccati.
5711!! Può essere quindi chiamato più volte allocando via via
5712!! descrittori relativi a dimensioni diverse.
5713!! Se un descrittore richiesto è già allocato, viene deallocato
5714!! (perdendone l'eventuale contenuto) e riallocato con l'estensione
5715!! richiesta.
5716!! Per i descrittori relativi a dimensioni che non siano variabili o attributi,
5717!! è possibile specificare l'estensione di una dimensione a 0,
5718!! in tal caso il descrittore viene comunque allocato con lunghezza nulla,
5719!! che è diverso da non allocarlo. Per i descrittori di variabili e attributi
5720!! passare un'estensione 0 equivale a non fornire il parametro.
5721!! Avere uno o più descrittori dimensionati con estensione nulla fa sì
5722!! che anche il volume dati successivamente allocato abbia estensione nulla;
5723!! sebbene ciò appaia inutile, un volume del genere può in realtà servire,
5724!! in associazione ai metodi ::vol7d_merge o ::vol7d_append per estendere
5725!! un volume esistente aggiungendo elementi in alcune dimensioni (quelle
5726!! a estensione non nulla, ovviamente) e mantenendo invariato tutto il resto.
5727!! Per quanto riguarda i descrittori delle dimensioni relative alle
5728!! variabili, la relativa estensione è specificata con la nomenclatura
5729!! \a n&lt;x&gt;&lt;y&gt;&lt;z&gt; dove &lt;x&gt; può valere:
5730!! - \a ana per variabili relative a voumi di anagrafica
5731!! - \a dati per variabili relative a voumi di dati
5732!!
5733!! &lt;y&gt; può valere:
5734!! - \a var per variabili
5735!! - \a attr per attributi
5736!! - \a varattr variabili aventi attributi nei volumi di attributi
5737!!
5738!! &lt;z&gt; può valere:
5739!! - \a r per variabili o attributi a valori reali
5740!! - \a d per variabili o attributi a valori a doppia precisione
5741!! - \a i per variabili o attributi a valori interi
5742!! - \a b per variabili o attributi a valori byte
5743!! - \a c per variabili o attributi a valori carattere
5744!!
5745SUBROUTINE vol7d_alloc(this, nana, ntime, nlevel, ntimerange, nnetwork, &
5746 nanavarr, nanavard, nanavari, nanavarb, nanavarc, &
5747 nanaattrr, nanaattrd, nanaattri, nanaattrb, nanaattrc, &
5748 nanavarattrr, nanavarattrd, nanavarattri, nanavarattrb, nanavarattrc, &
5749 ndativarr, ndativard, ndativari, ndativarb, ndativarc, &
5750 ndatiattrr, ndatiattrd, ndatiattri, ndatiattrb, ndatiattrc, &
5751 ndativarattrr, ndativarattrd, ndativarattri, ndativarattrb, ndativarattrc, &
5752 ini)
5753TYPE(vol7d),INTENT(inout) :: this !< oggetto di cui allocare i descrittori
5754INTEGER,INTENT(in),OPTIONAL :: nana !< estensione della dimensione anagrafica
5755INTEGER,INTENT(in),OPTIONAL :: ntime !< estensione della dimensione tempo
5756INTEGER,INTENT(in),OPTIONAL :: nlevel !< estensione della dimensione livello varticale
5757INTEGER,INTENT(in),OPTIONAL :: ntimerange !< estensione della dimensione intervallo temporale (timerange)
5758INTEGER,INTENT(in),OPTIONAL :: nnetwork !< estensione della dimensione rete
5759!> estensione delle possibili dimensioni variabile
5760INTEGER,INTENT(in),OPTIONAL :: &
5761 nanavarr, nanavard, nanavari, nanavarb, nanavarc, &
5762 nanaattrr, nanaattrd, nanaattri, nanaattrb, nanaattrc, &
5763 nanavarattrr, nanavarattrd, nanavarattri, nanavarattrb, nanavarattrc, &
5764 ndativarr, ndativard, ndativari, ndativarb, ndativarc, &
5765 ndatiattrr, ndatiattrd, ndatiattri, ndatiattrb, ndatiattrc, &
5766 ndativarattrr, ndativarattrd, ndativarattri, ndativarattrb, ndativarattrc
5767LOGICAL,INTENT(in),OPTIONAL :: ini !< se fornito e vale \c .TRUE., viene chiamato il costruttore, senza parametri opzionali, per ogni elemento di tutti i descrittori allocati, inizializzandolo quindi a valore mancante
5768
5769INTEGER :: i
5770LOGICAL :: linit
5771
5772IF (PRESENT(ini)) THEN
5773 linit = ini
5774ELSE
5775 linit = .false.
5776ENDIF
5777
5778! Dimensioni principali
5779IF (PRESENT(nana)) THEN
5780 IF (nana >= 0) THEN
5781 IF (ASSOCIATED(this%ana)) DEALLOCATE(this%ana)
5782 ALLOCATE(this%ana(nana))
5783 IF (linit) THEN
5784 DO i = 1, nana
5785 CALL init(this%ana(i))
5786 ENDDO
5787 ENDIF
5788 ENDIF
5789ENDIF
5790IF (PRESENT(ntime)) THEN
5791 IF (ntime >= 0) THEN
5792 IF (ASSOCIATED(this%time)) DEALLOCATE(this%time)
5793 ALLOCATE(this%time(ntime))
5794 IF (linit) THEN
5795 DO i = 1, ntime
5796 CALL init(this%time(i))
5797 ENDDO
5798 ENDIF
5799 ENDIF
5800ENDIF
5801IF (PRESENT(nlevel)) THEN
5802 IF (nlevel >= 0) THEN
5803 IF (ASSOCIATED(this%level)) DEALLOCATE(this%level)
5804 ALLOCATE(this%level(nlevel))
5805 IF (linit) THEN
5806 DO i = 1, nlevel
5807 CALL init(this%level(i))
5808 ENDDO
5809 ENDIF
5810 ENDIF
5811ENDIF
5812IF (PRESENT(ntimerange)) THEN
5813 IF (ntimerange >= 0) THEN
5814 IF (ASSOCIATED(this%timerange)) DEALLOCATE(this%timerange)
5815 ALLOCATE(this%timerange(ntimerange))
5816 IF (linit) THEN
5817 DO i = 1, ntimerange
5818 CALL init(this%timerange(i))
5819 ENDDO
5820 ENDIF
5821 ENDIF
5822ENDIF
5823IF (PRESENT(nnetwork)) THEN
5824 IF (nnetwork >= 0) THEN
5825 IF (ASSOCIATED(this%network)) DEALLOCATE(this%network)
5826 ALLOCATE(this%network(nnetwork))
5827 IF (linit) THEN
5828 DO i = 1, nnetwork
5829 CALL init(this%network(i))
5830 ENDDO
5831 ENDIF
5832 ENDIF
5833ENDIF
5834! Dimensioni dei tipi delle variabili
5835CALL vol7d_varvect_alloc(this%anavar, nanavarr, nanavard, &
5836 nanavari, nanavarb, nanavarc, ini)
5837CALL vol7d_varvect_alloc(this%anaattr, nanaattrr, nanaattrd, &
5838 nanaattri, nanaattrb, nanaattrc, ini)
5839CALL vol7d_varvect_alloc(this%anavarattr, nanavarattrr, nanavarattrd, &
5840 nanavarattri, nanavarattrb, nanavarattrc, ini)
5841CALL vol7d_varvect_alloc(this%dativar, ndativarr, ndativard, &
5842 ndativari, ndativarb, ndativarc, ini)
5843CALL vol7d_varvect_alloc(this%datiattr, ndatiattrr, ndatiattrd, &
5844 ndatiattri, ndatiattrb, ndatiattrc, ini)
5845CALL vol7d_varvect_alloc(this%dativarattr, ndativarattrr, ndativarattrd, &
5846 ndativarattri, ndativarattrb, ndativarattrc, ini)
5847
5848END SUBROUTINE vol7d_alloc
5849
5850
5851FUNCTION vol7d_check_alloc_ana(this)
5852TYPE(vol7d),INTENT(in) :: this
5853LOGICAL :: vol7d_check_alloc_ana
5854
5855vol7d_check_alloc_ana = ASSOCIATED(this%ana) .AND. ASSOCIATED(this%network)
5856
5857END FUNCTION vol7d_check_alloc_ana
5858
5859SUBROUTINE vol7d_force_alloc_ana(this, ini)
5860TYPE(vol7d),INTENT(inout) :: this
5861LOGICAL,INTENT(in),OPTIONAL :: ini
5862
5863! Alloco i descrittori minimi per avere un volume di anagrafica
5864IF (.NOT. ASSOCIATED(this%ana)) CALL vol7d_alloc(this, nana=1, ini=ini)
5865IF (.NOT. ASSOCIATED(this%network)) CALL vol7d_alloc(this, nnetwork=1, ini=ini)
5866
5867END SUBROUTINE vol7d_force_alloc_ana
5868
5869
5870FUNCTION vol7d_check_alloc_dati(this)
5871TYPE(vol7d),INTENT(in) :: this
5872LOGICAL :: vol7d_check_alloc_dati
5873
5874vol7d_check_alloc_dati = vol7d_check_alloc_ana(this) .AND. &
5875 ASSOCIATED(this%time) .AND. ASSOCIATED(this%level) .AND. &
5876 ASSOCIATED(this%timerange)
5877
5878END FUNCTION vol7d_check_alloc_dati
5879
5880SUBROUTINE vol7d_force_alloc_dati(this, ini)
5881TYPE(vol7d),INTENT(inout) :: this
5882LOGICAL,INTENT(in),OPTIONAL :: ini
5883
5884! Alloco i descrittori minimi per avere un volume di dati
5885CALL vol7d_force_alloc_ana(this, ini)
5886IF (.NOT. ASSOCIATED(this%time)) CALL vol7d_alloc(this, ntime=1, ini=ini)
5887IF (.NOT. ASSOCIATED(this%level)) CALL vol7d_alloc(this, nlevel=1, ini=ini)
5888IF (.NOT. ASSOCIATED(this%timerange)) CALL vol7d_alloc(this, ntimerange=1, ini=ini)
5889
5890END SUBROUTINE vol7d_force_alloc_dati
5891
5892
5893SUBROUTINE vol7d_force_alloc(this)
5894TYPE(vol7d),INTENT(inout) :: this
5895
5896! If anything really not allocated yet, allocate with size 0
5897IF (.NOT. ASSOCIATED(this%ana)) CALL vol7d_alloc(this, nana=0)
5898IF (.NOT. ASSOCIATED(this%network)) CALL vol7d_alloc(this, nnetwork=0)
5899IF (.NOT. ASSOCIATED(this%time)) CALL vol7d_alloc(this, ntime=0)
5900IF (.NOT. ASSOCIATED(this%level)) CALL vol7d_alloc(this, nlevel=0)
5901IF (.NOT. ASSOCIATED(this%timerange)) CALL vol7d_alloc(this, ntimerange=0)
5902
5903END SUBROUTINE vol7d_force_alloc
5904
5905
5906FUNCTION vol7d_check_vol(this)
5907TYPE(vol7d),INTENT(in) :: this !< oggetto da controllare
5908LOGICAL :: vol7d_check_vol
5909
5910vol7d_check_vol = c_e(this)
5911
5912! Anagrafica
5913IF (ASSOCIATED(this%anavar%r) .AND. .NOT.ASSOCIATED(this%volanar)) THEN
5914 vol7d_check_vol = .false.
5915ENDIF
5916
5917IF (ASSOCIATED(this%anavar%d) .AND. .NOT.ASSOCIATED(this%volanad)) THEN
5918 vol7d_check_vol = .false.
5919ENDIF
5920
5921IF (ASSOCIATED(this%anavar%i) .AND. .NOT.ASSOCIATED(this%volanai)) THEN
5922 vol7d_check_vol = .false.
5923ENDIF
5924
5925IF (ASSOCIATED(this%anavar%b) .AND. .NOT.ASSOCIATED(this%volanab)) THEN
5926 vol7d_check_vol = .false.
5927ENDIF
5928
5929IF (ASSOCIATED(this%anavar%c) .AND. .NOT.ASSOCIATED(this%volanac)) THEN
5930 vol7d_check_vol = .false.
5931ENDIF
5932IF (ASSOCIATED(this%anavar%r) .OR. ASSOCIATED(this%anavar%d) .OR. &
5933 ASSOCIATED(this%anavar%i) .OR. ASSOCIATED(this%anavar%b) .OR. &
5934 ASSOCIATED(this%anavar%c)) THEN
5935 vol7d_check_vol = vol7d_check_vol .AND. vol7d_check_alloc_ana(this)
5936ENDIF
5937
5938! Attributi dell'anagrafica
5939IF (ASSOCIATED(this%anaattr%r) .AND. ASSOCIATED(this%anavarattr%r) .AND. &
5940 .NOT.ASSOCIATED(this%volanaattrr)) THEN
5941 vol7d_check_vol = .false.
5942ENDIF
5943
5944IF (ASSOCIATED(this%anaattr%d) .AND. ASSOCIATED(this%anavarattr%d) .AND. &
5945 .NOT.ASSOCIATED(this%volanaattrd)) THEN
5946 vol7d_check_vol = .false.
5947ENDIF
5948
5949IF (ASSOCIATED(this%anaattr%i) .AND. ASSOCIATED(this%anavarattr%i) .AND. &
5950 .NOT.ASSOCIATED(this%volanaattri)) THEN
5951 vol7d_check_vol = .false.
5952ENDIF
5953
5954IF (ASSOCIATED(this%anaattr%b) .AND. ASSOCIATED(this%anavarattr%b) .AND. &
5955 .NOT.ASSOCIATED(this%volanaattrb)) THEN
5956 vol7d_check_vol = .false.
5957ENDIF
5958
5959IF (ASSOCIATED(this%anaattr%c) .AND. ASSOCIATED(this%anavarattr%c) .AND. &
5960 .NOT.ASSOCIATED(this%volanaattrc)) THEN
5961 vol7d_check_vol = .false.
5962ENDIF
5963
5964! Dati
5965IF (ASSOCIATED(this%dativar%r) .AND. .NOT.ASSOCIATED(this%voldatir)) THEN
5966 vol7d_check_vol = .false.
5967ENDIF
5968
5969IF (ASSOCIATED(this%dativar%d) .AND. .NOT.ASSOCIATED(this%voldatid)) THEN
5970 vol7d_check_vol = .false.
5971ENDIF
5972
5973IF (ASSOCIATED(this%dativar%i) .AND. .NOT.ASSOCIATED(this%voldatii)) THEN
5974 vol7d_check_vol = .false.
5975ENDIF
5976
5977IF (ASSOCIATED(this%dativar%b) .AND. .NOT.ASSOCIATED(this%voldatib)) THEN
5978 vol7d_check_vol = .false.
5979ENDIF
5980
5981IF (ASSOCIATED(this%dativar%c) .AND. .NOT.ASSOCIATED(this%voldatic)) THEN
5982 vol7d_check_vol = .false.
5983ENDIF
5984
5985! Attributi dei dati
5986IF (ASSOCIATED(this%datiattr%r) .AND. ASSOCIATED(this%dativarattr%r) .AND. &
5987 .NOT.ASSOCIATED(this%voldatiattrr)) THEN
5988 vol7d_check_vol = .false.
5989ENDIF
5990
5991IF (ASSOCIATED(this%datiattr%d) .AND. ASSOCIATED(this%dativarattr%d) .AND. &
5992 .NOT.ASSOCIATED(this%voldatiattrd)) THEN
5993 vol7d_check_vol = .false.
5994ENDIF
5995
5996IF (ASSOCIATED(this%datiattr%i) .AND. ASSOCIATED(this%dativarattr%i) .AND. &
5997 .NOT.ASSOCIATED(this%voldatiattri)) THEN
5998 vol7d_check_vol = .false.
5999ENDIF
6000
6001IF (ASSOCIATED(this%datiattr%b) .AND. ASSOCIATED(this%dativarattr%b) .AND. &
6002 .NOT.ASSOCIATED(this%voldatiattrb)) THEN
6003 vol7d_check_vol = .false.
6004ENDIF
6005
6006IF (ASSOCIATED(this%datiattr%c) .AND. ASSOCIATED(this%dativarattr%c) .AND. &
6007 .NOT.ASSOCIATED(this%voldatiattrc)) THEN
6008 vol7d_check_vol = .false.
6009ENDIF
6010IF (ASSOCIATED(this%dativar%r) .OR. ASSOCIATED(this%dativar%d) .OR. &
6011 ASSOCIATED(this%dativar%i) .OR. ASSOCIATED(this%dativar%b) .OR. &
6012 ASSOCIATED(this%dativar%c)) THEN
6013 vol7d_check_vol = vol7d_check_vol .AND. vol7d_check_alloc_dati(this)
6014ENDIF
6015
6016END FUNCTION vol7d_check_vol
6017
6018
6019!> Metodo per allocare i volumi richiesti di variabili e attributi per
6020!! anagrafica e dati.
6021!! Se alcuni dei descrittori relativi alle dimensioni anagrafica,
6022!! livello verticale, tempo, intervallo temporale (timerange), rete non sono
6023!! stati richiesti preventivamente con la ::vol7d_alloc, essi vengono allocati
6024!! automaticamente da questo metodo
6025!! con estensione di default pari a 1 (non 0!), questo significa, ad esempio,
6026!! che se prevedo di avere soli dati superficiali, cioè ad un solo livello
6027!! verticale, o una sola rete di stazioni, non devo preoccuparmi di
6028!! specificare questa informazione.
6029!! Tra i 20 possibili volumi allocabili
6030!! ((variabili,attributi)*(anagrafica,dati)*(r,d,i,b,c)=20)
6031!! saranno allocati solo quelli per cui è stato precedentemente richiesto il
6032!! corrispondente descrittore variabili/attributi con la ::vol7d_alloc.
6033SUBROUTINE vol7d_alloc_vol(this, ini, inivol)
6034TYPE(vol7d),INTENT(inout) :: this !< oggetto di cui allocare i volumi
6035LOGICAL,INTENT(in),OPTIONAL :: ini !< se fornito e vale \c .TRUE., viene chiamato il costruttore, senza parametri opzionali, per ogni elemento di tutti i descrittori allocati
6036LOGICAL,INTENT(in),OPTIONAL :: inivol !< se fornito e vale \c .TRUE., i volumi allocati saranno inizializzati a valore mancante
6037
6038LOGICAL :: linivol
6039
6040IF (PRESENT(inivol)) THEN
6041 linivol = inivol
6042ELSE
6043 linivol = .true.
6044ENDIF
6045
6046! Anagrafica
6047IF (ASSOCIATED(this%anavar%r) .AND. .NOT.ASSOCIATED(this%volanar)) THEN
6048 CALL vol7d_force_alloc_ana(this, ini)
6049 ALLOCATE(this%volanar(SIZE(this%ana), SIZE(this%anavar%r), SIZE(this%network)))
6050 IF (linivol) this%volanar(:,:,:) = rmiss
6051ENDIF
6052
6053IF (ASSOCIATED(this%anavar%d) .AND. .NOT.ASSOCIATED(this%volanad)) THEN
6054 CALL vol7d_force_alloc_ana(this, ini)
6055 ALLOCATE(this%volanad(SIZE(this%ana), SIZE(this%anavar%d), SIZE(this%network)))
6056 IF (linivol) this%volanad(:,:,:) = rdmiss
6057ENDIF
6058
6059IF (ASSOCIATED(this%anavar%i) .AND. .NOT.ASSOCIATED(this%volanai)) THEN
6060 CALL vol7d_force_alloc_ana(this, ini)
6061 ALLOCATE(this%volanai(SIZE(this%ana), SIZE(this%anavar%i), SIZE(this%network)))
6062 IF (linivol) this%volanai(:,:,:) = imiss
6063ENDIF
6064
6065IF (ASSOCIATED(this%anavar%b) .AND. .NOT.ASSOCIATED(this%volanab)) THEN
6066 CALL vol7d_force_alloc_ana(this, ini)
6067 ALLOCATE(this%volanab(SIZE(this%ana), SIZE(this%anavar%b), SIZE(this%network)))
6068 IF (linivol) this%volanab(:,:,:) = ibmiss
6069ENDIF
6070
6071IF (ASSOCIATED(this%anavar%c) .AND. .NOT.ASSOCIATED(this%volanac)) THEN
6072 CALL vol7d_force_alloc_ana(this, ini)
6073 ALLOCATE(this%volanac(SIZE(this%ana), SIZE(this%anavar%c), SIZE(this%network)))
6074 IF (linivol) this%volanac(:,:,:) = cmiss
6075ENDIF
6076
6077! Attributi dell'anagrafica
6078IF (ASSOCIATED(this%anaattr%r) .AND. ASSOCIATED(this%anavarattr%r) .AND. &
6079 .NOT.ASSOCIATED(this%volanaattrr)) THEN
6080 CALL vol7d_force_alloc_ana(this, ini)
6081 ALLOCATE(this%volanaattrr(SIZE(this%ana), SIZE(this%anavarattr%r), &
6082 SIZE(this%network), SIZE(this%anaattr%r)))
6083 IF (linivol) this%volanaattrr(:,:,:,:) = rmiss
6084ENDIF
6085
6086IF (ASSOCIATED(this%anaattr%d) .AND. ASSOCIATED(this%anavarattr%d) .AND. &
6087 .NOT.ASSOCIATED(this%volanaattrd)) THEN
6088 CALL vol7d_force_alloc_ana(this, ini)
6089 ALLOCATE(this%volanaattrd(SIZE(this%ana), SIZE(this%anavarattr%d), &
6090 SIZE(this%network), SIZE(this%anaattr%d)))
6091 IF (linivol) this%volanaattrd(:,:,:,:) = rdmiss
6092ENDIF
6093
6094IF (ASSOCIATED(this%anaattr%i) .AND. ASSOCIATED(this%anavarattr%i) .AND. &
6095 .NOT.ASSOCIATED(this%volanaattri)) THEN
6096 CALL vol7d_force_alloc_ana(this, ini)
6097 ALLOCATE(this%volanaattri(SIZE(this%ana), SIZE(this%anavarattr%i), &
6098 SIZE(this%network), SIZE(this%anaattr%i)))
6099 IF (linivol) this%volanaattri(:,:,:,:) = imiss
6100ENDIF
6101
6102IF (ASSOCIATED(this%anaattr%b) .AND. ASSOCIATED(this%anavarattr%b) .AND. &
6103 .NOT.ASSOCIATED(this%volanaattrb)) THEN
6104 CALL vol7d_force_alloc_ana(this, ini)
6105 ALLOCATE(this%volanaattrb(SIZE(this%ana), SIZE(this%anavarattr%b), &
6106 SIZE(this%network), SIZE(this%anaattr%b)))
6107 IF (linivol) this%volanaattrb(:,:,:,:) = ibmiss
6108ENDIF
6109
6110IF (ASSOCIATED(this%anaattr%c) .AND. ASSOCIATED(this%anavarattr%c) .AND. &
6111 .NOT.ASSOCIATED(this%volanaattrc)) THEN
6112 CALL vol7d_force_alloc_ana(this, ini)
6113 ALLOCATE(this%volanaattrc(SIZE(this%ana), SIZE(this%anavarattr%c), &
6114 SIZE(this%network), SIZE(this%anaattr%c)))
6115 IF (linivol) this%volanaattrc(:,:,:,:) = cmiss
6116ENDIF
6117
6118! Dati
6119IF (ASSOCIATED(this%dativar%r) .AND. .NOT.ASSOCIATED(this%voldatir)) THEN
6120 CALL vol7d_force_alloc_dati(this, ini)
6121 ALLOCATE(this%voldatir(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
6122 SIZE(this%timerange), SIZE(this%dativar%r), SIZE(this%network)))
6123 IF (linivol) this%voldatir(:,:,:,:,:,:) = rmiss
6124ENDIF
6125
6126IF (ASSOCIATED(this%dativar%d) .AND. .NOT.ASSOCIATED(this%voldatid)) THEN
6127 CALL vol7d_force_alloc_dati(this, ini)
6128 ALLOCATE(this%voldatid(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
6129 SIZE(this%timerange), SIZE(this%dativar%d), SIZE(this%network)))
6130 IF (linivol) this%voldatid(:,:,:,:,:,:) = rdmiss
6131ENDIF
6132
6133IF (ASSOCIATED(this%dativar%i) .AND. .NOT.ASSOCIATED(this%voldatii)) THEN
6134 CALL vol7d_force_alloc_dati(this, ini)
6135 ALLOCATE(this%voldatii(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
6136 SIZE(this%timerange), SIZE(this%dativar%i), SIZE(this%network)))
6137 IF (linivol) this%voldatii(:,:,:,:,:,:) = imiss
6138ENDIF
6139
6140IF (ASSOCIATED(this%dativar%b) .AND. .NOT.ASSOCIATED(this%voldatib)) THEN
6141 CALL vol7d_force_alloc_dati(this, ini)
6142 ALLOCATE(this%voldatib(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
6143 SIZE(this%timerange), SIZE(this%dativar%b), SIZE(this%network)))
6144 IF (linivol) this%voldatib(:,:,:,:,:,:) = ibmiss
6145ENDIF
6146
6147IF (ASSOCIATED(this%dativar%c) .AND. .NOT.ASSOCIATED(this%voldatic)) THEN
6148 CALL vol7d_force_alloc_dati(this, ini)
6149 ALLOCATE(this%voldatic(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
6150 SIZE(this%timerange), SIZE(this%dativar%c), SIZE(this%network)))
6151 IF (linivol) this%voldatic(:,:,:,:,:,:) = cmiss
6152ENDIF
6153
6154! Attributi dei dati
6155IF (ASSOCIATED(this%datiattr%r) .AND. ASSOCIATED(this%dativarattr%r) .AND. &
6156 .NOT.ASSOCIATED(this%voldatiattrr)) THEN
6157 CALL vol7d_force_alloc_dati(this, ini)
6158 ALLOCATE(this%voldatiattrr(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
6159 SIZE(this%timerange), SIZE(this%dativarattr%r), SIZE(this%network), &
6160 SIZE(this%datiattr%r)))
6161 IF (linivol) this%voldatiattrr(:,:,:,:,:,:,:) = rmiss
6162ENDIF
6163
6164IF (ASSOCIATED(this%datiattr%d) .AND. ASSOCIATED(this%dativarattr%d) .AND. &
6165 .NOT.ASSOCIATED(this%voldatiattrd)) THEN
6166 CALL vol7d_force_alloc_dati(this, ini)
6167 ALLOCATE(this%voldatiattrd(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
6168 SIZE(this%timerange), SIZE(this%dativarattr%d), SIZE(this%network), &
6169 SIZE(this%datiattr%d)))
6170 IF (linivol) this%voldatiattrd(:,:,:,:,:,:,:) = rdmiss
6171ENDIF
6172
6173IF (ASSOCIATED(this%datiattr%i) .AND. ASSOCIATED(this%dativarattr%i) .AND. &
6174 .NOT.ASSOCIATED(this%voldatiattri)) THEN
6175 CALL vol7d_force_alloc_dati(this, ini)
6176 ALLOCATE(this%voldatiattri(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
6177 SIZE(this%timerange), SIZE(this%dativarattr%i), SIZE(this%network), &
6178 SIZE(this%datiattr%i)))
6179 IF (linivol) this%voldatiattri(:,:,:,:,:,:,:) = imiss
6180ENDIF
6181
6182IF (ASSOCIATED(this%datiattr%b) .AND. ASSOCIATED(this%dativarattr%b) .AND. &
6183 .NOT.ASSOCIATED(this%voldatiattrb)) THEN
6184 CALL vol7d_force_alloc_dati(this, ini)
6185 ALLOCATE(this%voldatiattrb(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
6186 SIZE(this%timerange), SIZE(this%dativarattr%b), SIZE(this%network), &
6187 SIZE(this%datiattr%b)))
6188 IF (linivol) this%voldatiattrb(:,:,:,:,:,:,:) = ibmiss
6189ENDIF
6190
6191IF (ASSOCIATED(this%datiattr%c) .AND. ASSOCIATED(this%dativarattr%c) .AND. &
6192 .NOT.ASSOCIATED(this%voldatiattrc)) THEN
6193 CALL vol7d_force_alloc_dati(this, ini)
6194 ALLOCATE(this%voldatiattrc(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
6195 SIZE(this%timerange), SIZE(this%dativarattr%c), SIZE(this%network), &
6196 SIZE(this%datiattr%c)))
6197 IF (linivol) this%voldatiattrc(:,:,:,:,:,:,:) = cmiss
6198ENDIF
6199
6200! Catch-all method
6201CALL vol7d_force_alloc(this)
6202
6203! Creo gli indici var-attr
6204
6205#ifdef DEBUG
6206CALL l4f_log(l4f_debug,"calling: vol7d_set_attr_ind")
6207#endif
6208
6209CALL vol7d_set_attr_ind(this)
6210
6211
6212
6213END SUBROUTINE vol7d_alloc_vol
6214
6215
6216!> Metodo per creare gli indici che associano le variabili aventi attributo
6217!! alle variabili nei relativi descrittori.
6218!! Ha senso chiamare questo metodo solo dopo che i descrittori delle variabili
6219!! e degli attributi desiderati sono stati allocati ed è stato assegnato un
6220!! valore ai relativi membri btable (vedi vol7d_var_class::vol7d_var), se
6221!! i descrittori non sono stati allocati o assegnati, il metodo non fa niente.
6222SUBROUTINE vol7d_set_attr_ind(this)
6223TYPE(vol7d),INTENT(inout) :: this !< oggetto in cui creare gli indici
6224
6225INTEGER :: i
6226
6227! real
6228IF (ASSOCIATED(this%dativar%r)) THEN
6229 IF (ASSOCIATED(this%dativarattr%r)) THEN
6230 DO i = 1, SIZE(this%dativar%r)
6231 this%dativar%r(i)%r = &
6232 firsttrue(this%dativar%r(i)%btable == this%dativarattr%r(:)%btable)
6233 ENDDO
6234 ENDIF
6235
6236 IF (ASSOCIATED(this%dativarattr%d)) THEN
6237 DO i = 1, SIZE(this%dativar%r)
6238 this%dativar%r(i)%d = &
6239 firsttrue(this%dativar%r(i)%btable == this%dativarattr%d(:)%btable)
6240 ENDDO
6241 ENDIF
6242
6243 IF (ASSOCIATED(this%dativarattr%i)) THEN
6244 DO i = 1, SIZE(this%dativar%r)
6245 this%dativar%r(i)%i = &
6246 firsttrue(this%dativar%r(i)%btable == this%dativarattr%i(:)%btable)
6247 ENDDO
6248 ENDIF
6249
6250 IF (ASSOCIATED(this%dativarattr%b)) THEN
6251 DO i = 1, SIZE(this%dativar%r)
6252 this%dativar%r(i)%b = &
6253 firsttrue(this%dativar%r(i)%btable == this%dativarattr%b(:)%btable)
6254 ENDDO
6255 ENDIF
6256
6257 IF (ASSOCIATED(this%dativarattr%c)) THEN
6258 DO i = 1, SIZE(this%dativar%r)
6259 this%dativar%r(i)%c = &
6260 firsttrue(this%dativar%r(i)%btable == this%dativarattr%c(:)%btable)
6261 ENDDO
6262 ENDIF
6263ENDIF
6264! double
6265IF (ASSOCIATED(this%dativar%d)) THEN
6266 IF (ASSOCIATED(this%dativarattr%r)) THEN
6267 DO i = 1, SIZE(this%dativar%d)
6268 this%dativar%d(i)%r = &
6269 firsttrue(this%dativar%d(i)%btable == this%dativarattr%r(:)%btable)
6270 ENDDO
6271 ENDIF
6272
6273 IF (ASSOCIATED(this%dativarattr%d)) THEN
6274 DO i = 1, SIZE(this%dativar%d)
6275 this%dativar%d(i)%d = &
6276 firsttrue(this%dativar%d(i)%btable == this%dativarattr%d(:)%btable)
6277 ENDDO
6278 ENDIF
6279
6280 IF (ASSOCIATED(this%dativarattr%i)) THEN
6281 DO i = 1, SIZE(this%dativar%d)
6282 this%dativar%d(i)%i = &
6283 firsttrue(this%dativar%d(i)%btable == this%dativarattr%i(:)%btable)
6284 ENDDO
6285 ENDIF
6286
6287 IF (ASSOCIATED(this%dativarattr%b)) THEN
6288 DO i = 1, SIZE(this%dativar%d)
6289 this%dativar%d(i)%b = &
6290 firsttrue(this%dativar%d(i)%btable == this%dativarattr%b(:)%btable)
6291 ENDDO
6292 ENDIF
6293
6294 IF (ASSOCIATED(this%dativarattr%c)) THEN
6295 DO i = 1, SIZE(this%dativar%d)
6296 this%dativar%d(i)%c = &
6297 firsttrue(this%dativar%d(i)%btable == this%dativarattr%c(:)%btable)
6298 ENDDO
6299 ENDIF
6300ENDIF
6301! integer
6302IF (ASSOCIATED(this%dativar%i)) THEN
6303 IF (ASSOCIATED(this%dativarattr%r)) THEN
6304 DO i = 1, SIZE(this%dativar%i)
6305 this%dativar%i(i)%r = &
6306 firsttrue(this%dativar%i(i)%btable == this%dativarattr%r(:)%btable)
6307 ENDDO
6308 ENDIF
6309
6310 IF (ASSOCIATED(this%dativarattr%d)) THEN
6311 DO i = 1, SIZE(this%dativar%i)
6312 this%dativar%i(i)%d = &
6313 firsttrue(this%dativar%i(i)%btable == this%dativarattr%d(:)%btable)
6314 ENDDO
6315 ENDIF
6316
6317 IF (ASSOCIATED(this%dativarattr%i)) THEN
6318 DO i = 1, SIZE(this%dativar%i)
6319 this%dativar%i(i)%i = &
6320 firsttrue(this%dativar%i(i)%btable == this%dativarattr%i(:)%btable)
6321 ENDDO
6322 ENDIF
6323
6324 IF (ASSOCIATED(this%dativarattr%b)) THEN
6325 DO i = 1, SIZE(this%dativar%i)
6326 this%dativar%i(i)%b = &
6327 firsttrue(this%dativar%i(i)%btable == this%dativarattr%b(:)%btable)
6328 ENDDO
6329 ENDIF
6330
6331 IF (ASSOCIATED(this%dativarattr%c)) THEN
6332 DO i = 1, SIZE(this%dativar%i)
6333 this%dativar%i(i)%c = &
6334 firsttrue(this%dativar%i(i)%btable == this%dativarattr%c(:)%btable)
6335 ENDDO
6336 ENDIF
6337ENDIF
6338! byte
6339IF (ASSOCIATED(this%dativar%b)) THEN
6340 IF (ASSOCIATED(this%dativarattr%r)) THEN
6341 DO i = 1, SIZE(this%dativar%b)
6342 this%dativar%b(i)%r = &
6343 firsttrue(this%dativar%b(i)%btable == this%dativarattr%r(:)%btable)
6344 ENDDO
6345 ENDIF
6346
6347 IF (ASSOCIATED(this%dativarattr%d)) THEN
6348 DO i = 1, SIZE(this%dativar%b)
6349 this%dativar%b(i)%d = &
6350 firsttrue(this%dativar%b(i)%btable == this%dativarattr%d(:)%btable)
6351 ENDDO
6352 ENDIF
6353
6354 IF (ASSOCIATED(this%dativarattr%i)) THEN
6355 DO i = 1, SIZE(this%dativar%b)
6356 this%dativar%b(i)%i = &
6357 firsttrue(this%dativar%b(i)%btable == this%dativarattr%i(:)%btable)
6358 ENDDO
6359 ENDIF
6360
6361 IF (ASSOCIATED(this%dativarattr%b)) THEN
6362 DO i = 1, SIZE(this%dativar%b)
6363 this%dativar%b(i)%b = &
6364 firsttrue(this%dativar%b(i)%btable == this%dativarattr%b(:)%btable)
6365 ENDDO
6366 ENDIF
6367
6368 IF (ASSOCIATED(this%dativarattr%c)) THEN
6369 DO i = 1, SIZE(this%dativar%b)
6370 this%dativar%b(i)%c = &
6371 firsttrue(this%dativar%b(i)%btable == this%dativarattr%c(:)%btable)
6372 ENDDO
6373 ENDIF
6374ENDIF
6375! character
6376IF (ASSOCIATED(this%dativar%c)) THEN
6377 IF (ASSOCIATED(this%dativarattr%r)) THEN
6378 DO i = 1, SIZE(this%dativar%c)
6379 this%dativar%c(i)%r = &
6380 firsttrue(this%dativar%c(i)%btable == this%dativarattr%r(:)%btable)
6381 ENDDO
6382 ENDIF
6383
6384 IF (ASSOCIATED(this%dativarattr%d)) THEN
6385 DO i = 1, SIZE(this%dativar%c)
6386 this%dativar%c(i)%d = &
6387 firsttrue(this%dativar%c(i)%btable == this%dativarattr%d(:)%btable)
6388 ENDDO
6389 ENDIF
6390
6391 IF (ASSOCIATED(this%dativarattr%i)) THEN
6392 DO i = 1, SIZE(this%dativar%c)
6393 this%dativar%c(i)%i = &
6394 firsttrue(this%dativar%c(i)%btable == this%dativarattr%i(:)%btable)
6395 ENDDO
6396 ENDIF
6397
6398 IF (ASSOCIATED(this%dativarattr%b)) THEN
6399 DO i = 1, SIZE(this%dativar%c)
6400 this%dativar%c(i)%b = &
6401 firsttrue(this%dativar%c(i)%btable == this%dativarattr%b(:)%btable)
6402 ENDDO
6403 ENDIF
6404
6405 IF (ASSOCIATED(this%dativarattr%c)) THEN
6406 DO i = 1, SIZE(this%dativar%c)
6407 this%dativar%c(i)%c = &
6408 firsttrue(this%dativar%c(i)%btable == this%dativarattr%c(:)%btable)
6409 ENDDO
6410 ENDIF
6411ENDIF
6412
6413END SUBROUTINE vol7d_set_attr_ind
6414
6415
6416!> Metodo per fondere 2 oggetti vol7d.
6417!! Il secondo volume viene accodato al primo e poi distrutto, si veda
6418!! quindi la descrizione di ::vol7d_append. Se uno degli oggetti \a
6419!! this o \a that sono vuoti non perde tempo inutile,
6420SUBROUTINE vol7d_merge(this, that, sort, bestdata, &
6421 ltimesimple, ltimerangesimple, llevelsimple, lanasimple)
6422TYPE(vol7d),INTENT(INOUT) :: this !< primo oggetto in ingresso, alla fine conterrà il risultato della fusione
6423TYPE(vol7d),INTENT(INOUT) :: that !< secondo oggetto in ingresso, alla fine sarà distrutto
6424LOGICAL,INTENT(IN),OPTIONAL :: sort !< se fornito e uguale a \c .TRUE., i descrittori che supportano un ordinamento (operatori > e/o <) risulteranno ordinati in ordine crescente nell'oggetto finale
6425LOGICAL,INTENT(in),OPTIONAL :: bestdata !< if provided and \a .TRUE. in case of overlapping volumes keep valid data where available, or data from the second volume if both valid
6426LOGICAL,INTENT(IN),OPTIONAL :: ltimesimple, ltimerangesimple, llevelsimple, lanasimple ! experimental, please do not use outside the library now
6427
6428TYPE(vol7d) :: v7d_clean
6429
6430
6431IF (.NOT.c_e(this)) THEN ! speedup
6432 this = that
6433 CALL init(v7d_clean)
6434 that = v7d_clean ! destroy that without deallocating
6435ELSE ! Append that to this and destroy that
6436 CALL vol7d_append(this, that, sort, bestdata, &
6437 ltimesimple, ltimerangesimple, llevelsimple, lanasimple)
6438 CALL delete(that)
6439ENDIF
6440
6441END SUBROUTINE vol7d_merge
6442
6443
6444!> Metodo per accodare un oggetto vol7d ad un altro.
6445!! Si tratta di un metodo molto potente e versatile;
6446!! i descrittori delle dimensioni del volume finale conterranno i valori
6447!! dei corrispondenti descrittori del primo e del secondo volume
6448!! e i volumi di anagrafica e dati conterranno i valori dei due volumi
6449!! ai posti giusti, e valori mancanti per le nuove combinazioni che
6450!! eventualmente si verranno a creare.
6451!! Se i volumi multidimensionali di anagrafica e/o dati dei 2 oggetti
6452!! hanno un'intersezione non nulla, negli elementi comuni il volume finale
6453!! conterrà il corrispondente elemento del \b secondo volume.
6454!! Attenzione che, durante l'esecuzione del metodo, la memoria richiesta è
6455!! pari alla memoria complessiva occupata dai 2 volumi iniziali più
6456!! la memoria complessiva del volume finale, per cui, nel caso di volumi grandi,
6457!! ci potrebbero essere problemi di esaurimento della memoria centrale.
6458!! Se l'oggetto \a that è vuoto non perde tempo inutile,
6459!!
6460!! \todo nel caso di elementi comuni inserire la possibiità (opzionale per
6461!! non penalizzare le prestazioni quando ciò non serve) di effettuare una scelta
6462!! più ragionata dell'elemento da tenere, almeno controllando i dati mancanti
6463!! se non le flag di qualità
6464!!
6465!! \todo "rateizzare" l'allocazione dei volumi per ridurre l'occupazione di
6466!! memoria nel caso siano allocati contemporaneamente volumi di variabili e
6467!! di attributi o più volumi di tipi diversi
6468!!
6469!! \todo il parametro \a that è dichiarato \a INOUT perché la vol7d_alloc_vol
6470!! può modificarlo, bisognerebbe implementare una vol7d_check_vol che restituisca
6471!! errore anziché usare la vol7d_alloc_vol.
6472SUBROUTINE vol7d_append(this, that, sort, bestdata, &
6473 ltimesimple, ltimerangesimple, llevelsimple, lanasimple, lnetworksimple)
6474TYPE(vol7d),INTENT(INOUT) :: this !< primo oggetto in ingresso, a cui sarà accodato il secondo
6475TYPE(vol7d),INTENT(IN) :: that !< secondo oggetto in ingresso, non viene modificato dal metodo
6476LOGICAL,INTENT(IN),OPTIONAL :: sort !< se fornito e uguale a \c .TRUE., i descrittori che supportano un ordinamento (operatori > e/o <) risulteranno ordinati in ordine crescente nell'oggetto finale
6477! experimental, please do not use outside the library now, they force the use
6478! of a simplified mapping algorithm which is valid only whene the dimension
6479! content is the same in both volumes , or when one of them is empty
6480LOGICAL,INTENT(in),OPTIONAL :: bestdata !< if provided and \a .TRUE. in case of overlapping volumes keep valid data where available, or data from the second volume if both valid
6481LOGICAL,INTENT(IN),OPTIONAL :: ltimesimple, ltimerangesimple, llevelsimple, lanasimple, lnetworksimple
6482
6483
6484TYPE(vol7d) :: v7dtmp
6485LOGICAL :: lsort, lbestdata
6486INTEGER,POINTER :: remapt1(:), remapt2(:), remaptr1(:), remaptr2(:), &
6487 remapl1(:), remapl2(:), remapa1(:), remapa2(:), remapn1(:), remapn2(:)
6488
6489IF (.NOT.c_e(that)) RETURN ! speedup, nothing to do
6490IF (.NOT.vol7d_check_vol(that)) RETURN ! be safe
6491IF (.NOT.c_e(this)) THEN ! this case is like a vol7d_copy, more efficient to copy?
6492 CALL vol7d_copy(that, this, sort=sort)
6493 RETURN
6494ENDIF
6495
6496IF (this%time_definition /= that%time_definition) THEN
6497 CALL l4f_log(l4f_fatal, &
6498 'in vol7d_append, cannot append volumes with different &
6499 &time definition')
6500 CALL raise_fatal_error()
6501ENDIF
6502
6503! Completo l'allocazione per avere volumi a norma
6504CALL vol7d_alloc_vol(this)
6505
6506CALL init(v7dtmp, time_definition=this%time_definition)
6507CALL optio(sort, lsort)
6508CALL optio(bestdata, lbestdata)
6509
6510! Calcolo le mappature tra volumi vecchi e volume nuovo
6511! I puntatori remap* vengono tutti o allocati o nullificati
6512IF (optio_log(ltimesimple)) THEN
6513 CALL vol7d_remap2simple_datetime(this%time, that%time, v7dtmp%time, &
6514 lsort, remapt1, remapt2)
6515ELSE
6516 CALL vol7d_remap2_datetime(this%time, that%time, v7dtmp%time, &
6517 lsort, remapt1, remapt2)
6518ENDIF
6519IF (optio_log(ltimerangesimple)) THEN
6520 CALL vol7d_remap2simple_vol7d_timerange(this%timerange, that%timerange, &
6521 v7dtmp%timerange, lsort, remaptr1, remaptr2)
6522ELSE
6523 CALL vol7d_remap2_vol7d_timerange(this%timerange, that%timerange, &
6524 v7dtmp%timerange, lsort, remaptr1, remaptr2)
6525ENDIF
6526IF (optio_log(llevelsimple)) THEN
6527 CALL vol7d_remap2simple_vol7d_level(this%level, that%level, v7dtmp%level, &
6528 lsort, remapl1, remapl2)
6529ELSE
6530 CALL vol7d_remap2_vol7d_level(this%level, that%level, v7dtmp%level, &
6531 lsort, remapl1, remapl2)
6532ENDIF
6533IF (optio_log(lanasimple)) THEN
6534 CALL vol7d_remap2simple_vol7d_ana(this%ana, that%ana, v7dtmp%ana, &
6535 .false., remapa1, remapa2)
6536ELSE
6537 CALL vol7d_remap2_vol7d_ana(this%ana, that%ana, v7dtmp%ana, &
6538 .false., remapa1, remapa2)
6539ENDIF
6540IF (optio_log(lnetworksimple)) THEN
6541 CALL vol7d_remap2simple_vol7d_network(this%network, that%network, v7dtmp%network, &
6542 .false., remapn1, remapn2)
6543ELSE
6544 CALL vol7d_remap2_vol7d_network(this%network, that%network, v7dtmp%network, &
6545 .false., remapn1, remapn2)
6546ENDIF
6547
6548! Faccio la fusione fisica dei volumi
6549CALL vol7d_merge_finalr(this, that, v7dtmp, &
6550 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
6551 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
6552CALL vol7d_merge_finald(this, that, v7dtmp, &
6553 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
6554 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
6555CALL vol7d_merge_finali(this, that, v7dtmp, &
6556 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
6557 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
6558CALL vol7d_merge_finalb(this, that, v7dtmp, &
6559 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
6560 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
6561CALL vol7d_merge_finalc(this, that, v7dtmp, &
6562 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
6563 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
6564
6565! Dealloco i vettori di rimappatura
6566IF (ASSOCIATED(remapt1)) DEALLOCATE(remapt1)
6567IF (ASSOCIATED(remapt2)) DEALLOCATE(remapt2)
6568IF (ASSOCIATED(remaptr1)) DEALLOCATE(remaptr1)
6569IF (ASSOCIATED(remaptr2)) DEALLOCATE(remaptr2)
6570IF (ASSOCIATED(remapl1)) DEALLOCATE(remapl1)
6571IF (ASSOCIATED(remapl2)) DEALLOCATE(remapl2)
6572IF (ASSOCIATED(remapa1)) DEALLOCATE(remapa1)
6573IF (ASSOCIATED(remapa2)) DEALLOCATE(remapa2)
6574IF (ASSOCIATED(remapn1)) DEALLOCATE(remapn1)
6575IF (ASSOCIATED(remapn2)) DEALLOCATE(remapn2)
6576
6577! Distruggo il vecchio volume e assegno il nuovo a this
6578CALL delete(this)
6579this = v7dtmp
6580! Ricreo gli indici var-attr
6581CALL vol7d_set_attr_ind(this)
6582
6583END SUBROUTINE vol7d_append
6584
6585
6586!> Metodo per creare una copia completa e indipendente di un oggetto vol7d.
6587!! Questo metodo crea un duplicato di tutti i membri di un oggetto vol7d,
6588!! con la possibilità di rielaborarlo durante la copia. Se l'oggetto da copiare
6589!! è vuoto non perde tempo inutile.
6590!! Attenzione, il codice:
6591!! \code
6592!! USE vol7d_class
6593!! TYPE(vol7d) :: vol1, vol2
6594!! CALL init(vol1)
6595!! CALL init(vol2)
6596!! ... ! riempio vol1
6597!! vol2 = vol1
6598!! \endcode
6599!! fa una cosa diversa rispetto a:
6600!! \code
6601!! USE vol7d_class
6602!! TYPE(vol7d) :: vol1, vol2
6603!! CALL init(vol1)
6604!! CALL init(vol2)
6605!! ... ! riempio vol1
6606!! CALL vol7d_copy(vol1, vol2)
6607!! \endcode
6608!! nel primo caso, infatti, l'operatore di assegnazione copia solo i componenti
6609!! statici di \a vol1 nei corrispondenti elementi di \a vol2, mentre i componenti che
6610!! sono allocati dinamicamente (cioè quelli che in ::vol7d hanno l'attributo
6611!! \c POINTER, in pratica quasi tutti) non vengono duplicati, ma per essi vol2
6612!! conterrà un puntatore al corrispondente elemento a cui già punta vol1, e quindi
6613!! eventuali cambiamenti al contenuto di uno dei due oggetti influenzerà il
6614!! contenuto dell'altro; nel secondo caso, invece, vol1 e vol2 sono, dopo la
6615!! vol7d_copy, 2 istanze
6616!! completamente indipendenti, ma uguali tra loro per contenuto, della classe
6617!! vol7d, e quindi hanno vita indipendente.
6618SUBROUTINE vol7d_copy(this, that, sort, unique, miss, &
6619 lsort_time, lsort_timerange, lsort_level, &
6620 ltime, ltimerange, llevel, lana, lnetwork, &
6621 lanavarr, lanavard, lanavari, lanavarb, lanavarc, &
6622 lanaattrr, lanaattrd, lanaattri, lanaattrb, lanaattrc, &
6623 lanavarattrr, lanavarattrd, lanavarattri, lanavarattrb, lanavarattrc, &
6624 ldativarr, ldativard, ldativari, ldativarb, ldativarc, &
6625 ldatiattrr, ldatiattrd, ldatiattri, ldatiattrb, ldatiattrc, &
6626 ldativarattrr, ldativarattrd, ldativarattri, ldativarattrb, ldativarattrc)
6627TYPE(vol7d),INTENT(IN) :: this !< oggetto origine
6628TYPE(vol7d),INTENT(INOUT) :: that !< oggetto destinazione
6629LOGICAL,INTENT(IN),OPTIONAL :: sort !< if present and \a .TRUE., sort all the sortable dimensions
6630LOGICAL,INTENT(IN),OPTIONAL :: unique !< se fornito e uguale a \c .TRUE., gli eventuali elementi duplicati nei descrittori dell'oggetto iniziale verranno collassati in un unico elemento (con eventuale perdita dei dati relativi agli elementi duplicati)
6631LOGICAL,INTENT(IN),OPTIONAL :: miss !< se fornito e uguale a \c .TRUE., gli eventuali elementi dei descrittori uguali al corrispondente valore mancante verranno eliminati dall'oggetto riformato
6632LOGICAL,INTENT(IN),OPTIONAL :: lsort_time !< if present and \a .TRUE., sort only time dimension (alternative to \a sort )
6633LOGICAL,INTENT(IN),OPTIONAL :: lsort_timerange !< if present and \a .TRUE., sort only timerange dimension (alternative to \a sort )
6634LOGICAL,INTENT(IN),OPTIONAL :: lsort_level !< if present and \a .TRUE., sort only level dimension (alternative to \a sort )
6635!> se fornito, deve essere un vettore logico della stessa lunghezza di
6636!! this%time indicante quali elementi della dimensione \a time
6637!! mantenere (valori \c .TRUE.) e quali scartare (valori \c .FALSE.)
6638!! nel volume copiato; in alternativa può essere un vettore di
6639!! lunghezza 1, in tal caso, se \c .FALSE. , equivale a scartare tutti
6640!! gli elementi (utile principalmente per le variabili); è compatibile
6641!! col parametro \a miss
6642LOGICAL,INTENT(IN),OPTIONAL :: ltime(:)
6643!> come il precedente per la dimensione \a timerange
6644LOGICAL,INTENT(IN),OPTIONAL :: ltimerange(:)
6645!> come il precedente per la dimensione \a level
6646LOGICAL,INTENT(IN),OPTIONAL :: llevel(:)
6647!> come il precedente per la dimensione \a ana
6648LOGICAL,INTENT(IN),OPTIONAL :: lana(:)
6649!> come il precedente per la dimensione \a network
6650LOGICAL,INTENT(IN),OPTIONAL :: lnetwork(:)
6651!> come il precedente per tutte le possibili dimensioni variabile
6652LOGICAL,INTENT(in),OPTIONAL :: &
6653 lanavarr(:), lanavard(:), lanavari(:), lanavarb(:), lanavarc(:), &
6654 lanaattrr(:), lanaattrd(:), lanaattri(:), lanaattrb(:), lanaattrc(:), &
6655 lanavarattrr(:), lanavarattrd(:), lanavarattri(:), lanavarattrb(:), lanavarattrc(:), &
6656 ldativarr(:), ldativard(:), ldativari(:), ldativarb(:), ldativarc(:), &
6657 ldatiattrr(:), ldatiattrd(:), ldatiattri(:), ldatiattrb(:), ldatiattrc(:), &
6658 ldativarattrr(:), ldativarattrd(:), ldativarattri(:), ldativarattrb(:), ldativarattrc(:)
6659
6660LOGICAL :: lsort, lunique, lmiss
6661INTEGER,POINTER :: remapt(:), remaptr(:), remapl(:), remapa(:), remapn(:)
6662
6663CALL init(that)
6664IF (.NOT.c_e(this)) RETURN ! speedup, nothing to do
6665IF (.NOT.vol7d_check_vol(this)) RETURN ! be safe
6666
6667CALL optio(sort, lsort)
6668CALL optio(unique, lunique)
6669CALL optio(miss, lmiss)
6670
6671! Calcolo le mappature tra volume vecchio e volume nuovo
6672! I puntatori remap* vengono tutti o allocati o nullificati
6673CALL vol7d_remap1_datetime(this%time, that%time, &
6674 lsort.OR.optio_log(lsort_time), lunique, lmiss, remapt, ltime)
6675CALL vol7d_remap1_vol7d_timerange(this%timerange, that%timerange, &
6676 lsort.OR.optio_log(lsort_timerange), lunique, lmiss, remaptr, ltimerange)
6677CALL vol7d_remap1_vol7d_level(this%level, that%level, &
6678 lsort.OR.optio_log(lsort_level), lunique, lmiss, remapl, llevel)
6679CALL vol7d_remap1_vol7d_ana(this%ana, that%ana, &
6680 lsort, lunique, lmiss, remapa, lana)
6681CALL vol7d_remap1_vol7d_network(this%network, that%network, &
6682 lsort, lunique, lmiss, remapn, lnetwork)
6683
6684! lanavari, lanavarb, lanavarc, &
6685! lanaattri, lanaattrb, lanaattrc, &
6686! lanavarattri, lanavarattrb, lanavarattrc, &
6687! ldativari, ldativarb, ldativarc, &
6688! ldatiattri, ldatiattrb, ldatiattrc, &
6689! ldativarattri, ldativarattrb, ldativarattrc
6690! Faccio la riforma fisica dei volumi
6691CALL vol7d_reform_finalr(this, that, &
6692 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
6693 lanavarr, lanaattrr, lanavarattrr, ldativarr, ldatiattrr, ldativarattrr)
6694CALL vol7d_reform_finald(this, that, &
6695 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
6696 lanavard, lanaattrd, lanavarattrd, ldativard, ldatiattrd, ldativarattrd)
6697CALL vol7d_reform_finali(this, that, &
6698 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
6699 lanavari, lanaattri, lanavarattri, ldativari, ldatiattri, ldativarattri)
6700CALL vol7d_reform_finalb(this, that, &
6701 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
6702 lanavarb, lanaattrb, lanavarattrb, ldativarb, ldatiattrb, ldativarattrb)
6703CALL vol7d_reform_finalc(this, that, &
6704 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
6705 lanavarc, lanaattrc, lanavarattrc, ldativarc, ldatiattrc, ldativarattrc)
6706
6707! Dealloco i vettori di rimappatura
6708IF (ASSOCIATED(remapt)) DEALLOCATE(remapt)
6709IF (ASSOCIATED(remaptr)) DEALLOCATE(remaptr)
6710IF (ASSOCIATED(remapl)) DEALLOCATE(remapl)
6711IF (ASSOCIATED(remapa)) DEALLOCATE(remapa)
6712IF (ASSOCIATED(remapn)) DEALLOCATE(remapn)
6713
6714! Ricreo gli indici var-attr
6715CALL vol7d_set_attr_ind(that)
6716that%time_definition = this%time_definition
6717
6718END SUBROUTINE vol7d_copy
6719
6720
6721!> Metodo per riformare in varie maniere un oggetto vol7d.
6722!! Equivale ad una copia (vedi ::vol7d_copy)
6723!! seguita dalla distruzione del volume iniziale e alla
6724!! sua riassegnazione al volume copiato. Ha senso se almeno uno dei parametri
6725!! \a sort, \a uniq o \a miss è fornito uguale a \c .TRUE., altrimenti
6726!! è solo una perdita di tempo.
6727!! Può essere utile, ad esempio, per eliminare stazioni
6728!! o istanti temporali indesiderati, basta assegnare il loro corrispondente
6729!! elemento del descrittore a valore mancante e chiamare vol7d_reform
6730!! con miss=.TRUE. .
6731SUBROUTINE vol7d_reform(this, sort, unique, miss, &
6732 lsort_time, lsort_timerange, lsort_level, &
6733 ltime, ltimerange, llevel, lana, lnetwork, &
6734 lanavarr, lanavard, lanavari, lanavarb, lanavarc, &
6735 lanaattrr, lanaattrd, lanaattri, lanaattrb, lanaattrc, &
6736 lanavarattrr, lanavarattrd, lanavarattri, lanavarattrb, lanavarattrc, &
6737 ldativarr, ldativard, ldativari, ldativarb, ldativarc, &
6738 ldatiattrr, ldatiattrd, ldatiattri, ldatiattrb, ldatiattrc, &
6739 ldativarattrr, ldativarattrd, ldativarattri, ldativarattrb, ldativarattrc&
6740 ,purgeana)
6741TYPE(vol7d),INTENT(INOUT) :: this !< oggetto da riformare
6742LOGICAL,INTENT(IN),OPTIONAL :: sort !< if present and \a .TRUE., sort all the sortable dimensions
6743LOGICAL,INTENT(IN),OPTIONAL :: unique !< se fornito e uguale a \c .TRUE., gli eventuali elementi duplicati nei descrittori dell'oggetto iniziale verranno collassati in un unico elemento (con eventuale perdita dei dati relativi agli elementi duplicati)
6744LOGICAL,INTENT(IN),OPTIONAL :: miss !< se fornito e uguale a \c .TRUE., gli eventuali elementi dei descrittori uguali al corrispondente valore mancante verranno eliminati dall'oggetto riformato
6745LOGICAL,INTENT(IN),OPTIONAL :: lsort_time !< if present and \a .TRUE., sort only time dimension (alternative to \a sort )
6746LOGICAL,INTENT(IN),OPTIONAL :: lsort_timerange !< if present and \a .TRUE., sort only timerange dimension (alternative to \a sort )
6747LOGICAL,INTENT(IN),OPTIONAL :: lsort_level !< if present and \a .TRUE., sort only level dimension (alternative to \a sort )
6748!> se fornito, deve essere un vettore logico della stessa lunghezza di
6749!! this%time indicante quali elementi della dimensione \a time
6750!! mantenere (valori \c .TRUE.) e quali scartare (valori \c .FALSE.)
6751!! nel volume copiato; in alternativa può essere un vettore di
6752!! lunghezza 1, in tal caso, se \c .FALSE. , equivale a scartare tutti
6753!! gli elementi (utile principalmente per le variabili); è compatibile
6754!! col parametro \a miss
6755LOGICAL,INTENT(IN),OPTIONAL :: ltime(:)
6756LOGICAL,INTENT(IN),OPTIONAL :: ltimerange(:) !< come il precedente per la dimensione \a timerange
6757LOGICAL,INTENT(IN),OPTIONAL :: llevel(:) !< come il precedente per la dimensione \a level
6758LOGICAL,INTENT(IN),OPTIONAL :: lana(:) !< come il precedente per la dimensione \a ana
6759LOGICAL,INTENT(IN),OPTIONAL :: lnetwork(:) !< come il precedente per la dimensione \a network
6760!> come il precedente per tutte le possibili dimensioni variabile
6761LOGICAL,INTENT(in),OPTIONAL :: &
6762 lanavarr(:), lanavard(:), lanavari(:), lanavarb(:), lanavarc(:), &
6763 lanaattrr(:), lanaattrd(:), lanaattri(:), lanaattrb(:), lanaattrc(:), &
6764 lanavarattrr(:), lanavarattrd(:), lanavarattri(:), lanavarattrb(:), lanavarattrc(:), &
6765 ldativarr(:), ldativard(:), ldativari(:), ldativarb(:), ldativarc(:), &
6766 ldatiattrr(:), ldatiattrd(:), ldatiattri(:), ldatiattrb(:), ldatiattrc(:), &
6767 ldativarattrr(:), ldativarattrd(:), ldativarattri(:), ldativarattrb(:), ldativarattrc(:)
6768LOGICAL,INTENT(IN),OPTIONAL :: purgeana !< if true remove ana with all data missing
6769
6770TYPE(vol7d) :: v7dtmp
6771logical,allocatable :: llana(:)
6772integer :: i
6773
6774CALL vol7d_copy(this, v7dtmp, sort, unique, miss, &
6775 lsort_time, lsort_timerange, lsort_level, &
6776 ltime, ltimerange, llevel, lana, lnetwork, &
6777 lanavarr, lanavard, lanavari, lanavarb, lanavarc, &
6778 lanaattrr, lanaattrd, lanaattri, lanaattrb, lanaattrc, &
6779 lanavarattrr, lanavarattrd, lanavarattri, lanavarattrb, lanavarattrc, &
6780 ldativarr, ldativard, ldativari, ldativarb, ldativarc, &
6781 ldatiattrr, ldatiattrd, ldatiattri, ldatiattrb, ldatiattrc, &
6782 ldativarattrr, ldativarattrd, ldativarattri, ldativarattrb, ldativarattrc)
6783
6784! destroy old volume
6785CALL delete(this)
6786
6787if (optio_log(purgeana)) then
6788 allocate(llana(size(v7dtmp%ana)))
6789 llana =.false.
6790 do i =1,size(v7dtmp%ana)
6791 if (associated(v7dtmp%voldatii)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatii(i,:,:,:,:,:)))
6792 if (associated(v7dtmp%voldatir)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatir(i,:,:,:,:,:)))
6793 if (associated(v7dtmp%voldatid)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatid(i,:,:,:,:,:)))
6794 if (associated(v7dtmp%voldatib)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatib(i,:,:,:,:,:)))
6795 if (associated(v7dtmp%voldatic)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatic(i,:,:,:,:,:)))
6796 end do
6797 CALL vol7d_copy(v7dtmp, this,lana=llana)
6798 CALL delete(v7dtmp)
6799 deallocate(llana)
6800else
6801 this=v7dtmp
6802end if
6803
6804END SUBROUTINE vol7d_reform
6805
6806
6807!> Sorts the sortable dimensions in the volume \a this only when necessary.
6808!! Most of the times, the time, timerange and level dimensions in a
6809!! vol7d object are correctly sorted; on the other side many methods
6810!! strictly rely on this fact in order to work correctly. This method
6811!! performs a quick check and sorts the required dimensions only if
6812!! they are not sorted in ascending order yet, improving safety
6813!! without impairing much performance.
6814SUBROUTINE vol7d_smart_sort(this, lsort_time, lsort_timerange, lsort_level)
6815TYPE(vol7d),INTENT(INOUT) :: this !< object to be sorted
6816LOGICAL,OPTIONAL,INTENT(in) :: lsort_time !< if present and \a .TRUE., sort time dimension if it is not sorted in ascending order
6817LOGICAL,OPTIONAL,INTENT(in) :: lsort_timerange !< if present and \a .TRUE., sort timerange dimension if it is not sorted in ascending order
6818LOGICAL,OPTIONAL,INTENT(in) :: lsort_level !< if present and \a .TRUE., sort vertical level dimension if it is not sorted in ascending order
6819
6820INTEGER :: i
6821LOGICAL :: to_be_sorted
6822
6823to_be_sorted = .false.
6824CALL vol7d_alloc_vol(this) ! usual safety check
6825
6826IF (optio_log(lsort_time)) THEN
6827 DO i = 2, SIZE(this%time)
6828 IF (this%time(i) < this%time(i-1)) THEN
6829 to_be_sorted = .true.
6830 EXIT
6831 ENDIF
6832 ENDDO
6833ENDIF
6834IF (optio_log(lsort_timerange)) THEN
6835 DO i = 2, SIZE(this%timerange)
6836 IF (this%timerange(i) < this%timerange(i-1)) THEN
6837 to_be_sorted = .true.
6838 EXIT
6839 ENDIF
6840 ENDDO
6841ENDIF
6842IF (optio_log(lsort_level)) THEN
6843 DO i = 2, SIZE(this%level)
6844 IF (this%level(i) < this%level(i-1)) THEN
6845 to_be_sorted = .true.
6846 EXIT
6847 ENDIF
6848 ENDDO
6849ENDIF
6850
6851IF (to_be_sorted) CALL vol7d_reform(this, &
6852 lsort_time=lsort_time, lsort_timerange=lsort_timerange, lsort_level=lsort_level )
6853
6854END SUBROUTINE vol7d_smart_sort
6855
6856!> Filter the contents of a volume keeping only desired data.
6857!! This subroutine filters a vol7d object by keeping only a subset of
6858!! the data contained. It can keep only times within a specified
6859!! interval, only station networks contained in a list and only
6860!! specified station or data variables. If a filter parameter is not
6861!! provided, no filtering will take place according to that criterion.
6862!! The volume is reallocated keeping only the desired data.
6863SUBROUTINE vol7d_filter(this, avl, vl, nl, s_d, e_d)
6864TYPE(vol7d),INTENT(inout) :: this !< volume to be filtered
6865CHARACTER(len=*),INTENT(in),OPTIONAL :: avl(:) !< list of station variables to be kept, if not provided or of zero length, all variables are kept
6866CHARACTER(len=*),INTENT(in),OPTIONAL :: vl(:) !< list of data variables to be kept, if not provided or of zero length, all variables are kept
6867TYPE(vol7d_network),OPTIONAL :: nl(:) !< list of station networks to be kept, if not provided or of zero length, all networks are kept
6868TYPE(datetime),INTENT(in),OPTIONAL :: s_d !< initial time interval for time filtering, if not provided or equal to missing data no lower limit is imposed
6869TYPE(datetime),INTENT(in),OPTIONAL :: e_d !< final time interval for time filtering, if not provided or equal to missing data no upper limit is imposed
6870
6871INTEGER :: i
6872
6873IF (PRESENT(avl)) THEN
6874 IF (SIZE(avl) > 0) THEN
6875
6876 IF (ASSOCIATED(this%anavar%r)) THEN
6877 DO i = 1, SIZE(this%anavar%r)
6878 IF (all(this%anavar%r(i)%btable /= avl)) this%anavar%r(i) = vol7d_var_miss
6879 ENDDO
6880 ENDIF
6881
6882 IF (ASSOCIATED(this%anavar%i)) THEN
6883 DO i = 1, SIZE(this%anavar%i)
6884 IF (all(this%anavar%i(i)%btable /= avl)) this%anavar%i(i) = vol7d_var_miss
6885 ENDDO
6886 ENDIF
6887
6888 IF (ASSOCIATED(this%anavar%b)) THEN
6889 DO i = 1, SIZE(this%anavar%b)
6890 IF (all(this%anavar%b(i)%btable /= avl)) this%anavar%b(i) = vol7d_var_miss
6891 ENDDO
6892 ENDIF
6893
6894 IF (ASSOCIATED(this%anavar%d)) THEN
6895 DO i = 1, SIZE(this%anavar%d)
6896 IF (all(this%anavar%d(i)%btable /= avl)) this%anavar%d(i) = vol7d_var_miss
6897 ENDDO
6898 ENDIF
6899
6900 IF (ASSOCIATED(this%anavar%c)) THEN
6901 DO i = 1, SIZE(this%anavar%c)
6902 IF (all(this%anavar%c(i)%btable /= avl)) this%anavar%c(i) = vol7d_var_miss
6903 ENDDO
6904 ENDIF
6905
6906 ENDIF
6907ENDIF
6908
6909
6910IF (PRESENT(vl)) THEN
6911 IF (size(vl) > 0) THEN
6912 IF (ASSOCIATED(this%dativar%r)) THEN
6913 DO i = 1, SIZE(this%dativar%r)
6914 IF (all(this%dativar%r(i)%btable /= vl)) this%dativar%r(i) = vol7d_var_miss
6915 ENDDO
6916 ENDIF
6917
6918 IF (ASSOCIATED(this%dativar%i)) THEN
6919 DO i = 1, SIZE(this%dativar%i)
6920 IF (all(this%dativar%i(i)%btable /= vl)) this%dativar%i(i) = vol7d_var_miss
6921 ENDDO
6922 ENDIF
6923
6924 IF (ASSOCIATED(this%dativar%b)) THEN
6925 DO i = 1, SIZE(this%dativar%b)
6926 IF (all(this%dativar%b(i)%btable /= vl)) this%dativar%b(i) = vol7d_var_miss
6927 ENDDO
6928 ENDIF
6929
6930 IF (ASSOCIATED(this%dativar%d)) THEN
6931 DO i = 1, SIZE(this%dativar%d)
6932 IF (all(this%dativar%d(i)%btable /= vl)) this%dativar%d(i) = vol7d_var_miss
6933 ENDDO
6934 ENDIF
6935
6936 IF (ASSOCIATED(this%dativar%c)) THEN
6937 DO i = 1, SIZE(this%dativar%c)
6938 IF (all(this%dativar%c(i)%btable /= vl)) this%dativar%c(i) = vol7d_var_miss
6939 ENDDO
6940 ENDIF
6941
6942 IF (ASSOCIATED(this%dativar%c)) THEN
6943 DO i = 1, SIZE(this%dativar%c)
6944 IF (all(this%dativar%c(i)%btable /= vl)) this%dativar%c(i) = vol7d_var_miss
6945 ENDDO
6946 ENDIF
6947
6948 ENDIF
6949ENDIF
6950
6951IF (PRESENT(nl)) THEN
6952 IF (SIZE(nl) > 0) THEN
6953 DO i = 1, SIZE(this%network)
6954 IF (all(this%network(i) /= nl)) this%network(i) = vol7d_network_miss
6955 ENDDO
6956 ENDIF
6957ENDIF
6958
6959IF (PRESENT(s_d)) THEN
6960 IF (c_e(s_d)) THEN
6961 WHERE (this%time < s_d)
6962 this%time = datetime_miss
6963 END WHERE
6964 ENDIF
6965ENDIF
6966
6967IF (PRESENT(e_d)) THEN
6968 IF (c_e(e_d)) THEN
6969 WHERE (this%time > e_d)
6970 this%time = datetime_miss
6971 END WHERE
6972 ENDIF
6973ENDIF
6974
6975CALL vol7d_reform(this, miss=.true.)
6976
6977END SUBROUTINE vol7d_filter
6978
6979
6980!> Metodo per convertire i volumi di dati di un oggetto vol7d in dati
6981!! reali dove possibile. L'oggetto convertito è una copia completa
6982!! dell'originale che può essere quindi distrutto dopo la chiamata.
6983!! Per i dati di anagrafica, al momento sono convertiti solo
6984!! i dati CHARACTER se è passato \a anaconv=.TRUE.
6985!! Gli attributi non sono toccati.
6986SUBROUTINE vol7d_convr(this, that, anaconv)
6987TYPE(vol7d),INTENT(IN) :: this !< oggetto origine
6988TYPE(vol7d),INTENT(INOUT) :: that !< oggetto convertito
6989LOGICAL,OPTIONAL,INTENT(in) :: anaconv !< converti anche anagrafica
6990INTEGER :: i
6991LOGICAL :: fv(1)=(/.false./), tv(1)=(/.true./), acp(1), acn(1)
6992TYPE(vol7d) :: v7d_tmp
6993
6994IF (optio_log(anaconv)) THEN
6995 acp=fv
6996 acn=tv
6997ELSE
6998 acp=tv
6999 acn=fv
7000ENDIF
7001
7002! Volume con solo i dati reali e tutti gli attributi
7003! l'anagrafica e` copiata interamente se necessario
7004CALL vol7d_copy(this, that, &
7005 lanavarr=tv, lanavard=acp, lanavari=acp, lanavarb=acp, lanavarc=acp, &
7006 ldativarr=tv, ldativard=fv, ldativari=fv, ldativarb=fv, ldativarc=fv)
7007
7008! Volume solo di dati double
7009CALL vol7d_copy(this, v7d_tmp, &
7010 lanavarr=fv, lanavard=acn, lanavari=fv, lanavarb=fv, lanavarc=fv, &
7011 lanaattrr=fv, lanaattrd=fv, lanaattri=fv, lanaattrb=fv, lanaattrc=fv, &
7012 lanavarattrr=fv, lanavarattrd=fv, lanavarattri=fv, lanavarattrb=fv, lanavarattrc=fv, &
7013 ldativarr=fv, ldativard=tv, ldativari=fv, ldativarb=fv, ldativarc=fv, &
7014 ldatiattrr=fv, ldatiattrd=fv, ldatiattri=fv, ldatiattrb=fv, ldatiattrc=fv, &
7015 ldativarattrr=fv, ldativarattrd=fv, ldativarattri=fv, ldativarattrb=fv, ldativarattrc=fv)
7016
7017! converto a dati reali
7018IF (ASSOCIATED(v7d_tmp%anavar%d) .OR. ASSOCIATED(v7d_tmp%dativar%d)) THEN
7019
7020 IF (ASSOCIATED(v7d_tmp%anavar%d)) THEN
7021! alloco i dati reali e vi trasferisco i double
7022 ALLOCATE(v7d_tmp%volanar(SIZE(v7d_tmp%volanad, 1), SIZE(v7d_tmp%volanad, 2), &
7023 SIZE(v7d_tmp%volanad, 3)))
7024 DO i = 1, SIZE(v7d_tmp%anavar%d)
7025 v7d_tmp%volanar(:,i,:) = &
7026 realdat(v7d_tmp%volanad(:,i,:), v7d_tmp%anavar%d(i))
7027 ENDDO
7028 DEALLOCATE(v7d_tmp%volanad)
7029! trasferisco le variabili
7030 v7d_tmp%anavar%r => v7d_tmp%anavar%d
7031 NULLIFY(v7d_tmp%anavar%d)
7032 ENDIF
7033
7034 IF (ASSOCIATED(v7d_tmp%dativar%d)) THEN
7035! alloco i dati reali e vi trasferisco i double
7036 ALLOCATE(v7d_tmp%voldatir(SIZE(v7d_tmp%voldatid, 1), SIZE(v7d_tmp%voldatid, 2), &
7037 SIZE(v7d_tmp%voldatid, 3), SIZE(v7d_tmp%voldatid, 4), SIZE(v7d_tmp%voldatid, 5), &
7038 SIZE(v7d_tmp%voldatid, 6)))
7039 DO i = 1, SIZE(v7d_tmp%dativar%d)
7040 v7d_tmp%voldatir(:,:,:,:,i,:) = &
7041 realdat(v7d_tmp%voldatid(:,:,:,:,i,:), v7d_tmp%dativar%d(i))
7042 ENDDO
7043 DEALLOCATE(v7d_tmp%voldatid)
7044! trasferisco le variabili
7045 v7d_tmp%dativar%r => v7d_tmp%dativar%d
7046 NULLIFY(v7d_tmp%dativar%d)
7047 ENDIF
7048
7049! fondo con il volume definitivo
7050 CALL vol7d_merge(that, v7d_tmp)
7051ELSE
7052 CALL delete(v7d_tmp)
7053ENDIF
7054
7055
7056! Volume solo di dati interi
7057CALL vol7d_copy(this, v7d_tmp, &
7058 lanavarr=fv, lanavard=fv, lanavari=acn, lanavarb=fv, lanavarc=fv, &
7059 lanaattrr=fv, lanaattrd=fv, lanaattri=fv, lanaattrb=fv, lanaattrc=fv, &
7060 lanavarattrr=fv, lanavarattrd=fv, lanavarattri=fv, lanavarattrb=fv, lanavarattrc=fv, &
7061 ldativarr=fv, ldativard=fv, ldativari=tv, ldativarb=fv, ldativarc=fv, &
7062 ldatiattrr=fv, ldatiattrd=fv, ldatiattri=fv, ldatiattrb=fv, ldatiattrc=fv, &
7063 ldativarattrr=fv, ldativarattrd=fv, ldativarattri=fv, ldativarattrb=fv, ldativarattrc=fv)
7064
7065! converto a dati reali
7066IF (ASSOCIATED(v7d_tmp%anavar%i) .OR. ASSOCIATED(v7d_tmp%dativar%i)) THEN
7067
7068 IF (ASSOCIATED(v7d_tmp%anavar%i)) THEN
7069! alloco i dati reali e vi trasferisco gli interi
7070 ALLOCATE(v7d_tmp%volanar(SIZE(v7d_tmp%volanai, 1), SIZE(v7d_tmp%volanai, 2), &
7071 SIZE(v7d_tmp%volanai, 3)))
7072 DO i = 1, SIZE(v7d_tmp%anavar%i)
7073 v7d_tmp%volanar(:,i,:) = &
7074 realdat(v7d_tmp%volanai(:,i,:), v7d_tmp%anavar%i(i))
7075 ENDDO
7076 DEALLOCATE(v7d_tmp%volanai)
7077! trasferisco le variabili
7078 v7d_tmp%anavar%r => v7d_tmp%anavar%i
7079 NULLIFY(v7d_tmp%anavar%i)
7080 ENDIF
7081
7082 IF (ASSOCIATED(v7d_tmp%dativar%i)) THEN
7083! alloco i dati reali e vi trasferisco gli interi
7084 ALLOCATE(v7d_tmp%voldatir(SIZE(v7d_tmp%voldatii, 1), SIZE(v7d_tmp%voldatii, 2), &
7085 SIZE(v7d_tmp%voldatii, 3), SIZE(v7d_tmp%voldatii, 4), SIZE(v7d_tmp%voldatii, 5), &
7086 SIZE(v7d_tmp%voldatii, 6)))
7087 DO i = 1, SIZE(v7d_tmp%dativar%i)
7088 v7d_tmp%voldatir(:,:,:,:,i,:) = &
7089 realdat(v7d_tmp%voldatii(:,:,:,:,i,:), v7d_tmp%dativar%i(i))
7090 ENDDO
7091 DEALLOCATE(v7d_tmp%voldatii)
7092! trasferisco le variabili
7093 v7d_tmp%dativar%r => v7d_tmp%dativar%i
7094 NULLIFY(v7d_tmp%dativar%i)
7095 ENDIF
7096
7097! fondo con il volume definitivo
7098 CALL vol7d_merge(that, v7d_tmp)
7099ELSE
7100 CALL delete(v7d_tmp)
7101ENDIF
7102
7103
7104! Volume solo di dati byte
7105CALL vol7d_copy(this, v7d_tmp, &
7106 lanavarr=fv, lanavard=fv, lanavari=fv, lanavarb=acn, lanavarc=fv, &
7107 lanaattrr=fv, lanaattrd=fv, lanaattri=fv, lanaattrb=fv, lanaattrc=fv, &
7108 lanavarattrr=fv, lanavarattrd=fv, lanavarattri=fv, lanavarattrb=fv, lanavarattrc=fv, &
7109 ldativarr=fv, ldativard=fv, ldativari=fv, ldativarb=tv, ldativarc=fv, &
7110 ldatiattrr=fv, ldatiattrd=fv, ldatiattri=fv, ldatiattrb=fv, ldatiattrc=fv, &
7111 ldativarattrr=fv, ldativarattrd=fv, ldativarattri=fv, ldativarattrb=fv, ldativarattrc=fv)
7112
7113! converto a dati reali
7114IF (ASSOCIATED(v7d_tmp%anavar%b) .OR. ASSOCIATED(v7d_tmp%dativar%b)) THEN
7115
7116 IF (ASSOCIATED(v7d_tmp%anavar%b)) THEN
7117! alloco i dati reali e vi trasferisco i byte
7118 ALLOCATE(v7d_tmp%volanar(SIZE(v7d_tmp%volanab, 1), SIZE(v7d_tmp%volanab, 2), &
7119 SIZE(v7d_tmp%volanab, 3)))
7120 DO i = 1, SIZE(v7d_tmp%anavar%b)
7121 v7d_tmp%volanar(:,i,:) = &
7122 realdat(v7d_tmp%volanab(:,i,:), v7d_tmp%anavar%b(i))
7123 ENDDO
7124 DEALLOCATE(v7d_tmp%volanab)
7125! trasferisco le variabili
7126 v7d_tmp%anavar%r => v7d_tmp%anavar%b
7127 NULLIFY(v7d_tmp%anavar%b)
7128 ENDIF
7129
7130 IF (ASSOCIATED(v7d_tmp%dativar%b)) THEN
7131! alloco i dati reali e vi trasferisco i byte
7132 ALLOCATE(v7d_tmp%voldatir(SIZE(v7d_tmp%voldatib, 1), SIZE(v7d_tmp%voldatib, 2), &
7133 SIZE(v7d_tmp%voldatib, 3), SIZE(v7d_tmp%voldatib, 4), SIZE(v7d_tmp%voldatib, 5), &
7134 SIZE(v7d_tmp%voldatib, 6)))
7135 DO i = 1, SIZE(v7d_tmp%dativar%b)
7136 v7d_tmp%voldatir(:,:,:,:,i,:) = &
7137 realdat(v7d_tmp%voldatib(:,:,:,:,i,:), v7d_tmp%dativar%b(i))
7138 ENDDO
7139 DEALLOCATE(v7d_tmp%voldatib)
7140! trasferisco le variabili
7141 v7d_tmp%dativar%r => v7d_tmp%dativar%b
7142 NULLIFY(v7d_tmp%dativar%b)
7143 ENDIF
7144
7145! fondo con il volume definitivo
7146 CALL vol7d_merge(that, v7d_tmp)
7147ELSE
7148 CALL delete(v7d_tmp)
7149ENDIF
7150
7151
7152! Volume solo di dati character
7153CALL vol7d_copy(this, v7d_tmp, &
7154 lanavarr=fv, lanavard=fv, lanavari=fv, lanavarb=fv, lanavarc=acn, &
7155 lanaattrr=fv, lanaattrd=fv, lanaattri=fv, lanaattrb=fv, lanaattrc=fv, &
7156 lanavarattrr=fv, lanavarattrd=fv, lanavarattri=fv, lanavarattrb=fv, lanavarattrc=fv, &
7157 ldativarr=fv, ldativard=fv, ldativari=fv, ldativarb=fv, ldativarc=tv, &
7158 ldatiattrr=fv, ldatiattrd=fv, ldatiattri=fv, ldatiattrb=fv, ldatiattrc=fv, &
7159 ldativarattrr=fv, ldativarattrd=fv, ldativarattri=fv, ldativarattrb=fv, ldativarattrc=fv)
7160
7161! converto a dati reali
7162IF (ASSOCIATED(v7d_tmp%anavar%c) .OR. ASSOCIATED(v7d_tmp%dativar%c)) THEN
7163
7164 IF (ASSOCIATED(v7d_tmp%anavar%c)) THEN
7165! alloco i dati reali e vi trasferisco i character
7166 ALLOCATE(v7d_tmp%volanar(SIZE(v7d_tmp%volanac, 1), SIZE(v7d_tmp%volanac, 2), &
7167 SIZE(v7d_tmp%volanac, 3)))
7168 DO i = 1, SIZE(v7d_tmp%anavar%c)
7169 v7d_tmp%volanar(:,i,:) = &
7170 realdat(v7d_tmp%volanac(:,i,:), v7d_tmp%anavar%c(i))
7171 ENDDO
7172 DEALLOCATE(v7d_tmp%volanac)
7173! trasferisco le variabili
7174 v7d_tmp%anavar%r => v7d_tmp%anavar%c
7175 NULLIFY(v7d_tmp%anavar%c)
7176 ENDIF
7177
7178 IF (ASSOCIATED(v7d_tmp%dativar%c)) THEN
7179! alloco i dati reali e vi trasferisco i character
7180 ALLOCATE(v7d_tmp%voldatir(SIZE(v7d_tmp%voldatic, 1), SIZE(v7d_tmp%voldatic, 2), &
7181 SIZE(v7d_tmp%voldatic, 3), SIZE(v7d_tmp%voldatic, 4), SIZE(v7d_tmp%voldatic, 5), &
7182 SIZE(v7d_tmp%voldatic, 6)))
7183 DO i = 1, SIZE(v7d_tmp%dativar%c)
7184 v7d_tmp%voldatir(:,:,:,:,i,:) = &
7185 realdat(v7d_tmp%voldatic(:,:,:,:,i,:), v7d_tmp%dativar%c(i))
7186 ENDDO
7187 DEALLOCATE(v7d_tmp%voldatic)
7188! trasferisco le variabili
7189 v7d_tmp%dativar%r => v7d_tmp%dativar%c
7190 NULLIFY(v7d_tmp%dativar%c)
7191 ENDIF
7192
7193! fondo con il volume definitivo
7194 CALL vol7d_merge(that, v7d_tmp)
7195ELSE
7196 CALL delete(v7d_tmp)
7197ENDIF
7198
7199END SUBROUTINE vol7d_convr
7200
7201
7202!> Metodo per ottenere solo le differenze tra due oggetti vol7d.
7203!! Il primo volume viene confrontato col secondo; nel secondo volume ovunque
7204!! i dati confrontati siano coincidenti viene impostato valore mancante.
7205SUBROUTINE vol7d_diff_only (this, that, data_only,ana)
7206TYPE(vol7d),INTENT(IN) :: this !< primo volume da confrontare
7207TYPE(vol7d),INTENT(OUT) :: that !< secondo volume da confrontare in cui eliminare i dati coincidenti
7208logical , optional, intent(in) :: data_only !< attiva l'elaborazione dei soli dati e non dell'anagrafica (default: .false.)
7209logical , optional, intent(in) :: ana !< attiva l'elaborazione dell'anagrafica (coordinate e ident) (default: .false.)
7210logical :: ldata_only,lana
7211
7212IF (PRESENT(data_only)) THEN
7213 ldata_only = data_only
7214ELSE
7215 ldata_only = .false.
7216ENDIF
7217
7218IF (PRESENT(ana)) THEN
7219 lana = ana
7220ELSE
7221 lana = .false.
7222ENDIF
7223
7224
7225#undef VOL7D_POLY_ARRAY
7226#define VOL7D_POLY_ARRAY voldati
7227#include "vol7d_class_diff.F90"
7228#undef VOL7D_POLY_ARRAY
7229#define VOL7D_POLY_ARRAY voldatiattr
7230#include "vol7d_class_diff.F90"
7231#undef VOL7D_POLY_ARRAY
7232
7233if ( .not. ldata_only) then
7234
7235#define VOL7D_POLY_ARRAY volana
7236#include "vol7d_class_diff.F90"
7237#undef VOL7D_POLY_ARRAY
7238#define VOL7D_POLY_ARRAY volanaattr
7239#include "vol7d_class_diff.F90"
7240#undef VOL7D_POLY_ARRAY
7241
7242 if(lana)then
7243 where ( this%ana == that%ana )
7244 that%ana = vol7d_ana_miss
7245 end where
7246 end if
7247
7248end if
7249
7250
7251
7252END SUBROUTINE vol7d_diff_only
7253
7254
7255
7256! Creo le routine da ripetere per i vari tipi di dati di v7d
7257! tramite un template e il preprocessore
7258#undef VOL7D_POLY_TYPE
7259#undef VOL7D_POLY_TYPES
7260#define VOL7D_POLY_TYPE REAL
7261#define VOL7D_POLY_TYPES r
7262#include "vol7d_class_type_templ.F90"
7263#undef VOL7D_POLY_TYPE
7264#undef VOL7D_POLY_TYPES
7265#define VOL7D_POLY_TYPE DOUBLE PRECISION
7266#define VOL7D_POLY_TYPES d
7267#include "vol7d_class_type_templ.F90"
7268#undef VOL7D_POLY_TYPE
7269#undef VOL7D_POLY_TYPES
7270#define VOL7D_POLY_TYPE INTEGER
7271#define VOL7D_POLY_TYPES i
7272#include "vol7d_class_type_templ.F90"
7273#undef VOL7D_POLY_TYPE
7274#undef VOL7D_POLY_TYPES
7275#define VOL7D_POLY_TYPE INTEGER(kind=int_b)
7276#define VOL7D_POLY_TYPES b
7277#include "vol7d_class_type_templ.F90"
7278#undef VOL7D_POLY_TYPE
7279#undef VOL7D_POLY_TYPES
7280#define VOL7D_POLY_TYPE CHARACTER(len=vol7d_cdatalen)
7281#define VOL7D_POLY_TYPES c
7282#include "vol7d_class_type_templ.F90"
7283
7284! Creo le routine da ripetere per i vari descrittori di dimensioni di v7d
7285! tramite un template e il preprocessore
7286#define VOL7D_SORT
7287#undef VOL7D_NO_ZERO_ALLOC
7288#undef VOL7D_POLY_TYPE
7289#define VOL7D_POLY_TYPE datetime
7290#include "vol7d_class_desc_templ.F90"
7291#undef VOL7D_POLY_TYPE
7292#define VOL7D_POLY_TYPE vol7d_timerange
7293#include "vol7d_class_desc_templ.F90"
7294#undef VOL7D_POLY_TYPE
7295#define VOL7D_POLY_TYPE vol7d_level
7296#include "vol7d_class_desc_templ.F90"
7297#undef VOL7D_SORT
7298#undef VOL7D_POLY_TYPE
7299#define VOL7D_POLY_TYPE vol7d_network
7300#include "vol7d_class_desc_templ.F90"
7301#undef VOL7D_POLY_TYPE
7302#define VOL7D_POLY_TYPE vol7d_ana
7303#include "vol7d_class_desc_templ.F90"
7304#define VOL7D_NO_ZERO_ALLOC
7305#undef VOL7D_POLY_TYPE
7306#define VOL7D_POLY_TYPE vol7d_var
7307#include "vol7d_class_desc_templ.F90"
7308
7309!>\brief Scrittura su file di un volume Vol7d.
7310!! Scrittura su file unformatted di un intero volume Vol7d.
7311!! Il volume viene serializzato e scritto su file.
7312!! Il file puo' essere aperto opzionalmente dall'utente. Si possono passare
7313!! opzionalmente unità e nome del file altrimenti assegnati internamente a dei default; se assegnati internamente
7314!! tali parametri saranno in output.
7315!! Se non viene fornito il nome file viene utilizzato un file di default con nome pari al nome del programma in
7316!! esecuzione con postfisso ".v7d".
7317!! Come parametro opzionale c'è la description che insieme alla data corrente viene inserita nell'header del file.
7318subroutine vol7d_write_on_file (this,unit,description,filename,filename_auto)
7319
7320TYPE(vol7d),INTENT(IN) :: this !< volume vol7d da scrivere
7321integer,optional,intent(inout) :: unit !< unità su cui scrivere; se passata =0 ritorna il valore rielaborato (default =rielaborato internamente con getlun )
7322character(len=*),intent(in),optional :: filename !< nome del file su cui scrivere
7323character(len=*),intent(out),optional :: filename_auto !< nome del file generato se "filename" è omesso
7324character(len=*),INTENT(IN),optional :: description !< descrizione del volume
7325
7326integer :: lunit
7327character(len=254) :: ldescription,arg,lfilename
7328integer :: nana, ntime, ntimerange, nlevel, nnetwork, &
7329 ndativarr, ndativari, ndativarb, ndativard, ndativarc,&
7330 ndatiattrr, ndatiattri, ndatiattrb, ndatiattrd, ndatiattrc,&
7331 ndativarattrr, ndativarattri, ndativarattrb, ndativarattrd, ndativarattrc,&
7332 nanavarr, nanavari, nanavarb, nanavard, nanavarc,&
7333 nanaattrr, nanaattri, nanaattrb, nanaattrd, nanaattrc,&
7334 nanavarattrr, nanavarattri, nanavarattrb, nanavarattrd, nanavarattrc
7335!integer :: im,id,iy
7336integer :: tarray(8)
7337logical :: opened,exist
7338
7339 nana=0
7340 ntime=0
7341 ntimerange=0
7342 nlevel=0
7343 nnetwork=0
7344 ndativarr=0
7345 ndativari=0
7346 ndativarb=0
7347 ndativard=0
7348 ndativarc=0
7349 ndatiattrr=0
7350 ndatiattri=0
7351 ndatiattrb=0
7352 ndatiattrd=0
7353 ndatiattrc=0
7354 ndativarattrr=0
7355 ndativarattri=0
7356 ndativarattrb=0
7357 ndativarattrd=0
7358 ndativarattrc=0
7359 nanavarr=0
7360 nanavari=0
7361 nanavarb=0
7362 nanavard=0
7363 nanavarc=0
7364 nanaattrr=0
7365 nanaattri=0
7366 nanaattrb=0
7367 nanaattrd=0
7368 nanaattrc=0
7369 nanavarattrr=0
7370 nanavarattri=0
7371 nanavarattrb=0
7372 nanavarattrd=0
7373 nanavarattrc=0
7374
7375
7376!call idate(im,id,iy)
7377call date_and_time(values=tarray)
7378call getarg(0,arg)
7379
7380if (present(description))then
7381 ldescription=description
7382else
7383 ldescription="Vol7d generated by: "//trim(arg)
7384end if
7385
7386if (.not. present(unit))then
7387 lunit=getunit()
7388else
7389 if (unit==0)then
7390 lunit=getunit()
7391 unit=lunit
7392 else
7393 lunit=unit
7394 end if
7395end if
7396
7397lfilename=trim(arg)//".v7d"
7398if (index(arg,'/',back=.true.) > 0) lfilename=lfilename(index(arg,'/',back=.true.)+1 : )
7399
7400if (present(filename))then
7401 if (filename /= "")then
7402 lfilename=filename
7403 end if
7404end if
7405
7406if (present(filename_auto))filename_auto=lfilename
7407
7408
7409inquire(unit=lunit,opened=opened)
7410if (.not. opened) then
7411! inquire(file=lfilename, EXIST=exist)
7412! IF (exist) THEN
7413! CALL l4f_log(L4F_FATAL, &
7414! 'in vol7d_write_on_file, file exists, cannot open file '//TRIM(lfilename))
7415! CALL raise_fatal_error()
7416! ENDIF
7417 OPEN(unit=lunit, file=lfilename, form='UNFORMATTED', access='STREAM')
7418 CALL l4f_log(l4f_info, 'opened: '//trim(lfilename))
7419end if
7420
7421if (associated(this%ana)) nana=size(this%ana)
7422if (associated(this%time)) ntime=size(this%time)
7423if (associated(this%timerange)) ntimerange=size(this%timerange)
7424if (associated(this%level)) nlevel=size(this%level)
7425if (associated(this%network)) nnetwork=size(this%network)
7426
7427if (associated(this%dativar%r)) ndativarr=size(this%dativar%r)
7428if (associated(this%dativar%i)) ndativari=size(this%dativar%i)
7429if (associated(this%dativar%b)) ndativarb=size(this%dativar%b)
7430if (associated(this%dativar%d)) ndativard=size(this%dativar%d)
7431if (associated(this%dativar%c)) ndativarc=size(this%dativar%c)
7432
7433if (associated(this%datiattr%r)) ndatiattrr=size(this%datiattr%r)
7434if (associated(this%datiattr%i)) ndatiattri=size(this%datiattr%i)
7435if (associated(this%datiattr%b)) ndatiattrb=size(this%datiattr%b)
7436if (associated(this%datiattr%d)) ndatiattrd=size(this%datiattr%d)
7437if (associated(this%datiattr%c)) ndatiattrc=size(this%datiattr%c)
7438
7439if (associated(this%dativarattr%r)) ndativarattrr=size(this%dativarattr%r)
7440if (associated(this%dativarattr%i)) ndativarattri=size(this%dativarattr%i)
7441if (associated(this%dativarattr%b)) ndativarattrb=size(this%dativarattr%b)
7442if (associated(this%dativarattr%d)) ndativarattrd=size(this%dativarattr%d)
7443if (associated(this%dativarattr%c)) ndativarattrc=size(this%dativarattr%c)
7444
7445if (associated(this%anavar%r)) nanavarr=size(this%anavar%r)
7446if (associated(this%anavar%i)) nanavari=size(this%anavar%i)
7447if (associated(this%anavar%b)) nanavarb=size(this%anavar%b)
7448if (associated(this%anavar%d)) nanavard=size(this%anavar%d)
7449if (associated(this%anavar%c)) nanavarc=size(this%anavar%c)
7450
7451if (associated(this%anaattr%r)) nanaattrr=size(this%anaattr%r)
7452if (associated(this%anaattr%i)) nanaattri=size(this%anaattr%i)
7453if (associated(this%anaattr%b)) nanaattrb=size(this%anaattr%b)
7454if (associated(this%anaattr%d)) nanaattrd=size(this%anaattr%d)
7455if (associated(this%anaattr%c)) nanaattrc=size(this%anaattr%c)
7456
7457if (associated(this%anavarattr%r)) nanavarattrr=size(this%anavarattr%r)
7458if (associated(this%anavarattr%i)) nanavarattri=size(this%anavarattr%i)
7459if (associated(this%anavarattr%b)) nanavarattrb=size(this%anavarattr%b)
7460if (associated(this%anavarattr%d)) nanavarattrd=size(this%anavarattr%d)
7461if (associated(this%anavarattr%c)) nanavarattrc=size(this%anavarattr%c)
7462
7463write(unit=lunit)ldescription
7464write(unit=lunit)tarray
7465
7466write(unit=lunit)&
7467 nana, ntime, ntimerange, nlevel, nnetwork, &
7468 ndativarr, ndativari, ndativarb, ndativard, ndativarc,&
7469 ndatiattrr, ndatiattri, ndatiattrb, ndatiattrd, ndatiattrc,&
7470 ndativarattrr, ndativarattri, ndativarattrb, ndativarattrd, ndativarattrc,&
7471 nanavarr, nanavari, nanavarb, nanavard, nanavarc,&
7472 nanaattrr, nanaattri, nanaattrb, nanaattrd, nanaattrc,&
7473 nanavarattrr, nanavarattri, nanavarattrb, nanavarattrd, nanavarattrc, &
7474 this%time_definition
7475
7476
7477!write(unit=lunit)this
7478
7479
7480!! prime 5 dimensioni
7481if (associated(this%ana)) call write_unit(this%ana, lunit)
7482if (associated(this%time)) call write_unit(this%time, lunit)
7483if (associated(this%level)) write(unit=lunit)this%level
7484if (associated(this%timerange)) write(unit=lunit)this%timerange
7485if (associated(this%network)) write(unit=lunit)this%network
7486
7487 !! 6a dimensione: variabile dell'anagrafica e dei dati
7488 !! con relativi attributi e in 5 tipi diversi
7489
7490if (associated(this%anavar%r)) write(unit=lunit)this%anavar%r
7491if (associated(this%anavar%i)) write(unit=lunit)this%anavar%i
7492if (associated(this%anavar%b)) write(unit=lunit)this%anavar%b
7493if (associated(this%anavar%d)) write(unit=lunit)this%anavar%d
7494if (associated(this%anavar%c)) write(unit=lunit)this%anavar%c
7495
7496if (associated(this%anaattr%r)) write(unit=lunit)this%anaattr%r
7497if (associated(this%anaattr%i)) write(unit=lunit)this%anaattr%i
7498if (associated(this%anaattr%b)) write(unit=lunit)this%anaattr%b
7499if (associated(this%anaattr%d)) write(unit=lunit)this%anaattr%d
7500if (associated(this%anaattr%c)) write(unit=lunit)this%anaattr%c
7501
7502if (associated(this%anavarattr%r)) write(unit=lunit)this%anavarattr%r
7503if (associated(this%anavarattr%i)) write(unit=lunit)this%anavarattr%i
7504if (associated(this%anavarattr%b)) write(unit=lunit)this%anavarattr%b
7505if (associated(this%anavarattr%d)) write(unit=lunit)this%anavarattr%d
7506if (associated(this%anavarattr%c)) write(unit=lunit)this%anavarattr%c
7507
7508if (associated(this%dativar%r)) write(unit=lunit)this%dativar%r
7509if (associated(this%dativar%i)) write(unit=lunit)this%dativar%i
7510if (associated(this%dativar%b)) write(unit=lunit)this%dativar%b
7511if (associated(this%dativar%d)) write(unit=lunit)this%dativar%d
7512if (associated(this%dativar%c)) write(unit=lunit)this%dativar%c
7513
7514if (associated(this%datiattr%r)) write(unit=lunit)this%datiattr%r
7515if (associated(this%datiattr%i)) write(unit=lunit)this%datiattr%i
7516if (associated(this%datiattr%b)) write(unit=lunit)this%datiattr%b
7517if (associated(this%datiattr%d)) write(unit=lunit)this%datiattr%d
7518if (associated(this%datiattr%c)) write(unit=lunit)this%datiattr%c
7519
7520if (associated(this%dativarattr%r)) write(unit=lunit)this%dativarattr%r
7521if (associated(this%dativarattr%i)) write(unit=lunit)this%dativarattr%i
7522if (associated(this%dativarattr%b)) write(unit=lunit)this%dativarattr%b
7523if (associated(this%dativarattr%d)) write(unit=lunit)this%dativarattr%d
7524if (associated(this%dativarattr%c)) write(unit=lunit)this%dativarattr%c
7525
7526!! Volumi di valori e attributi per anagrafica e dati
7527
7528if (associated(this%volanar)) write(unit=lunit)this%volanar
7529if (associated(this%volanaattrr)) write(unit=lunit)this%volanaattrr
7530if (associated(this%voldatir)) write(unit=lunit)this%voldatir
7531if (associated(this%voldatiattrr)) write(unit=lunit)this%voldatiattrr
7532
7533if (associated(this%volanai)) write(unit=lunit)this%volanai
7534if (associated(this%volanaattri)) write(unit=lunit)this%volanaattri
7535if (associated(this%voldatii)) write(unit=lunit)this%voldatii
7536if (associated(this%voldatiattri)) write(unit=lunit)this%voldatiattri
7537
7538if (associated(this%volanab)) write(unit=lunit)this%volanab
7539if (associated(this%volanaattrb)) write(unit=lunit)this%volanaattrb
7540if (associated(this%voldatib)) write(unit=lunit)this%voldatib
7541if (associated(this%voldatiattrb)) write(unit=lunit)this%voldatiattrb
7542
7543if (associated(this%volanad)) write(unit=lunit)this%volanad
7544if (associated(this%volanaattrd)) write(unit=lunit)this%volanaattrd
7545if (associated(this%voldatid)) write(unit=lunit)this%voldatid
7546if (associated(this%voldatiattrd)) write(unit=lunit)this%voldatiattrd
7547
7548if (associated(this%volanac)) write(unit=lunit)this%volanac
7549if (associated(this%volanaattrc)) write(unit=lunit)this%volanaattrc
7550if (associated(this%voldatic)) write(unit=lunit)this%voldatic
7551if (associated(this%voldatiattrc)) write(unit=lunit)this%voldatiattrc
7552
7553if (.not. present(unit)) close(unit=lunit)
7554
7555end subroutine vol7d_write_on_file
7556
7557
7558!>\brief Lettura da file di un volume Vol7d.
7559!! Lettura da file unformatted di un intero volume Vol7d.
7560!! Questa subroutine comprende vol7d_alloc e vol7d_alloc_vol.
7561!! Il file puo' essere aperto opzionalmente dall'utente. Si possono passare
7562!! opzionalmente unità e nome del file altrimenti assegnati internamente a dei default; se assegnati internamente
7563!! tali parametri saranno in output.
7564
7565
7566subroutine vol7d_read_from_file (this,unit,filename,description,tarray,filename_auto)
7567
7568TYPE(vol7d),INTENT(OUT) :: this !< Volume vol7d da leggere
7569integer,intent(inout),optional :: unit !< unità su cui è stato aperto un file; se =0 rielaborato internamente (default = elaborato internamente con getunit)
7570character(len=*),INTENT(in),optional :: filename !< nome del file eventualmente da aprire (default = (nome dell'eseguibile)//.v7d )
7571character(len=*),intent(out),optional :: filename_auto !< nome del file generato se "filename" è omesso
7572character(len=*),INTENT(out),optional :: description !< descrizione del volume letto
7573integer,intent(out),optional :: tarray(8) !< vettore come definito da "date_and_time" della data di scrittura del volume
7574
7575
7576integer :: nana, ntime, ntimerange, nlevel, nnetwork, &
7577 ndativarr, ndativari, ndativarb, ndativard, ndativarc,&
7578 ndatiattrr, ndatiattri, ndatiattrb, ndatiattrd, ndatiattrc,&
7579 ndativarattrr, ndativarattri, ndativarattrb, ndativarattrd, ndativarattrc,&
7580 nanavarr, nanavari, nanavarb, nanavard, nanavarc,&
7581 nanaattrr, nanaattri, nanaattrb, nanaattrd, nanaattrc,&
7582 nanavarattrr, nanavarattri, nanavarattrb, nanavarattrd, nanavarattrc
7583
7584character(len=254) :: ldescription,lfilename,arg
7585integer :: ltarray(8),lunit,ios
7586logical :: opened,exist
7587
7588
7589call getarg(0,arg)
7590
7591if (.not. present(unit))then
7592 lunit=getunit()
7593else
7594 if (unit==0)then
7595 lunit=getunit()
7596 unit=lunit
7597 else
7598 lunit=unit
7599 end if
7600end if
7601
7602lfilename=trim(arg)//".v7d"
7603if (index(arg,'/',back=.true.) > 0) lfilename=lfilename(index(arg,'/',back=.true.)+1 : )
7604
7605if (present(filename))then
7606 if (filename /= "")then
7607 lfilename=filename
7608 end if
7609end if
7610
7611if (present(filename_auto))filename_auto=lfilename
7612
7613
7614inquire(unit=lunit,opened=opened)
7615IF (.NOT. opened) THEN
7616 inquire(file=lfilename,exist=exist)
7617 IF (.NOT.exist) THEN
7618 CALL l4f_log(l4f_fatal, &
7619 'in vol7d_read_from_file, file does not exists, cannot open')
7620 CALL raise_fatal_error()
7621 ENDIF
7622 OPEN(unit=lunit, file=lfilename, form='UNFORMATTED', access='STREAM', &
7623 status='OLD', action='READ')
7624 CALL l4f_log(l4f_info, 'opened: '//trim(lfilename))
7625end if
7626
7627
7628call init(this)
7629read(unit=lunit,iostat=ios)ldescription
7630
7631if (ios < 0) then ! A negative value indicates that the End of File or End of Record
7632 call vol7d_alloc (this)
7633 call vol7d_alloc_vol (this)
7634 if (present(description))description=ldescription
7635 if (present(tarray))tarray=ltarray
7636 if (.not. present(unit)) close(unit=lunit)
7637end if
7638
7639read(unit=lunit)ltarray
7640
7641CALL l4f_log(l4f_info, 'Reading vol7d from file')
7642CALL l4f_log(l4f_info, 'description: '//trim(ldescription))
7643CALL l4f_log(l4f_info, 'written on '//trim(to_char(ltarray(1)))//' '// &
7644 trim(to_char(ltarray(2)))//' '//trim(to_char(ltarray(3))))
7645
7646if (present(description))description=ldescription
7647if (present(tarray))tarray=ltarray
7648
7649read(unit=lunit)&
7650 nana, ntime, ntimerange, nlevel, nnetwork, &
7651 ndativarr, ndativari, ndativarb, ndativard, ndativarc,&
7652 ndatiattrr, ndatiattri, ndatiattrb, ndatiattrd, ndatiattrc,&
7653 ndativarattrr, ndativarattri, ndativarattrb, ndativarattrd, ndativarattrc,&
7654 nanavarr, nanavari, nanavarb, nanavard, nanavarc,&
7655 nanaattrr, nanaattri, nanaattrb, nanaattrd, nanaattrc,&
7656 nanavarattrr, nanavarattri, nanavarattrb, nanavarattrd, nanavarattrc, &
7657 this%time_definition
7658
7659call vol7d_alloc (this, &
7660 nana=nana, ntime=ntime, ntimerange=ntimerange, nlevel=nlevel, nnetwork=nnetwork,&
7661 ndativarr=ndativarr, ndativari=ndativari, ndativarb=ndativarb,&
7662 ndativard=ndativard, ndativarc=ndativarc,&
7663 ndatiattrr=ndatiattrr, ndatiattri=ndatiattri, ndatiattrb=ndatiattrb,&
7664 ndatiattrd=ndatiattrd, ndatiattrc=ndatiattrc,&
7665 ndativarattrr=ndativarattrr, ndativarattri=ndativarattri, ndativarattrb=ndativarattrb, &
7666 ndativarattrd=ndativarattrd, ndativarattrc=ndativarattrc,&
7667 nanavarr=nanavarr, nanavari=nanavari, nanavarb=nanavarb, &
7668 nanavard=nanavard, nanavarc=nanavarc,&
7669 nanaattrr=nanaattrr, nanaattri=nanaattri, nanaattrb=nanaattrb,&
7670 nanaattrd=nanaattrd, nanaattrc=nanaattrc,&
7671 nanavarattrr=nanavarattrr, nanavarattri=nanavarattri, nanavarattrb=nanavarattrb, &
7672 nanavarattrd=nanavarattrd, nanavarattrc=nanavarattrc)
7673
7674
7675if (associated(this%ana)) call read_unit(this%ana, lunit)
7676if (associated(this%time)) call read_unit(this%time, lunit)
7677if (associated(this%level)) read(unit=lunit)this%level
7678if (associated(this%timerange)) read(unit=lunit)this%timerange
7679if (associated(this%network)) read(unit=lunit)this%network
7680
7681if (associated(this%anavar%r)) read(unit=lunit)this%anavar%r
7682if (associated(this%anavar%i)) read(unit=lunit)this%anavar%i
7683if (associated(this%anavar%b)) read(unit=lunit)this%anavar%b
7684if (associated(this%anavar%d)) read(unit=lunit)this%anavar%d
7685if (associated(this%anavar%c)) read(unit=lunit)this%anavar%c
7686
7687if (associated(this%anaattr%r)) read(unit=lunit)this%anaattr%r
7688if (associated(this%anaattr%i)) read(unit=lunit)this%anaattr%i
7689if (associated(this%anaattr%b)) read(unit=lunit)this%anaattr%b
7690if (associated(this%anaattr%d)) read(unit=lunit)this%anaattr%d
7691if (associated(this%anaattr%c)) read(unit=lunit)this%anaattr%c
7692
7693if (associated(this%anavarattr%r)) read(unit=lunit)this%anavarattr%r
7694if (associated(this%anavarattr%i)) read(unit=lunit)this%anavarattr%i
7695if (associated(this%anavarattr%b)) read(unit=lunit)this%anavarattr%b
7696if (associated(this%anavarattr%d)) read(unit=lunit)this%anavarattr%d
7697if (associated(this%anavarattr%c)) read(unit=lunit)this%anavarattr%c
7698
7699if (associated(this%dativar%r)) read(unit=lunit)this%dativar%r
7700if (associated(this%dativar%i)) read(unit=lunit)this%dativar%i
7701if (associated(this%dativar%b)) read(unit=lunit)this%dativar%b
7702if (associated(this%dativar%d)) read(unit=lunit)this%dativar%d
7703if (associated(this%dativar%c)) read(unit=lunit)this%dativar%c
7704
7705if (associated(this%datiattr%r)) read(unit=lunit)this%datiattr%r
7706if (associated(this%datiattr%i)) read(unit=lunit)this%datiattr%i
7707if (associated(this%datiattr%b)) read(unit=lunit)this%datiattr%b
7708if (associated(this%datiattr%d)) read(unit=lunit)this%datiattr%d
7709if (associated(this%datiattr%c)) read(unit=lunit)this%datiattr%c
7710
7711if (associated(this%dativarattr%r)) read(unit=lunit)this%dativarattr%r
7712if (associated(this%dativarattr%i)) read(unit=lunit)this%dativarattr%i
7713if (associated(this%dativarattr%b)) read(unit=lunit)this%dativarattr%b
7714if (associated(this%dativarattr%d)) read(unit=lunit)this%dativarattr%d
7715if (associated(this%dativarattr%c)) read(unit=lunit)this%dativarattr%c
7716
7717call vol7d_alloc_vol (this)
7718
7719!! Volumi di valori e attributi per anagrafica e dati
7720
7721if (associated(this%volanar)) read(unit=lunit)this%volanar
7722if (associated(this%volanaattrr)) read(unit=lunit)this%volanaattrr
7723if (associated(this%voldatir)) read(unit=lunit)this%voldatir
7724if (associated(this%voldatiattrr)) read(unit=lunit)this%voldatiattrr
7725
7726if (associated(this%volanai)) read(unit=lunit)this%volanai
7727if (associated(this%volanaattri)) read(unit=lunit)this%volanaattri
7728if (associated(this%voldatii)) read(unit=lunit)this%voldatii
7729if (associated(this%voldatiattri)) read(unit=lunit)this%voldatiattri
7730
7731if (associated(this%volanab)) read(unit=lunit)this%volanab
7732if (associated(this%volanaattrb)) read(unit=lunit)this%volanaattrb
7733if (associated(this%voldatib)) read(unit=lunit)this%voldatib
7734if (associated(this%voldatiattrb)) read(unit=lunit)this%voldatiattrb
7735
7736if (associated(this%volanad)) read(unit=lunit)this%volanad
7737if (associated(this%volanaattrd)) read(unit=lunit)this%volanaattrd
7738if (associated(this%voldatid)) read(unit=lunit)this%voldatid
7739if (associated(this%voldatiattrd)) read(unit=lunit)this%voldatiattrd
7740
7741if (associated(this%volanac)) read(unit=lunit)this%volanac
7742if (associated(this%volanaattrc)) read(unit=lunit)this%volanaattrc
7743if (associated(this%voldatic)) read(unit=lunit)this%voldatic
7744if (associated(this%voldatiattrc)) read(unit=lunit)this%voldatiattrc
7745
7746if (.not. present(unit)) close(unit=lunit)
7747
7748end subroutine vol7d_read_from_file
7749
7750
7751! to double precision
7752elemental doubleprecision function doubledatd(voldat,var)
7753doubleprecision,intent(in) :: voldat
7754type(vol7d_var),intent(in) :: var
7755
7756doubledatd=voldat
7757
7758end function doubledatd
7759
7760
7761elemental doubleprecision function doubledatr(voldat,var)
7762real,intent(in) :: voldat
7763type(vol7d_var),intent(in) :: var
7764
7765if (c_e(voldat))then
7766 doubledatr=dble(voldat)
7767else
7768 doubledatr=dmiss
7769end if
7770
7771end function doubledatr
7772
7773
7774elemental doubleprecision function doubledati(voldat,var)
7775integer,intent(in) :: voldat
7776type(vol7d_var),intent(in) :: var
7777
7778if (c_e(voldat)) then
7779 if (c_e(var%scalefactor))then
7780 doubledati=dble(voldat)/10.d0**var%scalefactor
7781 else
7782 doubledati=dble(voldat)
7783 endif
7784else
7785 doubledati=dmiss
7786end if
7787
7788end function doubledati
7789
7790
7791elemental doubleprecision function doubledatb(voldat,var)
7792integer(kind=int_b),intent(in) :: voldat
7793type(vol7d_var),intent(in) :: var
7794
7795if (c_e(voldat)) then
7796 if (c_e(var%scalefactor))then
7797 doubledatb=dble(voldat)/10.d0**var%scalefactor
7798 else
7799 doubledatb=dble(voldat)
7800 endif
7801else
7802 doubledatb=dmiss
7803end if
7804
7805end function doubledatb
7806
7807
7808elemental doubleprecision function doubledatc(voldat,var)
7809CHARACTER(len=vol7d_cdatalen),intent(in) :: voldat
7810type(vol7d_var),intent(in) :: var
7811
7812doubledatc = c2d(voldat)
7813if (c_e(doubledatc) .and. c_e(var%scalefactor))then
7814 doubledatc=doubledatc/10.d0**var%scalefactor
7815end if
7816
7817end function doubledatc
7818
7819
7820! to integer
7821elemental integer function integerdatd(voldat,var)
7822doubleprecision,intent(in) :: voldat
7823type(vol7d_var),intent(in) :: var
7824
7825if (c_e(voldat))then
7826 if (c_e(var%scalefactor)) then
7827 integerdatd=nint(voldat*10d0**var%scalefactor)
7828 else
7829 integerdatd=nint(voldat)
7830 endif
7831else
7832 integerdatd=imiss
7833end if
7834
7835end function integerdatd
7836
7837
7838elemental integer function integerdatr(voldat,var)
7839real,intent(in) :: voldat
7840type(vol7d_var),intent(in) :: var
7841
7842if (c_e(voldat))then
7843 if (c_e(var%scalefactor)) then
7844 integerdatr=nint(voldat*10d0**var%scalefactor)
7845 else
7846 integerdatr=nint(voldat)
7847 endif
7848else
7849 integerdatr=imiss
7850end if
7851
7852end function integerdatr
7853
7854
7855elemental integer function integerdati(voldat,var)
7856integer,intent(in) :: voldat
7857type(vol7d_var),intent(in) :: var
7858
7859integerdati=voldat
7860
7861end function integerdati
7862
7863
7864elemental integer function integerdatb(voldat,var)
7865integer(kind=int_b),intent(in) :: voldat
7866type(vol7d_var),intent(in) :: var
7867
7868if (c_e(voldat))then
7869 integerdatb=voldat
7870else
7871 integerdatb=imiss
7872end if
7873
7874end function integerdatb
7875
7876
7877elemental integer function integerdatc(voldat,var)
7878CHARACTER(len=vol7d_cdatalen),intent(in) :: voldat
7879type(vol7d_var),intent(in) :: var
7880
7881integerdatc=c2i(voldat)
7882
7883end function integerdatc
7884
7885
7886! to real
7887elemental real function realdatd(voldat,var)
7888doubleprecision,intent(in) :: voldat
7889type(vol7d_var),intent(in) :: var
7890
7891if (c_e(voldat))then
7892 realdatd=real(voldat)
7893else
7894 realdatd=rmiss
7895end if
7896
7897end function realdatd
7898
7899
7900elemental real function realdatr(voldat,var)
7901real,intent(in) :: voldat
7902type(vol7d_var),intent(in) :: var
7903
7904realdatr=voldat
7905
7906end function realdatr
7907
7908
7909elemental real function realdati(voldat,var)
7910integer,intent(in) :: voldat
7911type(vol7d_var),intent(in) :: var
7912
7913if (c_e(voldat)) then
7914 if (c_e(var%scalefactor))then
7915 realdati=float(voldat)/10.**var%scalefactor
7916 else
7917 realdati=float(voldat)
7918 endif
7919else
7920 realdati=rmiss
7921end if
7922
7923end function realdati
7924
7925
7926elemental real function realdatb(voldat,var)
7927integer(kind=int_b),intent(in) :: voldat
7928type(vol7d_var),intent(in) :: var
7929
7930if (c_e(voldat)) then
7931 if (c_e(var%scalefactor))then
7932 realdatb=float(voldat)/10**var%scalefactor
7933 else
7934 realdatb=float(voldat)
7935 endif
7936else
7937 realdatb=rmiss
7938end if
7939
7940end function realdatb
7941
7942
7943elemental real function realdatc(voldat,var)
7944CHARACTER(len=vol7d_cdatalen),intent(in) :: voldat
7945type(vol7d_var),intent(in) :: var
7946
7947realdatc=c2r(voldat)
7948if (c_e(realdatc) .and. c_e(var%scalefactor))then
7949 realdatc=realdatc/10.**var%scalefactor
7950end if
7951
7952end function realdatc
7953
7954
7955!> Return an ana volume of a requested variable as real data.
7956!! It returns a 2-d array of the proper shape (ana x network) for the
7957!! ana variable requested, converted to real type. If the conversion
7958!! fails or if the variable is not contained in the ana volume,
7959!! missing data are returned.
7960FUNCTION realanavol(this, var) RESULT(vol)
7961TYPE(vol7d),INTENT(in) :: this !< the \a vol7d object to query, the method \a vol7d_alloc_vol must have been called for it otherwise progam may abort
7962TYPE(vol7d_var),INTENT(in) :: var !< the ana variable to be returned
7963REAL :: vol(SIZE(this%ana),size(this%network))
7964
7965CHARACTER(len=1) :: dtype
7966INTEGER :: indvar
7967
7968dtype = cmiss
7969indvar = index(this%anavar, var, type=dtype)
7970
7971IF (indvar > 0) THEN
7972 SELECT CASE (dtype)
7973 CASE("d")
7974 vol = realdat(this%volanad(:,indvar,:), var)
7975 CASE("r")
7976 vol = this%volanar(:,indvar,:)
7977 CASE("i")
7978 vol = realdat(this%volanai(:,indvar,:), var)
7979 CASE("b")
7980 vol = realdat(this%volanab(:,indvar,:), var)
7981 CASE("c")
7982 vol = realdat(this%volanac(:,indvar,:), var)
7983 CASE default
7984 vol = rmiss
7985 END SELECT
7986ELSE
7987 vol = rmiss
7988ENDIF
7989
7990END FUNCTION realanavol
7991
7992
7993!> Return an ana volume of a requested variable as integer data.
7994!! It returns a 2-d array of the proper shape (ana x network) for the
7995!! ana variable requested, converted to integer type. If the conversion
7996!! fails or if the variable is not contained in the ana volume,
7997!! missing data are returned.
7998FUNCTION integeranavol(this, var) RESULT(vol)
7999TYPE(vol7d),INTENT(in) :: this !< the \a vol7d object to query, the method \a vol7d_alloc_vol must have been called for it otherwise progam may abort
8000TYPE(vol7d_var),INTENT(in) :: var !< the ana variable to be returned
8001INTEGER :: vol(SIZE(this%ana),size(this%network))
8002
8003CHARACTER(len=1) :: dtype
8004INTEGER :: indvar
8005
8006dtype = cmiss
8007indvar = index(this%anavar, var, type=dtype)
8008
8009IF (indvar > 0) THEN
8010 SELECT CASE (dtype)
8011 CASE("d")
8012 vol = integerdat(this%volanad(:,indvar,:), var)
8013 CASE("r")
8014 vol = integerdat(this%volanar(:,indvar,:), var)
8015 CASE("i")
8016 vol = this%volanai(:,indvar,:)
8017 CASE("b")
8018 vol = integerdat(this%volanab(:,indvar,:), var)
8019 CASE("c")
8020 vol = integerdat(this%volanac(:,indvar,:), var)
8021 CASE default
8022 vol = imiss
8023 END SELECT
8024ELSE
8025 vol = imiss
8026ENDIF
8027
8028END FUNCTION integeranavol
8029
8030
8031!> Move data for all variables from one coordinate in the character volume to other.
8032!! Only not missing data will be copyed and all attributes will be moved together.
8033!! Usefull to colapse data spread in more indices (level or time or ....).
8034!! After the move is possible to set to missing some descriptor and make a copy with miss=.true.
8035!! to obtain a new vol7d with less data shape.
8036subroutine move_datac (v7d,&
8037 indana,indtime,indlevel,indtimerange,indnetwork,&
8038 indananew,indtimenew,indlevelnew,indtimerangenew,indnetworknew)
8039
8040TYPE(vol7d),intent(inout) :: v7d !< data in form of character in this object will be moved
8041
8042integer,intent(in) :: indana,indtime,indlevel,indtimerange,indnetwork !< source coordinate of the data
8043integer,intent(in) :: indananew,indtimenew,indlevelnew,indtimerangenew,indnetworknew !< destination coordinate of data
8044integer :: inddativar,inddativarattr
8045
8046
8047do inddativar=1,size(v7d%dativar%c)
8048
8049 if (c_e(v7d%voldatic(indana,indtime,indlevel,indtimerange,inddativar,indnetwork)) .and. &
8050 .not. c_e(v7d%voldatic(indananew,indtimenew,indlevelnew,indtimerangenew,inddativar,indnetworknew))&
8051 ) then
8052
8053 ! dati
8054 v7d%voldatic &
8055 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativar,indnetworknew) = &
8056 v7d%voldatic &
8057 (indana,indtime,indlevel,indtimerange,inddativar,indnetwork)
8058
8059
8060 ! attributi
8061 if (associated (v7d%dativarattr%i)) then
8062 inddativarattr = index(v7d%dativarattr%i,v7d%dativar%c(inddativar))
8063 if (inddativarattr > 0 ) then
8064 v7d%voldatiattri &
8065 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
8066 v7d%voldatiattri &
8067 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
8068 end if
8069 end if
8070
8071 if (associated (v7d%dativarattr%r)) then
8072 inddativarattr = index(v7d%dativarattr%r,v7d%dativar%c(inddativar))
8073 if (inddativarattr > 0 ) then
8074 v7d%voldatiattrr &
8075 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
8076 v7d%voldatiattrr &
8077 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
8078 end if
8079 end if
8080
8081 if (associated (v7d%dativarattr%d)) then
8082 inddativarattr = index(v7d%dativarattr%d,v7d%dativar%c(inddativar))
8083 if (inddativarattr > 0 ) then
8084 v7d%voldatiattrd &
8085 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
8086 v7d%voldatiattrd &
8087 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
8088 end if
8089 end if
8090
8091 if (associated (v7d%dativarattr%b)) then
8092 inddativarattr = index(v7d%dativarattr%b,v7d%dativar%c(inddativar))
8093 if (inddativarattr > 0 ) then
8094 v7d%voldatiattrb &
8095 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
8096 v7d%voldatiattrb &
8097 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
8098 end if
8099 end if
8100
8101 if (associated (v7d%dativarattr%c)) then
8102 inddativarattr = index(v7d%dativarattr%c,v7d%dativar%c(inddativar))
8103 if (inddativarattr > 0 ) then
8104 v7d%voldatiattrc &
8105 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
8106 v7d%voldatiattrc &
8107 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
8108 end if
8109 end if
8110
8111 end if
8112
8113end do
8114
8115end subroutine move_datac
8116
8117!> Move data for all variables from one coordinate in the real volume to other.
8118!! Only not missing data will be copyed and all attributes will be moved together.
8119!! Usefull to colapse data spread in more indices (level or time or ....).
8120!! After the move is possible to set to missing some descriptor and make a copy with miss=.true.
8121!! to obtain a new vol7d with less data shape.
8122subroutine move_datar (v7d,&
8123 indana,indtime,indlevel,indtimerange,indnetwork,&
8124 indananew,indtimenew,indlevelnew,indtimerangenew,indnetworknew)
8125
8126TYPE(vol7d),intent(inout) :: v7d !< data in form of character in this object will be moved
8127
8128integer,intent(in) :: indana,indtime,indlevel,indtimerange,indnetwork !< source coordinate of the data
8129integer,intent(in) :: indananew,indtimenew,indlevelnew,indtimerangenew,indnetworknew !< destination coordinate of data
8130integer :: inddativar,inddativarattr
8131
8132
8133do inddativar=1,size(v7d%dativar%r)
8134
8135 if (c_e(v7d%voldatir(indana,indtime,indlevel,indtimerange,inddativar,indnetwork)) .and. &
8136 .not. c_e(v7d%voldatir(indananew,indtimenew,indlevelnew,indtimerangenew,inddativar,indnetworknew))&
8137 ) then
8138
8139 ! dati
8140 v7d%voldatir &
8141 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativar,indnetworknew) = &
8142 v7d%voldatir &
8143 (indana,indtime,indlevel,indtimerange,inddativar,indnetwork)
8144
8145
8146 ! attributi
8147 if (associated (v7d%dativarattr%i)) then
8148 inddativarattr = index(v7d%dativarattr%i,v7d%dativar%r(inddativar))
8149 if (inddativarattr > 0 ) then
8150 v7d%voldatiattri &
8151 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
8152 v7d%voldatiattri &
8153 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
8154 end if
8155 end if
8156
8157 if (associated (v7d%dativarattr%r)) then
8158 inddativarattr = index(v7d%dativarattr%r,v7d%dativar%r(inddativar))
8159 if (inddativarattr > 0 ) then
8160 v7d%voldatiattrr &
8161 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
8162 v7d%voldatiattrr &
8163 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
8164 end if
8165 end if
8166
8167 if (associated (v7d%dativarattr%d)) then
8168 inddativarattr = index(v7d%dativarattr%d,v7d%dativar%r(inddativar))
8169 if (inddativarattr > 0 ) then
8170 v7d%voldatiattrd &
8171 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
8172 v7d%voldatiattrd &
8173 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
8174 end if
8175 end if
8176
8177 if (associated (v7d%dativarattr%b)) then
8178 inddativarattr = index(v7d%dativarattr%b,v7d%dativar%r(inddativar))
8179 if (inddativarattr > 0 ) then
8180 v7d%voldatiattrb &
8181 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
8182 v7d%voldatiattrb &
8183 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
8184 end if
8185 end if
8186
8187 if (associated (v7d%dativarattr%c)) then
8188 inddativarattr = index(v7d%dativarattr%c,v7d%dativar%r(inddativar))
8189 if (inddativarattr > 0 ) then
8190 v7d%voldatiattrc &
8191 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
8192 v7d%voldatiattrc &
8193 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
8194 end if
8195 end if
8196
8197 end if
8198
8199end do
8200
8201end subroutine move_datar
8202
8203
8204!> Reduce some dimensions (level and timerage) for semplification (rounding).
8205!! You can use this for simplify and use variables in computation like alchimia
8206!! where fields have to be on the same coordinate
8207!! It return real or character data only: if input is charcter data only it return character otherwise il return
8208!! all the data converted to real.
8209!! examples:
8210!! means in time for short periods and istantaneous values
8211!! 2 meter and surface levels
8212!! If there are data on more then one almost equal levels or timeranges, the first var present (at least one point)
8213!! will be taken (order is by icreasing var index).
8214!! You can use predefined values for classic semplification
8215!! almost_equal_levels and almost_equal_timeranges
8216!! The level or timerange in output will be defined by the first element of level and timerange list
8217subroutine v7d_rounding(v7din,v7dout,level,timerange,nostatproc)
8218type(vol7d),intent(inout) :: v7din !< input volume
8219type(vol7d),intent(out) :: v7dout !> output volume
8220type(vol7d_level),intent(in),optional :: level(:) !< almost equal level list
8221type(vol7d_timerange),intent(in),optional :: timerange(:) !< almost equal timerange list
8222!logical,intent(in),optional :: merge !< if there are data on more then one almost equal levels or timeranges
8223!! will be merged POINT BY POINT with priority for the fird data found ordered by icreasing var index
8224logical,intent(in),optional :: nostatproc !< do not take in account statistical processing code in timerange and P2
8225
8226integer :: nana,nlevel,ntime,ntimerange,nnetwork,nbin
8227integer :: iana,ilevel,itimerange,indl,indt,itime,inetwork
8228type(vol7d_level) :: roundlevel(size(v7din%level))
8229type(vol7d_timerange) :: roundtimerange(size(v7din%timerange))
8230type(vol7d) :: v7d_tmp
8231
8232
8233nbin=0
8234
8235if (associated(v7din%dativar%r)) nbin = nbin + size(v7din%dativar%r)
8236if (associated(v7din%dativar%i)) nbin = nbin + size(v7din%dativar%i)
8237if (associated(v7din%dativar%d)) nbin = nbin + size(v7din%dativar%d)
8238if (associated(v7din%dativar%b)) nbin = nbin + size(v7din%dativar%b)
8239
8240call init(v7d_tmp)
8241
8242roundlevel=v7din%level
8243
8244if (present(level))then
8245 do ilevel = 1, size(v7din%level)
8246 if ((any(v7din%level(ilevel) .almosteq. level))) then
8247 roundlevel(ilevel)=level(1)
8248 end if
8249 end do
8250end if
8251
8252roundtimerange=v7din%timerange
8253
8254if (present(timerange))then
8255 do itimerange = 1, size(v7din%timerange)
8256 if ((any(v7din%timerange(itimerange) .almosteq. timerange))) then
8257 roundtimerange(itimerange)=timerange(1)
8258 end if
8259 end do
8260end if
8261
8262!set istantaneous values everywere
8263!preserve p1 for forecast time
8264if (optio_log(nostatproc)) then
8265 roundtimerange(:)%timerange=254
8266 roundtimerange(:)%p2=0
8267end if
8268
8269
8270nana=size(v7din%ana)
8271nlevel=count_distinct(roundlevel,back=.true.)
8272ntime=size(v7din%time)
8273ntimerange=count_distinct(roundtimerange,back=.true.)
8274nnetwork=size(v7din%network)
8275
8276call init(v7d_tmp)
8277
8278if (nbin == 0) then
8279 call copy(v7din,v7d_tmp)
8280else
8281 call vol7d_convr(v7din,v7d_tmp)
8282end if
8283
8284v7d_tmp%level=roundlevel
8285v7d_tmp%timerange=roundtimerange
8286
8287do ilevel=1, size(v7d_tmp%level)
8288 indl=index(v7d_tmp%level,roundlevel(ilevel))
8289 do itimerange=1,size(v7d_tmp%timerange)
8290 indt=index(v7d_tmp%timerange,roundtimerange(itimerange))
8291
8292 if (indl /= ilevel .or. indt /= itimerange) then
8293
8294 do iana=1, nana
8295 do itime=1,ntime
8296 do inetwork=1,nnetwork
8297
8298 if (nbin > 0) then
8299 call move_datar (v7d_tmp,&
8300 iana,itime,ilevel,itimerange,inetwork,&
8301 iana,itime,indl,indt,inetwork)
8302 else
8303 call move_datac (v7d_tmp,&
8304 iana,itime,ilevel,itimerange,inetwork,&
8305 iana,itime,indl,indt,inetwork)
8306 end if
8307
8308 end do
8309 end do
8310 end do
8311
8312 end if
8313
8314 end do
8315end do
8316
8317! set to missing level and time > nlevel
8318do ilevel=nlevel+1,size(v7d_tmp%level)
8319 call init (v7d_tmp%level(ilevel))
8320end do
8321
8322do itimerange=ntimerange+1,size(v7d_tmp%timerange)
8323 call init (v7d_tmp%timerange(itimerange))
8324end do
8325
8326!copy with remove
8327CALL copy(v7d_tmp,v7dout,miss=.true.,lsort_timerange=.true.,lsort_level=.true.)
8328CALL delete(v7d_tmp)
8329
8330!call display(v7dout)
8331
8332end subroutine v7d_rounding
8333
8334
8335END MODULE vol7d_class
8336
8337!>\example esempio_qc_convert.f90
8338!!\brief Programma esempio semplice per la scrittura su file di un volume vol7d
8339!!
8340!!Programma che scrive su file un volume vol7d letto da una serie di file ASCII.
8341!!Questo programma scrive i dati del clima che poi verranno letti da modqccli
8342
8343
8344!>\example esempio_v7ddballe_move_and_collapse.f90
8345!!\brief ! Example program to reduce to one the dimensions of levels and time without loss of data
Set of functions that return a trimmed CHARACTER representation of the input variable.
Legge un oggetto datetime/timedelta o un vettore di oggetti datetime/timedelta da un file FORMATTED o...
Scrive un oggetto datetime/timedelta o un vettore di oggetti datetime/timedelta su un file FORMATTED ...
Index method.
Generic subroutine for checking OPTIONAL parameters.
Test for a missing volume.
Check for problems return 0 if all check passed print diagnostics with log4f.
Distruttore per la classe vol7d.
doubleprecision data conversion
Scrittura su file.
Costruttore per la classe vol7d.
integer data conversion
real data conversion
Reduce some dimensions (level and timerage) for semplification (rounding).
Represent data in a pretty string.
This module defines usefull general purpose function and subroutine.
Utilities for CHARACTER variables.
Classi per la gestione delle coordinate temporali.
Gestione degli errori.
Definition of constants to be used for declaring variables of a desired type.
Definition kinds.F90:245
classe per la gestione del logging
Module for quickly interpreting the OPTIONAL parameters passed to a subprogram.
Classe per la gestione dell'anagrafica di stazioni meteo e affini.
Classe per la gestione di un volume completo di dati osservati.
Classe per la gestione dei livelli verticali in osservazioni meteo e affini.
Classe per la gestione delle reti di stazioni per osservazioni meteo e affini.
Classe per la gestione degli intervalli temporali di osservazioni meteo e affini.
Classe per gestire un vettore di oggetti di tipo vol7d_var_class::vol7d_var.
Definisce un oggetto contenente i volumi anagrafica e dati e tutti i descrittori delle loro dimension...

Generated with Doxygen.