|
libsim Versione 8.0.0
|
◆ vol7d_get_voldatid()
Crea una vista a dimensione ridotta di un volume di dati di tipo DOUBLE PRECISION. È 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: DOUBLE PRECISION, POINTER :: vol2d(:,:)
...
CALL vol7d_get_voldatid(v7d1, (/vol7d_ana_d, vol7d_time_d/), vol2d)
IF (ASSOCIATED(vol2d)) THEN
print*,vol2d
...
ENDIF
return
Definizione alla linea 4322 del file vol7d_class.F90. 4324! Copyright (C) 2010 ARPA-SIM <urpsim@smr.arpa.emr.it>
4325! authors:
4326! Davide Cesari <dcesari@arpa.emr.it>
4327! Paolo Patruno <ppatruno@arpa.emr.it>
4328
4329! This program is free software; you can redistribute it and/or
4330! modify it under the terms of the GNU General Public License as
4331! published by the Free Software Foundation; either version 2 of
4332! the License, or (at your option) any later version.
4333
4334! This program is distributed in the hope that it will be useful,
4335! but WITHOUT ANY WARRANTY; without even the implied warranty of
4336! MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
4337! GNU General Public License for more details.
4338
4339! You should have received a copy of the GNU General Public License
4340! along with this program. If not, see <http://www.gnu.org/licenses/>.
4341#include "config.h"
4342
4343!> \defgroup vol7d Libsim package, vol7d library.
4344!! The libsim vol7d library contains classes for managing pointwise
4345!! data, tipically weather observations, and for their import from a
4346!! Db-All.e database or from a WMO BUFR file. In order to compile and
4347!! link programs using this library, you have to insert the required
4348!! \c USE statements in the program units involved, specify the
4349!! location of module files when compiling (tipically \c
4350!! -I/usr/lib/gfortran/modules or \c -I/usr/lib64/gfortran/modules or
4351!! \c -I/usr/include) and indicate the library name \c -lsim_vol7d
4352!! when linking, assuming that the library has been installed in a
4353!! default location.
4354
4355!> Classe per la gestione di un volume completo di dati osservati.
4356!! Questo modulo definisce gli oggetti e i metodi per gestire
4357!! volumi di dati meteorologici sparsi.
4358!! I volumi definiti sono principalmente di 4 categorie:
4359!! - volumi di anagrafica (vol7d::volanar & c.), hanno 3 dimensioni:
4360!! - anagrafica
4361!! - variabile di anagrafica
4362!! - rete
4363!! - volumi di attributi di anagrafica (vol7d::volanaattrr & c.), hanno 4 dimensioni:
4364!! - anagrafica
4365!! - variabile di anagrafica
4366!! - rete
4367!! - variabile di attributi delle variabili di anagrafica
4368!! - volumi di dati (vol7d::voldatir & c.), hanno 6 dimensioni:
4369!! - anagrafica
4370!! - tempo
4371!! - livello verticale
4372!! - intervallo temporale (timerange)
4373!! - variabile di dati
4374!! - rete
4375!! - volumi di attributi di dati (vol7d::voldatiattrr & c.), hanno 7 dimensioni:
4376!! - anagrafica
4377!! - tempo
4378!! - livello verticale
4379!! - intervallo temporale (timerange)
4380!! - variabile di dati
4381!! - rete
4382!! - variabile di attributi delle variabili di dati
4383!!
4384!! Tutte le variabili sono inoltre disponibil1 in 5 tipi diversi:
4385!! - reale (abbreviato r)
4386!! - doppia precisione (abbreviato d)
4387!! - intero (abbreviato i)
4388!! - byte (abbreviato b)
4389!! - carattere (abbreviato c)
4390!!
4391!! Per ognuna delle dimensioni possibili, incluse le variabili e gli
4392!! attributi con i loro diversi tipi,
4393!! è definito un cosiddetto "vettore di descrittori", con un
4394!! numero di elementi pari all'estensione della dimensione stessa,
4395!! che contiene le informazioni necessarie a descrivere
4396!! gli elementi di quella dimensione.
4397!! In realtà l'utente non dovrà generalmente occuparsi di costruire
4398!! un oggetto vol7d con le proprie mani ma utilizzerà nella maggior parte
4399!! dei casi i metodi di importazione preconfezionati che importano dati da
4400!! DB-All.e (vol7d_dballe_class) o dal DB Oracle del SIM (vol7d_oraclesim_class).
4401!!
4402!!
4403!! Il programma esempio_v7d.f90 contiene un esempio elementare di uso
4404!! della classe vol7d:
4405!! \include esempio_v7d.f90
4406!!
4407!! \ingroup vol7d
4415USE io_units
4422IMPLICIT NONE
4423
4424
4425INTEGER, PARAMETER :: vol7d_maxdim_a = 3, vol7d_maxdim_aa = 4, &
4426 vol7d_maxdim_d = 6, vol7d_maxdim_ad = 7
4427
4428INTEGER, PARAMETER :: vol7d_ana_a=1 !< indice della dimensione "anagrafica" nei volumi di anagrafica, da usare nei metodi vol7d_get_volana*
4429INTEGER, PARAMETER :: vol7d_var_a=2 !< indice della dimensione "variabile" nei volumi di anagrafica, da usare nei metodi vol7d_get_volana*
4430INTEGER, PARAMETER :: vol7d_network_a=3 !< indice della dimensione "rete" nei volumi di anagrafica, da usare nei metodi vol7d_get_volana*
4431INTEGER, PARAMETER :: vol7d_attr_a=4 !< indice della dimensione "attributo" nei volumi di anagrafica, da usare nei metodi vol7d_get_volana*
4432INTEGER, PARAMETER :: vol7d_ana_d=1 !< indice della dimensione "anagrafica" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
4433INTEGER, PARAMETER :: vol7d_time_d=2 !< indice della dimensione "tempo" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
4434INTEGER, PARAMETER :: vol7d_level_d=3 !< indice della dimensione "livello verticale" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
4435INTEGER, PARAMETER :: vol7d_timerange_d=4 !< indice della dimensione "intervallo temporale" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
4436INTEGER, PARAMETER :: vol7d_var_d=5 !< indice della dimensione "variabile" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
4437INTEGER, PARAMETER :: vol7d_network_d=6 !< indice della dimensione "rete" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
4438INTEGER, PARAMETER :: vol7d_attr_d=7 !< indice della dimensione "attributo" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
4439INTEGER, PARAMETER :: vol7d_cdatalen=32
4440
4441TYPE vol7d_varmap
4442 INTEGER :: r, d, i, b, c
4443END TYPE vol7d_varmap
4444
4445!> Definisce un oggetto contenente i volumi anagrafica e dati e tutti
4446!! i descrittori delle loro dimensioni.
4448!> vettore descrittore della dimensione anagrafica
4449 TYPE(vol7d_ana),POINTER :: ana(:)
4450!> vettore descrittore della dimensione tempo
4451 TYPE(datetime),POINTER :: time(:)
4452!> vettore descrittore della dimensione livello verticale
4453 TYPE(vol7d_level),POINTER :: level(:)
4454!> vettore descrittore della dimensione intervallo temporale (timerange)
4455 TYPE(vol7d_timerange),POINTER :: timerange(:)
4456!> vettore descrittore della dimensione rete
4457 TYPE(vol7d_network),POINTER :: network(:)
4458!> vettore descrittore della dimensione variabile di anagrafica
4459 TYPE(vol7d_varvect) :: anavar
4460!> vettore descrittore della dimensione attributo delle variabili di anagrafica
4461 TYPE(vol7d_varvect) :: anaattr
4462!> vettore descrittore della dimensione variabile di anagrafica che ha tali attributi
4463 TYPE(vol7d_varvect) :: anavarattr
4464!> vettore descrittore della dimensione variabile di dati
4465 TYPE(vol7d_varvect) :: dativar
4466!> vettore descrittore della dimensione attributo delle variabili di dati
4467 TYPE(vol7d_varvect) :: datiattr
4468!> vettore descrittore della dimensione variabile di dati che ha tali attributi
4469 TYPE(vol7d_varvect) :: dativarattr
4470
4471!> volume di anagrafica a valori reali
4472 REAL,POINTER :: volanar(:,:,:)
4473!> volume di anagrafica a valori a doppia precisione
4474 DOUBLE PRECISION,POINTER :: volanad(:,:,:)
4475!> volume di anagrafica a valori interi
4476 INTEGER,POINTER :: volanai(:,:,:)
4477!> volume di anagrafica a valori byte
4478 INTEGER(kind=int_b),POINTER :: volanab(:,:,:)
4479!> volume di anagrafica a valori carattere
4480 CHARACTER(len=vol7d_cdatalen),POINTER :: volanac(:,:,:)
4481
4482!> volume di attributi di anagrafica a valori reali
4483 REAL,POINTER :: volanaattrr(:,:,:,:)
4484!> volume di attributi di anagrafica a valori a doppia precisione
4485 DOUBLE PRECISION,POINTER :: volanaattrd(:,:,:,:)
4486!> volume di attributi di anagrafica a valori interi
4487 INTEGER,POINTER :: volanaattri(:,:,:,:)
4488!> volume di attributi di anagrafica a valori byte
4489 INTEGER(kind=int_b),POINTER :: volanaattrb(:,:,:,:)
4490!> volume di attributi di anagrafica a valori carattere
4491 CHARACTER(len=vol7d_cdatalen),POINTER :: volanaattrc(:,:,:,:)
4492
4493!> volume di dati a valori reali
4494 REAL,POINTER :: voldatir(:,:,:,:,:,:) ! sono i dati
4495!> volume di dati a valori a doppia precisione
4496 DOUBLE PRECISION,POINTER :: voldatid(:,:,:,:,:,:)
4497!> volume di dati a valori interi
4498 INTEGER,POINTER :: voldatii(:,:,:,:,:,:)
4499!> volume di dati a valori byte
4500 INTEGER(kind=int_b),POINTER :: voldatib(:,:,:,:,:,:)
4501!> volume di dati a valori carattere
4502 CHARACTER(len=vol7d_cdatalen),POINTER :: voldatic(:,:,:,:,:,:)
4503
4504!> volume di attributi di dati a valori reali
4505 REAL,POINTER :: voldatiattrr(:,:,:,:,:,:,:)
4506!> volume di attributi di dati a valori a doppia precisione
4507 DOUBLE PRECISION,POINTER :: voldatiattrd(:,:,:,:,:,:,:)
4508!> volume di attributi di dati a valori interi
4509 INTEGER,POINTER :: voldatiattri(:,:,:,:,:,:,:)
4510!> volume di attributi di dati a valori byte
4511 INTEGER(kind=int_b),POINTER :: voldatiattrb(:,:,:,:,:,:,:)
4512!> volume di attributi di dati a valori carattere
4513 CHARACTER(len=vol7d_cdatalen),POINTER :: voldatiattrc(:,:,:,:,:,:,:)
4514
4515!> time definition; 0=time is reference time, 1=time is validity time
4516 integer :: time_definition
4517
4519
4520!> Costruttore per la classe vol7d.
4521!! Deve essere richiamato
4522!! per tutti gli oggetti di questo tipo definiti in un programma.
4524 MODULE PROCEDURE vol7d_init
4525END INTERFACE
4526
4527!> Distruttore per la classe vol7d.
4529 MODULE PROCEDURE vol7d_delete
4530END INTERFACE
4531
4532!> Scrittura su file.
4534 MODULE PROCEDURE vol7d_write_on_file
4535END INTERFACE
4536
4537!> Lettura da file.
4538INTERFACE import
4539 MODULE PROCEDURE vol7d_read_from_file
4540END INTERFACE
4541
4542!>Print object
4544 MODULE PROCEDURE vol7d_display, dat_display, dat_vect_display
4545END INTERFACE
4546
4547!>Represent data in a pretty string
4549 MODULE PROCEDURE to_char_dat
4550END INTERFACE
4551
4552!>doubleprecision data conversion
4554 MODULE PROCEDURE doubledatd,doubledatr,doubledati,doubledatb,doubledatc
4555END INTERFACE
4556
4557!>real data conversion
4559 MODULE PROCEDURE realdatd,realdatr,realdati,realdatb,realdatc
4560END INTERFACE
4561
4562!>integer data conversion
4564 MODULE PROCEDURE integerdatd,integerdatr,integerdati,integerdatb,integerdatc
4565END INTERFACE
4566
4567!>copy object
4569 MODULE PROCEDURE vol7d_copy
4570END INTERFACE
4571
4572!> Test for a missing volume
4574 MODULE PROCEDURE vol7d_c_e
4575END INTERFACE
4576
4577!> Check for problems
4578!! return 0 if all check passed
4579!! print diagnostics with log4f
4581 MODULE PROCEDURE vol7d_check
4582END INTERFACE
4583
4584!> Reduce some dimensions (level and timerage) for semplification (rounding).
4585!! You can use this for simplify and use variables in computation like alchimia
4586!! where fields have to be on the same coordinate
4587!! It return real or character data only: if input is charcter data only it return character otherwise il return
4588!! all the data converted to real.
4589!! examples:
4590!! means in time for short periods and istantaneous values
4591!! 2 meter and surface levels
4592!! If there are data on more then one almost equal levels or timeranges, the first var present (at least one point)
4593!! will be taken (order is by icreasing var index).
4594!! You can use predefined values for classic semplification
4595!! almost_equal_levels and almost_equal_timeranges
4596!! The level or timerange in output will be defined by the first element of level and timerange list
4598 MODULE PROCEDURE v7d_rounding
4599END INTERFACE
4600
4601!!$INTERFACE get_volana
4602!!$ MODULE PROCEDURE vol7d_get_volanar, vol7d_get_volanad, vol7d_get_volanai, &
4603!!$ vol7d_get_volanab, vol7d_get_volanac
4604!!$END INTERFACE
4605!!$
4606!!$INTERFACE get_voldati
4607!!$ MODULE PROCEDURE vol7d_get_voldatir, vol7d_get_voldatid, vol7d_get_voldatii, &
4608!!$ vol7d_get_voldatib, vol7d_get_voldatic
4609!!$END INTERFACE
4610!!$
4611!!$INTERFACE get_volanaattr
4612!!$ MODULE PROCEDURE vol7d_get_volanaattrr, vol7d_get_volanaattrd, &
4613!!$ vol7d_get_volanaattri, vol7d_get_volanaattrb, vol7d_get_volanaattrc
4614!!$END INTERFACE
4615!!$
4616!!$INTERFACE get_voldatiattr
4617!!$ MODULE PROCEDURE vol7d_get_voldatiattrr, vol7d_get_voldatiattrd, &
4618!!$ vol7d_get_voldatiattri, vol7d_get_voldatiattrb, vol7d_get_voldatiattrc
4619!!$END INTERFACE
4620
4621PRIVATE vol7d_get_volr, vol7d_get_vold, vol7d_get_voli, vol7d_get_volb, &
4622 vol7d_get_volc, &
4623 volptr1dr, volptr2dr, volptr3dr, volptr4dr, volptr5dr, volptr6dr, volptr7dr, &
4624 volptr1dd, volptr2dd, volptr3dd, volptr4dd, volptr5dd, volptr6dd, volptr7dd, &
4625 volptr1di, volptr2di, volptr3di, volptr4di, volptr5di, volptr6di, volptr7di, &
4626 volptr1db, volptr2db, volptr3db, volptr4db, volptr5db, volptr6db, volptr7db, &
4627 volptr1dc, volptr2dc, volptr3dc, volptr4dc, volptr5dc, volptr6dc, volptr7dc, &
4628 vol7d_nullifyr, vol7d_nullifyd, vol7d_nullifyi, vol7d_nullifyb, vol7d_nullifyc, &
4629 vol7d_init, vol7d_delete, vol7d_write_on_file, vol7d_read_from_file, &
4630 vol7d_check_alloc_ana, vol7d_force_alloc_ana, &
4631 vol7d_check_alloc_dati, vol7d_force_alloc_dati, vol7d_force_alloc, &
4632 vol7d_display, dat_display, dat_vect_display, &
4633 to_char_dat, vol7d_check
4634
4635PRIVATE doubledatd,doubledatr,doubledati,doubledatb,doubledatc
4636
4637PRIVATE vol7d_c_e
4638
4639CONTAINS
4640
4641
4642!> Inizializza un oggetto di tipo vol7d.
4643!! Non riceve alcun parametro tranne l'oggetto stesso. Attenzione, è necessario
4644!! comunque chiamare sempre il costruttore per evitare di avere dei puntatori in
4645!! uno stato indefinito.
4646SUBROUTINE vol7d_init(this,time_definition)
4647TYPE(vol7d),intent(out) :: this !< oggetto da inizializzare
4648INTEGER,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)
4649
4656
4657NULLIFY(this%ana, this%time, this%level, this%timerange, this%network)
4658
4659NULLIFY(this%volanar, this%volanaattrr, this%voldatir, this%voldatiattrr)
4660NULLIFY(this%volanad, this%volanaattrd, this%voldatid, this%voldatiattrd)
4661NULLIFY(this%volanai, this%volanaattri, this%voldatii, this%voldatiattri)
4662NULLIFY(this%volanab, this%volanaattrb, this%voldatib, this%voldatiattrb)
4663NULLIFY(this%volanac, this%volanaattrc, this%voldatic, this%voldatiattrc)
4664
4665if(present(time_definition)) then
4666 this%time_definition=time_definition
4667else
4668 this%time_definition=1 !default to validity time
4669end if
4670
4671END SUBROUTINE vol7d_init
4672
4673
4674!> Distrugge l'oggetto in maniera pulita, liberando l'eventuale memoria
4675!! dinamicamente allocata. Permette di distruggere la sola parte di dati
4676!! mantenendo l'anagrafica.
4677ELEMENTAL SUBROUTINE vol7d_delete(this, dataonly)
4678TYPE(vol7d),intent(inout) :: this !< oggetto da distruggere
4679LOGICAL, INTENT(in), OPTIONAL :: dataonly !< dealloca solo i dati, tenendo l'anagrafica, (default \c .FALSE.)
4680
4681
4682IF (.NOT. optio_log(dataonly)) THEN
4683 IF (ASSOCIATED(this%volanar)) DEALLOCATE(this%volanar)
4684 IF (ASSOCIATED(this%volanad)) DEALLOCATE(this%volanad)
4685 IF (ASSOCIATED(this%volanai)) DEALLOCATE(this%volanai)
4686 IF (ASSOCIATED(this%volanab)) DEALLOCATE(this%volanab)
4687 IF (ASSOCIATED(this%volanac)) DEALLOCATE(this%volanac)
4688 IF (ASSOCIATED(this%volanaattrr)) DEALLOCATE(this%volanaattrr)
4689 IF (ASSOCIATED(this%volanaattrd)) DEALLOCATE(this%volanaattrd)
4690 IF (ASSOCIATED(this%volanaattri)) DEALLOCATE(this%volanaattri)
4691 IF (ASSOCIATED(this%volanaattrb)) DEALLOCATE(this%volanaattrb)
4692 IF (ASSOCIATED(this%volanaattrc)) DEALLOCATE(this%volanaattrc)
4693ENDIF
4694IF (ASSOCIATED(this%voldatir)) DEALLOCATE(this%voldatir)
4695IF (ASSOCIATED(this%voldatid)) DEALLOCATE(this%voldatid)
4696IF (ASSOCIATED(this%voldatii)) DEALLOCATE(this%voldatii)
4697IF (ASSOCIATED(this%voldatib)) DEALLOCATE(this%voldatib)
4698IF (ASSOCIATED(this%voldatic)) DEALLOCATE(this%voldatic)
4699IF (ASSOCIATED(this%voldatiattrr)) DEALLOCATE(this%voldatiattrr)
4700IF (ASSOCIATED(this%voldatiattrd)) DEALLOCATE(this%voldatiattrd)
4701IF (ASSOCIATED(this%voldatiattri)) DEALLOCATE(this%voldatiattri)
4702IF (ASSOCIATED(this%voldatiattrb)) DEALLOCATE(this%voldatiattrb)
4703IF (ASSOCIATED(this%voldatiattrc)) DEALLOCATE(this%voldatiattrc)
4704
4705IF (.NOT. optio_log(dataonly)) THEN
4706 IF (ASSOCIATED(this%ana)) DEALLOCATE(this%ana)
4707 IF (ASSOCIATED(this%network)) DEALLOCATE(this%network)
4708ENDIF
4709IF (ASSOCIATED(this%time)) DEALLOCATE(this%time)
4710IF (ASSOCIATED(this%level)) DEALLOCATE(this%level)
4711IF (ASSOCIATED(this%timerange)) DEALLOCATE(this%timerange)
4712
4713IF (.NOT. optio_log(dataonly)) THEN
4717ENDIF
4721
4722END SUBROUTINE vol7d_delete
4723
4724
4725
4726integer function vol7d_check(this)
4727TYPE(vol7d),intent(in) :: this !< object to check
4728integer :: i,j,k,l,m,n
4729
4730vol7d_check=0
4731
4732if (associated(this%voldatii)) then
4733do i = 1,size(this%voldatii,1)
4734 do j = 1,size(this%voldatii,2)
4735 do k = 1,size(this%voldatii,3)
4736 do l = 1,size(this%voldatii,4)
4737 do m = 1,size(this%voldatii,5)
4738 do n = 1,size(this%voldatii,6)
4739 if (this%voldatii(i,j,k,l,m,n) /= this%voldatii(i,j,k,l,m,n) ) then
4740 CALL l4f_log(l4f_warn,"check: abnormal value at voldatii("&
4742 vol7d_check=1
4743 end if
4744 end do
4745 end do
4746 end do
4747 end do
4748 end do
4749end do
4750end if
4751
4752
4753if (associated(this%voldatir)) then
4754do i = 1,size(this%voldatir,1)
4755 do j = 1,size(this%voldatir,2)
4756 do k = 1,size(this%voldatir,3)
4757 do l = 1,size(this%voldatir,4)
4758 do m = 1,size(this%voldatir,5)
4759 do n = 1,size(this%voldatir,6)
4760 if (this%voldatir(i,j,k,l,m,n) /= this%voldatir(i,j,k,l,m,n) ) then
4761 CALL l4f_log(l4f_warn,"check: abnormal value at voldatir("&
4763 vol7d_check=2
4764 end if
4765 end do
4766 end do
4767 end do
4768 end do
4769 end do
4770end do
4771end if
4772
4773if (associated(this%voldatid)) then
4774do i = 1,size(this%voldatid,1)
4775 do j = 1,size(this%voldatid,2)
4776 do k = 1,size(this%voldatid,3)
4777 do l = 1,size(this%voldatid,4)
4778 do m = 1,size(this%voldatid,5)
4779 do n = 1,size(this%voldatid,6)
4780 if (this%voldatid(i,j,k,l,m,n) /= this%voldatid(i,j,k,l,m,n) ) then
4781 CALL l4f_log(l4f_warn,"check: abnormal value at voldatid("&
4783 vol7d_check=3
4784 end if
4785 end do
4786 end do
4787 end do
4788 end do
4789 end do
4790end do
4791end if
4792
4793if (associated(this%voldatib)) then
4794do i = 1,size(this%voldatib,1)
4795 do j = 1,size(this%voldatib,2)
4796 do k = 1,size(this%voldatib,3)
4797 do l = 1,size(this%voldatib,4)
4798 do m = 1,size(this%voldatib,5)
4799 do n = 1,size(this%voldatib,6)
4800 if (this%voldatib(i,j,k,l,m,n) /= this%voldatib(i,j,k,l,m,n) ) then
4801 CALL l4f_log(l4f_warn,"check: abnormal value at voldatib("&
4803 vol7d_check=4
4804 end if
4805 end do
4806 end do
4807 end do
4808 end do
4809 end do
4810end do
4811end if
4812
4813end function vol7d_check
4814
4815
4816
4817!TODO da completare ! aborta se i volumi sono allocati a dimensione 0
4818!> stampa a video una sintesi del contenuto
4819SUBROUTINE vol7d_display(this)
4820TYPE(vol7d),intent(in) :: this !< oggetto da visualizzare
4821integer :: i
4822
4823REAL :: rdat
4824DOUBLE PRECISION :: ddat
4825INTEGER :: idat
4826INTEGER(kind=int_b) :: bdat
4827CHARACTER(len=vol7d_cdatalen) :: cdat
4828
4829
4830print*,"<<<<<<<<<<<<<<<<<<< vol7d object >>>>>>>>>>>>>>>>>>>>"
4831if (this%time_definition == 0) then
4832 print*,"TIME DEFINITION: time is reference time"
4833else if (this%time_definition == 1) then
4834 print*,"TIME DEFINITION: time is validity time"
4835else if (this%time_definition == 2) then
4836 print*,"TIME DEFINITION: time is validity time, forecast range forced to 0"
4837else
4838 print*,"Time definition has a wrong walue:", this%time_definition
4839end if
4840
4841IF (ASSOCIATED(this%network))then
4842 print*,"---- network vector ----"
4843 print*,"elements=",size(this%network)
4844 do i=1, size(this%network)
4846 end do
4847end IF
4848
4849IF (ASSOCIATED(this%ana))then
4850 print*,"---- ana vector ----"
4851 print*,"elements=",size(this%ana)
4852 do i=1, size(this%ana)
4854 end do
4855end IF
4856
4857IF (ASSOCIATED(this%time))then
4858 print*,"---- time vector ----"
4859 print*,"elements=",size(this%time)
4860 do i=1, size(this%time)
4862 end do
4863end if
4864
4865IF (ASSOCIATED(this%level)) then
4866 print*,"---- level vector ----"
4867 print*,"elements=",size(this%level)
4868 do i =1,size(this%level)
4870 end do
4871end if
4872
4873IF (ASSOCIATED(this%timerange))then
4874 print*,"---- timerange vector ----"
4875 print*,"elements=",size(this%timerange)
4876 do i =1,size(this%timerange)
4878 end do
4879end if
4880
4881
4882print*,"---- ana vector ----"
4883print*,""
4884print*,"->>>>>>>>> anavar -"
4886print*,""
4887print*,"->>>>>>>>> anaattr -"
4889print*,""
4890print*,"->>>>>>>>> anavarattr -"
4892
4893print*,"-- ana data section (first point) --"
4894
4895idat=imiss
4896rdat=rmiss
4897ddat=dmiss
4898bdat=ibmiss
4899cdat=cmiss
4900
4901!ntime = MIN(SIZE(this%time),nprint)
4902!ntimerange = MIN(SIZE(this%timerange),nprint)
4903!nlevel = MIN(SIZE(this%level),nprint)
4904!nnetwork = MIN(SIZE(this%network),nprint)
4905!nana = MIN(SIZE(this%ana),nprint)
4906
4907IF (SIZE(this%ana) > 0 .AND. SIZE(this%network) > 0) THEN
4908if (associated(this%volanai)) then
4909 do i=1,size(this%anavar%i)
4910 idat=this%volanai(1,i,1)
4912 end do
4913end if
4914idat=imiss
4915
4916if (associated(this%volanar)) then
4917 do i=1,size(this%anavar%r)
4918 rdat=this%volanar(1,i,1)
4920 end do
4921end if
4922rdat=rmiss
4923
4924if (associated(this%volanad)) then
4925 do i=1,size(this%anavar%d)
4926 ddat=this%volanad(1,i,1)
4928 end do
4929end if
4930ddat=dmiss
4931
4932if (associated(this%volanab)) then
4933 do i=1,size(this%anavar%b)
4934 bdat=this%volanab(1,i,1)
4936 end do
4937end if
4938bdat=ibmiss
4939
4940if (associated(this%volanac)) then
4941 do i=1,size(this%anavar%c)
4942 cdat=this%volanac(1,i,1)
4944 end do
4945end if
4946cdat=cmiss
4947ENDIF
4948
4949print*,"---- data vector ----"
4950print*,""
4951print*,"->>>>>>>>> dativar -"
4953print*,""
4954print*,"->>>>>>>>> datiattr -"
4956print*,""
4957print*,"->>>>>>>>> dativarattr -"
4959
4960print*,"-- data data section (first point) --"
4961
4962idat=imiss
4963rdat=rmiss
4964ddat=dmiss
4965bdat=ibmiss
4966cdat=cmiss
4967
4968IF (SIZE(this%ana) > 0 .AND. SIZE(this%network) > 0 .AND. size(this%time) > 0 &
4969 .AND. size(this%level) > 0 .AND. size(this%timerange) > 0) THEN
4970if (associated(this%voldatii)) then
4971 do i=1,size(this%dativar%i)
4972 idat=this%voldatii(1,1,1,1,i,1)
4974 end do
4975end if
4976idat=imiss
4977
4978if (associated(this%voldatir)) then
4979 do i=1,size(this%dativar%r)
4980 rdat=this%voldatir(1,1,1,1,i,1)
4982 end do
4983end if
4984rdat=rmiss
4985
4986if (associated(this%voldatid)) then
4987 do i=1,size(this%dativar%d)
4988 ddat=this%voldatid(1,1,1,1,i,1)
4990 end do
4991end if
4992ddat=dmiss
4993
4994if (associated(this%voldatib)) then
4995 do i=1,size(this%dativar%b)
4996 bdat=this%voldatib(1,1,1,1,i,1)
4998 end do
4999end if
5000bdat=ibmiss
5001
5002if (associated(this%voldatic)) then
5003 do i=1,size(this%dativar%c)
5004 cdat=this%voldatic(1,1,1,1,i,1)
5006 end do
5007end if
5008cdat=cmiss
5009ENDIF
5010
5011print*,"<<<<<<<<<<<<<<<<<<< END vol7d object >>>>>>>>>>>>>>>>>>>>"
5012
5013END SUBROUTINE vol7d_display
5014
5015
5016!> stampa a video una sintesi del contenuto
5017SUBROUTINE dat_display(this,idat,rdat,ddat,bdat,cdat)
5018TYPE(vol7d_var),intent(in) :: this !< oggetto da visualizzare
5019!> real
5020REAL :: rdat
5021!> double precision
5022DOUBLE PRECISION :: ddat
5023!> integer
5024INTEGER :: idat
5025!> byte
5026INTEGER(kind=int_b) :: bdat
5027!> character
5028CHARACTER(len=*) :: cdat
5029
5030print *, to_char_dat(this,idat,rdat,ddat,bdat,cdat)
5031
5032end SUBROUTINE dat_display
5033
5034!> stampa a video una sintesi del contenuto
5035SUBROUTINE dat_vect_display(this,idat,rdat,ddat,bdat,cdat)
5036
5037TYPE(vol7d_var),intent(in) :: this(:) !< oggetto da visualizzare
5038!> real
5039REAL :: rdat(:)
5040!> double precision
5041DOUBLE PRECISION :: ddat(:)
5042!> integer
5043INTEGER :: idat(:)
5044!> byte
5045INTEGER(kind=int_b) :: bdat(:)
5046!> character
5047CHARACTER(len=*):: cdat(:)
5048
5049integer :: i
5050
5051do i =1,size(this)
5053end do
5054
5055end SUBROUTINE dat_vect_display
5056
5057
5058FUNCTION to_char_dat(this,idat,rdat,ddat,bdat,cdat)
5059#ifdef HAVE_DBALLE
5060USE dballef
5061#endif
5062TYPE(vol7d_var),INTENT(in) :: this
5063!> real
5064REAL :: rdat
5065!> double precision
5066DOUBLE PRECISION :: ddat
5067!> integer
5068INTEGER :: idat
5069!> byte
5070INTEGER(kind=int_b) :: bdat
5071!> character
5072CHARACTER(len=*) :: cdat
5073CHARACTER(len=80) :: to_char_dat
5074
5075CHARACTER(len=LEN(to_char_dat)) :: to_char_tmp
5076
5077
5078#ifdef HAVE_DBALLE
5079INTEGER :: handle, ier
5080
5081handle = 0
5082to_char_dat="VALUE: "
5083
5088
5090 ier = idba_messaggi(handle,"/dev/null", "w", "BUFR")
5091 ier = idba_spiegab(handle,this%btable,cdat,to_char_tmp)
5092 ier = idba_fatto(handle)
5093 to_char_dat=trim(to_char_dat)//" ;char> "//trim(to_char_tmp)
5094endif
5095
5096#else
5097
5098to_char_dat="VALUE: "
5104
5105#endif
5106
5107END FUNCTION to_char_dat
5108
5109
5110!> Tests whether anything has ever been assigned to a vol7d object
5111!! (.TRUE.) or it is as clean as after an init (.FALSE.).
5112FUNCTION vol7d_c_e(this) RESULT(c_e)
5113TYPE(vol7d), INTENT(in) :: this
5114
5115LOGICAL :: c_e
5116
5118 ASSOCIATED(this%level) .OR. ASSOCIATED(this%timerange) .OR. &
5119 ASSOCIATED(this%network) .OR. &
5120 ASSOCIATED(this%anavar%r) .OR. ASSOCIATED(this%anavar%d) .OR. &
5121 ASSOCIATED(this%anavar%i) .OR. ASSOCIATED(this%anavar%b) .OR. &
5122 ASSOCIATED(this%anavar%c) .OR. &
5123 ASSOCIATED(this%anaattr%r) .OR. ASSOCIATED(this%anaattr%d) .OR. &
5124 ASSOCIATED(this%anaattr%i) .OR. ASSOCIATED(this%anaattr%b) .OR. &
5125 ASSOCIATED(this%anaattr%c) .OR. &
5126 ASSOCIATED(this%dativar%r) .OR. ASSOCIATED(this%dativar%d) .OR. &
5127 ASSOCIATED(this%dativar%i) .OR. ASSOCIATED(this%dativar%b) .OR. &
5128 ASSOCIATED(this%dativar%c) .OR. &
5129 ASSOCIATED(this%datiattr%r) .OR. ASSOCIATED(this%datiattr%d) .OR. &
5130 ASSOCIATED(this%datiattr%i) .OR. ASSOCIATED(this%datiattr%b) .OR. &
5131 ASSOCIATED(this%datiattr%c)
5132
5133END FUNCTION vol7d_c_e
5134
5135
5136!> Metodo per allocare i descrittori delle 7 dimensioni.
5137!! Riceve un grande numero di parametri opzionali che
5138!! indicano quali descrittori allocare e con quale estensione;
5139!! i descrittori non specificati non vengono toccati.
5140!! Può essere quindi chiamato più volte allocando via via
5141!! descrittori relativi a dimensioni diverse.
5142!! Se un descrittore richiesto è già allocato, viene deallocato
5143!! (perdendone l'eventuale contenuto) e riallocato con l'estensione
5144!! richiesta.
5145!! Per i descrittori relativi a dimensioni che non siano variabili o attributi,
5146!! è possibile specificare l'estensione di una dimensione a 0,
5147!! in tal caso il descrittore viene comunque allocato con lunghezza nulla,
5148!! che è diverso da non allocarlo. Per i descrittori di variabili e attributi
5149!! passare un'estensione 0 equivale a non fornire il parametro.
5150!! Avere uno o più descrittori dimensionati con estensione nulla fa sì
5151!! che anche il volume dati successivamente allocato abbia estensione nulla;
5152!! sebbene ciò appaia inutile, un volume del genere può in realtà servire,
5153!! in associazione ai metodi ::vol7d_merge o ::vol7d_append per estendere
5154!! un volume esistente aggiungendo elementi in alcune dimensioni (quelle
5155!! a estensione non nulla, ovviamente) e mantenendo invariato tutto il resto.
5156!! Per quanto riguarda i descrittori delle dimensioni relative alle
5157!! variabili, la relativa estensione è specificata con la nomenclatura
5158!! \a n<x><y><z> dove <x> può valere:
5159!! - \a ana per variabili relative a voumi di anagrafica
5160!! - \a dati per variabili relative a voumi di dati
5161!!
5162!! <y> può valere:
5163!! - \a var per variabili
5164!! - \a attr per attributi
5165!! - \a varattr variabili aventi attributi nei volumi di attributi
5166!!
5167!! <z> può valere:
5168!! - \a r per variabili o attributi a valori reali
5169!! - \a d per variabili o attributi a valori a doppia precisione
5170!! - \a i per variabili o attributi a valori interi
5171!! - \a b per variabili o attributi a valori byte
5172!! - \a c per variabili o attributi a valori carattere
5173!!
5174SUBROUTINE vol7d_alloc(this, nana, ntime, nlevel, ntimerange, nnetwork, &
5175 nanavarr, nanavard, nanavari, nanavarb, nanavarc, &
5176 nanaattrr, nanaattrd, nanaattri, nanaattrb, nanaattrc, &
5177 nanavarattrr, nanavarattrd, nanavarattri, nanavarattrb, nanavarattrc, &
5178 ndativarr, ndativard, ndativari, ndativarb, ndativarc, &
5179 ndatiattrr, ndatiattrd, ndatiattri, ndatiattrb, ndatiattrc, &
5180 ndativarattrr, ndativarattrd, ndativarattri, ndativarattrb, ndativarattrc, &
5181 ini)
5182TYPE(vol7d),INTENT(inout) :: this !< oggetto di cui allocare i descrittori
5183INTEGER,INTENT(in),OPTIONAL :: nana !< estensione della dimensione anagrafica
5184INTEGER,INTENT(in),OPTIONAL :: ntime !< estensione della dimensione tempo
5185INTEGER,INTENT(in),OPTIONAL :: nlevel !< estensione della dimensione livello varticale
5186INTEGER,INTENT(in),OPTIONAL :: ntimerange !< estensione della dimensione intervallo temporale (timerange)
5187INTEGER,INTENT(in),OPTIONAL :: nnetwork !< estensione della dimensione rete
5188!> estensione delle possibili dimensioni variabile
5189INTEGER,INTENT(in),OPTIONAL :: &
5190 nanavarr, nanavard, nanavari, nanavarb, nanavarc, &
5191 nanaattrr, nanaattrd, nanaattri, nanaattrb, nanaattrc, &
5192 nanavarattrr, nanavarattrd, nanavarattri, nanavarattrb, nanavarattrc, &
5193 ndativarr, ndativard, ndativari, ndativarb, ndativarc, &
5194 ndatiattrr, ndatiattrd, ndatiattri, ndatiattrb, ndatiattrc, &
5195 ndativarattrr, ndativarattrd, ndativarattri, ndativarattrb, ndativarattrc
5196LOGICAL,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
5197
5198INTEGER :: i
5199LOGICAL :: linit
5200
5201IF (PRESENT(ini)) THEN
5202 linit = ini
5203ELSE
5204 linit = .false.
5205ENDIF
5206
5207! Dimensioni principali
5208IF (PRESENT(nana)) THEN
5209 IF (nana >= 0) THEN
5210 IF (ASSOCIATED(this%ana)) DEALLOCATE(this%ana)
5211 ALLOCATE(this%ana(nana))
5212 IF (linit) THEN
5213 DO i = 1, nana
5215 ENDDO
5216 ENDIF
5217 ENDIF
5218ENDIF
5219IF (PRESENT(ntime)) THEN
5220 IF (ntime >= 0) THEN
5221 IF (ASSOCIATED(this%time)) DEALLOCATE(this%time)
5222 ALLOCATE(this%time(ntime))
5223 IF (linit) THEN
5224 DO i = 1, ntime
5226 ENDDO
5227 ENDIF
5228 ENDIF
5229ENDIF
5230IF (PRESENT(nlevel)) THEN
5231 IF (nlevel >= 0) THEN
5232 IF (ASSOCIATED(this%level)) DEALLOCATE(this%level)
5233 ALLOCATE(this%level(nlevel))
5234 IF (linit) THEN
5235 DO i = 1, nlevel
5237 ENDDO
5238 ENDIF
5239 ENDIF
5240ENDIF
5241IF (PRESENT(ntimerange)) THEN
5242 IF (ntimerange >= 0) THEN
5243 IF (ASSOCIATED(this%timerange)) DEALLOCATE(this%timerange)
5244 ALLOCATE(this%timerange(ntimerange))
5245 IF (linit) THEN
5246 DO i = 1, ntimerange
5248 ENDDO
5249 ENDIF
5250 ENDIF
5251ENDIF
5252IF (PRESENT(nnetwork)) THEN
5253 IF (nnetwork >= 0) THEN
5254 IF (ASSOCIATED(this%network)) DEALLOCATE(this%network)
5255 ALLOCATE(this%network(nnetwork))
5256 IF (linit) THEN
5257 DO i = 1, nnetwork
5259 ENDDO
5260 ENDIF
5261 ENDIF
5262ENDIF
5263! Dimensioni dei tipi delle variabili
5264CALL vol7d_varvect_alloc(this%anavar, nanavarr, nanavard, &
5265 nanavari, nanavarb, nanavarc, ini)
5266CALL vol7d_varvect_alloc(this%anaattr, nanaattrr, nanaattrd, &
5267 nanaattri, nanaattrb, nanaattrc, ini)
5268CALL vol7d_varvect_alloc(this%anavarattr, nanavarattrr, nanavarattrd, &
5269 nanavarattri, nanavarattrb, nanavarattrc, ini)
5270CALL vol7d_varvect_alloc(this%dativar, ndativarr, ndativard, &
5271 ndativari, ndativarb, ndativarc, ini)
5272CALL vol7d_varvect_alloc(this%datiattr, ndatiattrr, ndatiattrd, &
5273 ndatiattri, ndatiattrb, ndatiattrc, ini)
5274CALL vol7d_varvect_alloc(this%dativarattr, ndativarattrr, ndativarattrd, &
5275 ndativarattri, ndativarattrb, ndativarattrc, ini)
5276
5277END SUBROUTINE vol7d_alloc
5278
5279
5280FUNCTION vol7d_check_alloc_ana(this)
5281TYPE(vol7d),INTENT(in) :: this
5282LOGICAL :: vol7d_check_alloc_ana
5283
5284vol7d_check_alloc_ana = ASSOCIATED(this%ana) .AND. ASSOCIATED(this%network)
5285
5286END FUNCTION vol7d_check_alloc_ana
5287
5288SUBROUTINE vol7d_force_alloc_ana(this, ini)
5289TYPE(vol7d),INTENT(inout) :: this
5290LOGICAL,INTENT(in),OPTIONAL :: ini
5291
5292! Alloco i descrittori minimi per avere un volume di anagrafica
5293IF (.NOT. ASSOCIATED(this%ana)) CALL vol7d_alloc(this, nana=1, ini=ini)
5294IF (.NOT. ASSOCIATED(this%network)) CALL vol7d_alloc(this, nnetwork=1, ini=ini)
5295
5296END SUBROUTINE vol7d_force_alloc_ana
5297
5298
5299FUNCTION vol7d_check_alloc_dati(this)
5300TYPE(vol7d),INTENT(in) :: this
5301LOGICAL :: vol7d_check_alloc_dati
5302
5303vol7d_check_alloc_dati = vol7d_check_alloc_ana(this) .AND. &
5304 ASSOCIATED(this%time) .AND. ASSOCIATED(this%level) .AND. &
5305 ASSOCIATED(this%timerange)
5306
5307END FUNCTION vol7d_check_alloc_dati
5308
5309SUBROUTINE vol7d_force_alloc_dati(this, ini)
5310TYPE(vol7d),INTENT(inout) :: this
5311LOGICAL,INTENT(in),OPTIONAL :: ini
5312
5313! Alloco i descrittori minimi per avere un volume di dati
5314CALL vol7d_force_alloc_ana(this, ini)
5315IF (.NOT. ASSOCIATED(this%time)) CALL vol7d_alloc(this, ntime=1, ini=ini)
5316IF (.NOT. ASSOCIATED(this%level)) CALL vol7d_alloc(this, nlevel=1, ini=ini)
5317IF (.NOT. ASSOCIATED(this%timerange)) CALL vol7d_alloc(this, ntimerange=1, ini=ini)
5318
5319END SUBROUTINE vol7d_force_alloc_dati
5320
5321
5322SUBROUTINE vol7d_force_alloc(this)
5323TYPE(vol7d),INTENT(inout) :: this
5324
5325! If anything really not allocated yet, allocate with size 0
5326IF (.NOT. ASSOCIATED(this%ana)) CALL vol7d_alloc(this, nana=0)
5327IF (.NOT. ASSOCIATED(this%network)) CALL vol7d_alloc(this, nnetwork=0)
5328IF (.NOT. ASSOCIATED(this%time)) CALL vol7d_alloc(this, ntime=0)
5329IF (.NOT. ASSOCIATED(this%level)) CALL vol7d_alloc(this, nlevel=0)
5330IF (.NOT. ASSOCIATED(this%timerange)) CALL vol7d_alloc(this, ntimerange=0)
5331
5332END SUBROUTINE vol7d_force_alloc
5333
5334
5335FUNCTION vol7d_check_vol(this)
5336TYPE(vol7d),INTENT(in) :: this !< oggetto da controllare
5337LOGICAL :: vol7d_check_vol
5338
5339vol7d_check_vol = c_e(this)
5340
5341! Anagrafica
5342IF (ASSOCIATED(this%anavar%r) .AND. .NOT.ASSOCIATED(this%volanar)) THEN
5343 vol7d_check_vol = .false.
5344ENDIF
5345
5346IF (ASSOCIATED(this%anavar%d) .AND. .NOT.ASSOCIATED(this%volanad)) THEN
5347 vol7d_check_vol = .false.
5348ENDIF
5349
5350IF (ASSOCIATED(this%anavar%i) .AND. .NOT.ASSOCIATED(this%volanai)) THEN
5351 vol7d_check_vol = .false.
5352ENDIF
5353
5354IF (ASSOCIATED(this%anavar%b) .AND. .NOT.ASSOCIATED(this%volanab)) THEN
5355 vol7d_check_vol = .false.
5356ENDIF
5357
5358IF (ASSOCIATED(this%anavar%c) .AND. .NOT.ASSOCIATED(this%volanac)) THEN
5359 vol7d_check_vol = .false.
5360ENDIF
5361IF (ASSOCIATED(this%anavar%r) .OR. ASSOCIATED(this%anavar%d) .OR. &
5362 ASSOCIATED(this%anavar%i) .OR. ASSOCIATED(this%anavar%b) .OR. &
5363 ASSOCIATED(this%anavar%c)) THEN
5364 vol7d_check_vol = vol7d_check_vol .AND. vol7d_check_alloc_ana(this)
5365ENDIF
5366
5367! Attributi dell'anagrafica
5368IF (ASSOCIATED(this%anaattr%r) .AND. ASSOCIATED(this%anavarattr%r) .AND. &
5369 .NOT.ASSOCIATED(this%volanaattrr)) THEN
5370 vol7d_check_vol = .false.
5371ENDIF
5372
5373IF (ASSOCIATED(this%anaattr%d) .AND. ASSOCIATED(this%anavarattr%d) .AND. &
5374 .NOT.ASSOCIATED(this%volanaattrd)) THEN
5375 vol7d_check_vol = .false.
5376ENDIF
5377
5378IF (ASSOCIATED(this%anaattr%i) .AND. ASSOCIATED(this%anavarattr%i) .AND. &
5379 .NOT.ASSOCIATED(this%volanaattri)) THEN
5380 vol7d_check_vol = .false.
5381ENDIF
5382
5383IF (ASSOCIATED(this%anaattr%b) .AND. ASSOCIATED(this%anavarattr%b) .AND. &
5384 .NOT.ASSOCIATED(this%volanaattrb)) THEN
5385 vol7d_check_vol = .false.
5386ENDIF
5387
5388IF (ASSOCIATED(this%anaattr%c) .AND. ASSOCIATED(this%anavarattr%c) .AND. &
5389 .NOT.ASSOCIATED(this%volanaattrc)) THEN
5390 vol7d_check_vol = .false.
5391ENDIF
5392
5393! Dati
5394IF (ASSOCIATED(this%dativar%r) .AND. .NOT.ASSOCIATED(this%voldatir)) THEN
5395 vol7d_check_vol = .false.
5396ENDIF
5397
5398IF (ASSOCIATED(this%dativar%d) .AND. .NOT.ASSOCIATED(this%voldatid)) THEN
5399 vol7d_check_vol = .false.
5400ENDIF
5401
5402IF (ASSOCIATED(this%dativar%i) .AND. .NOT.ASSOCIATED(this%voldatii)) THEN
5403 vol7d_check_vol = .false.
5404ENDIF
5405
5406IF (ASSOCIATED(this%dativar%b) .AND. .NOT.ASSOCIATED(this%voldatib)) THEN
5407 vol7d_check_vol = .false.
5408ENDIF
5409
5410IF (ASSOCIATED(this%dativar%c) .AND. .NOT.ASSOCIATED(this%voldatic)) THEN
5411 vol7d_check_vol = .false.
5412ENDIF
5413
5414! Attributi dei dati
5415IF (ASSOCIATED(this%datiattr%r) .AND. ASSOCIATED(this%dativarattr%r) .AND. &
5416 .NOT.ASSOCIATED(this%voldatiattrr)) THEN
5417 vol7d_check_vol = .false.
5418ENDIF
5419
5420IF (ASSOCIATED(this%datiattr%d) .AND. ASSOCIATED(this%dativarattr%d) .AND. &
5421 .NOT.ASSOCIATED(this%voldatiattrd)) THEN
5422 vol7d_check_vol = .false.
5423ENDIF
5424
5425IF (ASSOCIATED(this%datiattr%i) .AND. ASSOCIATED(this%dativarattr%i) .AND. &
5426 .NOT.ASSOCIATED(this%voldatiattri)) THEN
5427 vol7d_check_vol = .false.
5428ENDIF
5429
5430IF (ASSOCIATED(this%datiattr%b) .AND. ASSOCIATED(this%dativarattr%b) .AND. &
5431 .NOT.ASSOCIATED(this%voldatiattrb)) THEN
5432 vol7d_check_vol = .false.
5433ENDIF
5434
5435IF (ASSOCIATED(this%datiattr%c) .AND. ASSOCIATED(this%dativarattr%c) .AND. &
5436 .NOT.ASSOCIATED(this%voldatiattrc)) THEN
5437 vol7d_check_vol = .false.
5438ENDIF
5439IF (ASSOCIATED(this%dativar%r) .OR. ASSOCIATED(this%dativar%d) .OR. &
5440 ASSOCIATED(this%dativar%i) .OR. ASSOCIATED(this%dativar%b) .OR. &
5441 ASSOCIATED(this%dativar%c)) THEN
5442 vol7d_check_vol = vol7d_check_vol .AND. vol7d_check_alloc_dati(this)
5443ENDIF
5444
5445END FUNCTION vol7d_check_vol
5446
5447
5448!> Metodo per allocare i volumi richiesti di variabili e attributi per
5449!! anagrafica e dati.
5450!! Se alcuni dei descrittori relativi alle dimensioni anagrafica,
5451!! livello verticale, tempo, intervallo temporale (timerange), rete non sono
5452!! stati richiesti preventivamente con la ::vol7d_alloc, essi vengono allocati
5453!! automaticamente da questo metodo
5454!! con estensione di default pari a 1 (non 0!), questo significa, ad esempio,
5455!! che se prevedo di avere soli dati superficiali, cioè ad un solo livello
5456!! verticale, o una sola rete di stazioni, non devo preoccuparmi di
5457!! specificare questa informazione.
5458!! Tra i 20 possibili volumi allocabili
5459!! ((variabili,attributi)*(anagrafica,dati)*(r,d,i,b,c)=20)
5460!! saranno allocati solo quelli per cui è stato precedentemente richiesto il
5461!! corrispondente descrittore variabili/attributi con la ::vol7d_alloc.
5462SUBROUTINE vol7d_alloc_vol(this, ini, inivol)
5463TYPE(vol7d),INTENT(inout) :: this !< oggetto di cui allocare i volumi
5464LOGICAL,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
5465LOGICAL,INTENT(in),OPTIONAL :: inivol !< se fornito e vale \c .TRUE., i volumi allocati saranno inizializzati a valore mancante
5466
5467LOGICAL :: linivol
5468
5469IF (PRESENT(inivol)) THEN
5470 linivol = inivol
5471ELSE
5472 linivol = .true.
5473ENDIF
5474
5475! Anagrafica
5476IF (ASSOCIATED(this%anavar%r) .AND. .NOT.ASSOCIATED(this%volanar)) THEN
5477 CALL vol7d_force_alloc_ana(this, ini)
5478 ALLOCATE(this%volanar(SIZE(this%ana), SIZE(this%anavar%r), SIZE(this%network)))
5479 IF (linivol) this%volanar(:,:,:) = rmiss
5480ENDIF
5481
5482IF (ASSOCIATED(this%anavar%d) .AND. .NOT.ASSOCIATED(this%volanad)) THEN
5483 CALL vol7d_force_alloc_ana(this, ini)
5484 ALLOCATE(this%volanad(SIZE(this%ana), SIZE(this%anavar%d), SIZE(this%network)))
5485 IF (linivol) this%volanad(:,:,:) = rdmiss
5486ENDIF
5487
5488IF (ASSOCIATED(this%anavar%i) .AND. .NOT.ASSOCIATED(this%volanai)) THEN
5489 CALL vol7d_force_alloc_ana(this, ini)
5490 ALLOCATE(this%volanai(SIZE(this%ana), SIZE(this%anavar%i), SIZE(this%network)))
5491 IF (linivol) this%volanai(:,:,:) = imiss
5492ENDIF
5493
5494IF (ASSOCIATED(this%anavar%b) .AND. .NOT.ASSOCIATED(this%volanab)) THEN
5495 CALL vol7d_force_alloc_ana(this, ini)
5496 ALLOCATE(this%volanab(SIZE(this%ana), SIZE(this%anavar%b), SIZE(this%network)))
5497 IF (linivol) this%volanab(:,:,:) = ibmiss
5498ENDIF
5499
5500IF (ASSOCIATED(this%anavar%c) .AND. .NOT.ASSOCIATED(this%volanac)) THEN
5501 CALL vol7d_force_alloc_ana(this, ini)
5502 ALLOCATE(this%volanac(SIZE(this%ana), SIZE(this%anavar%c), SIZE(this%network)))
5503 IF (linivol) this%volanac(:,:,:) = cmiss
5504ENDIF
5505
5506! Attributi dell'anagrafica
5507IF (ASSOCIATED(this%anaattr%r) .AND. ASSOCIATED(this%anavarattr%r) .AND. &
5508 .NOT.ASSOCIATED(this%volanaattrr)) THEN
5509 CALL vol7d_force_alloc_ana(this, ini)
5510 ALLOCATE(this%volanaattrr(SIZE(this%ana), SIZE(this%anavarattr%r), &
5511 SIZE(this%network), SIZE(this%anaattr%r)))
5512 IF (linivol) this%volanaattrr(:,:,:,:) = rmiss
5513ENDIF
5514
5515IF (ASSOCIATED(this%anaattr%d) .AND. ASSOCIATED(this%anavarattr%d) .AND. &
5516 .NOT.ASSOCIATED(this%volanaattrd)) THEN
5517 CALL vol7d_force_alloc_ana(this, ini)
5518 ALLOCATE(this%volanaattrd(SIZE(this%ana), SIZE(this%anavarattr%d), &
5519 SIZE(this%network), SIZE(this%anaattr%d)))
5520 IF (linivol) this%volanaattrd(:,:,:,:) = rdmiss
5521ENDIF
5522
5523IF (ASSOCIATED(this%anaattr%i) .AND. ASSOCIATED(this%anavarattr%i) .AND. &
5524 .NOT.ASSOCIATED(this%volanaattri)) THEN
5525 CALL vol7d_force_alloc_ana(this, ini)
5526 ALLOCATE(this%volanaattri(SIZE(this%ana), SIZE(this%anavarattr%i), &
5527 SIZE(this%network), SIZE(this%anaattr%i)))
5528 IF (linivol) this%volanaattri(:,:,:,:) = imiss
5529ENDIF
5530
5531IF (ASSOCIATED(this%anaattr%b) .AND. ASSOCIATED(this%anavarattr%b) .AND. &
5532 .NOT.ASSOCIATED(this%volanaattrb)) THEN
5533 CALL vol7d_force_alloc_ana(this, ini)
5534 ALLOCATE(this%volanaattrb(SIZE(this%ana), SIZE(this%anavarattr%b), &
5535 SIZE(this%network), SIZE(this%anaattr%b)))
5536 IF (linivol) this%volanaattrb(:,:,:,:) = ibmiss
5537ENDIF
5538
5539IF (ASSOCIATED(this%anaattr%c) .AND. ASSOCIATED(this%anavarattr%c) .AND. &
5540 .NOT.ASSOCIATED(this%volanaattrc)) THEN
5541 CALL vol7d_force_alloc_ana(this, ini)
5542 ALLOCATE(this%volanaattrc(SIZE(this%ana), SIZE(this%anavarattr%c), &
5543 SIZE(this%network), SIZE(this%anaattr%c)))
5544 IF (linivol) this%volanaattrc(:,:,:,:) = cmiss
5545ENDIF
5546
5547! Dati
5548IF (ASSOCIATED(this%dativar%r) .AND. .NOT.ASSOCIATED(this%voldatir)) THEN
5549 CALL vol7d_force_alloc_dati(this, ini)
5550 ALLOCATE(this%voldatir(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
5551 SIZE(this%timerange), SIZE(this%dativar%r), SIZE(this%network)))
5552 IF (linivol) this%voldatir(:,:,:,:,:,:) = rmiss
5553ENDIF
5554
5555IF (ASSOCIATED(this%dativar%d) .AND. .NOT.ASSOCIATED(this%voldatid)) THEN
5556 CALL vol7d_force_alloc_dati(this, ini)
5557 ALLOCATE(this%voldatid(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
5558 SIZE(this%timerange), SIZE(this%dativar%d), SIZE(this%network)))
5559 IF (linivol) this%voldatid(:,:,:,:,:,:) = rdmiss
5560ENDIF
5561
5562IF (ASSOCIATED(this%dativar%i) .AND. .NOT.ASSOCIATED(this%voldatii)) THEN
5563 CALL vol7d_force_alloc_dati(this, ini)
5564 ALLOCATE(this%voldatii(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
5565 SIZE(this%timerange), SIZE(this%dativar%i), SIZE(this%network)))
5566 IF (linivol) this%voldatii(:,:,:,:,:,:) = imiss
5567ENDIF
5568
5569IF (ASSOCIATED(this%dativar%b) .AND. .NOT.ASSOCIATED(this%voldatib)) THEN
5570 CALL vol7d_force_alloc_dati(this, ini)
5571 ALLOCATE(this%voldatib(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
5572 SIZE(this%timerange), SIZE(this%dativar%b), SIZE(this%network)))
5573 IF (linivol) this%voldatib(:,:,:,:,:,:) = ibmiss
5574ENDIF
5575
5576IF (ASSOCIATED(this%dativar%c) .AND. .NOT.ASSOCIATED(this%voldatic)) THEN
5577 CALL vol7d_force_alloc_dati(this, ini)
5578 ALLOCATE(this%voldatic(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
5579 SIZE(this%timerange), SIZE(this%dativar%c), SIZE(this%network)))
5580 IF (linivol) this%voldatic(:,:,:,:,:,:) = cmiss
5581ENDIF
5582
5583! Attributi dei dati
5584IF (ASSOCIATED(this%datiattr%r) .AND. ASSOCIATED(this%dativarattr%r) .AND. &
5585 .NOT.ASSOCIATED(this%voldatiattrr)) THEN
5586 CALL vol7d_force_alloc_dati(this, ini)
5587 ALLOCATE(this%voldatiattrr(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
5588 SIZE(this%timerange), SIZE(this%dativarattr%r), SIZE(this%network), &
5589 SIZE(this%datiattr%r)))
5590 IF (linivol) this%voldatiattrr(:,:,:,:,:,:,:) = rmiss
5591ENDIF
5592
5593IF (ASSOCIATED(this%datiattr%d) .AND. ASSOCIATED(this%dativarattr%d) .AND. &
5594 .NOT.ASSOCIATED(this%voldatiattrd)) THEN
5595 CALL vol7d_force_alloc_dati(this, ini)
5596 ALLOCATE(this%voldatiattrd(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
5597 SIZE(this%timerange), SIZE(this%dativarattr%d), SIZE(this%network), &
5598 SIZE(this%datiattr%d)))
5599 IF (linivol) this%voldatiattrd(:,:,:,:,:,:,:) = rdmiss
5600ENDIF
5601
5602IF (ASSOCIATED(this%datiattr%i) .AND. ASSOCIATED(this%dativarattr%i) .AND. &
5603 .NOT.ASSOCIATED(this%voldatiattri)) THEN
5604 CALL vol7d_force_alloc_dati(this, ini)
5605 ALLOCATE(this%voldatiattri(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
5606 SIZE(this%timerange), SIZE(this%dativarattr%i), SIZE(this%network), &
5607 SIZE(this%datiattr%i)))
5608 IF (linivol) this%voldatiattri(:,:,:,:,:,:,:) = imiss
5609ENDIF
5610
5611IF (ASSOCIATED(this%datiattr%b) .AND. ASSOCIATED(this%dativarattr%b) .AND. &
5612 .NOT.ASSOCIATED(this%voldatiattrb)) THEN
5613 CALL vol7d_force_alloc_dati(this, ini)
5614 ALLOCATE(this%voldatiattrb(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
5615 SIZE(this%timerange), SIZE(this%dativarattr%b), SIZE(this%network), &
5616 SIZE(this%datiattr%b)))
5617 IF (linivol) this%voldatiattrb(:,:,:,:,:,:,:) = ibmiss
5618ENDIF
5619
5620IF (ASSOCIATED(this%datiattr%c) .AND. ASSOCIATED(this%dativarattr%c) .AND. &
5621 .NOT.ASSOCIATED(this%voldatiattrc)) THEN
5622 CALL vol7d_force_alloc_dati(this, ini)
5623 ALLOCATE(this%voldatiattrc(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
5624 SIZE(this%timerange), SIZE(this%dativarattr%c), SIZE(this%network), &
5625 SIZE(this%datiattr%c)))
5626 IF (linivol) this%voldatiattrc(:,:,:,:,:,:,:) = cmiss
5627ENDIF
5628
5629! Catch-all method
5630CALL vol7d_force_alloc(this)
5631
5632! Creo gli indici var-attr
5633
5634#ifdef DEBUG
5635CALL l4f_log(l4f_debug,"calling: vol7d_set_attr_ind")
5636#endif
5637
5638CALL vol7d_set_attr_ind(this)
5639
5640
5641
5642END SUBROUTINE vol7d_alloc_vol
5643
5644
5645!> Metodo per creare gli indici che associano le variabili aventi attributo
5646!! alle variabili nei relativi descrittori.
5647!! Ha senso chiamare questo metodo solo dopo che i descrittori delle variabili
5648!! e degli attributi desiderati sono stati allocati ed è stato assegnato un
5649!! valore ai relativi membri btable (vedi vol7d_var_class::vol7d_var), se
5650!! i descrittori non sono stati allocati o assegnati, il metodo non fa niente.
5651SUBROUTINE vol7d_set_attr_ind(this)
5652TYPE(vol7d),INTENT(inout) :: this !< oggetto in cui creare gli indici
5653
5654INTEGER :: i
5655
5656! real
5657IF (ASSOCIATED(this%dativar%r)) THEN
5658 IF (ASSOCIATED(this%dativarattr%r)) THEN
5659 DO i = 1, SIZE(this%dativar%r)
5660 this%dativar%r(i)%r = &
5661 firsttrue(this%dativar%r(i)%btable == this%dativarattr%r(:)%btable)
5662 ENDDO
5663 ENDIF
5664
5665 IF (ASSOCIATED(this%dativarattr%d)) THEN
5666 DO i = 1, SIZE(this%dativar%r)
5667 this%dativar%r(i)%d = &
5668 firsttrue(this%dativar%r(i)%btable == this%dativarattr%d(:)%btable)
5669 ENDDO
5670 ENDIF
5671
5672 IF (ASSOCIATED(this%dativarattr%i)) THEN
5673 DO i = 1, SIZE(this%dativar%r)
5674 this%dativar%r(i)%i = &
5675 firsttrue(this%dativar%r(i)%btable == this%dativarattr%i(:)%btable)
5676 ENDDO
5677 ENDIF
5678
5679 IF (ASSOCIATED(this%dativarattr%b)) THEN
5680 DO i = 1, SIZE(this%dativar%r)
5681 this%dativar%r(i)%b = &
5682 firsttrue(this%dativar%r(i)%btable == this%dativarattr%b(:)%btable)
5683 ENDDO
5684 ENDIF
5685
5686 IF (ASSOCIATED(this%dativarattr%c)) THEN
5687 DO i = 1, SIZE(this%dativar%r)
5688 this%dativar%r(i)%c = &
5689 firsttrue(this%dativar%r(i)%btable == this%dativarattr%c(:)%btable)
5690 ENDDO
5691 ENDIF
5692ENDIF
5693! double
5694IF (ASSOCIATED(this%dativar%d)) THEN
5695 IF (ASSOCIATED(this%dativarattr%r)) THEN
5696 DO i = 1, SIZE(this%dativar%d)
5697 this%dativar%d(i)%r = &
5698 firsttrue(this%dativar%d(i)%btable == this%dativarattr%r(:)%btable)
5699 ENDDO
5700 ENDIF
5701
5702 IF (ASSOCIATED(this%dativarattr%d)) THEN
5703 DO i = 1, SIZE(this%dativar%d)
5704 this%dativar%d(i)%d = &
5705 firsttrue(this%dativar%d(i)%btable == this%dativarattr%d(:)%btable)
5706 ENDDO
5707 ENDIF
5708
5709 IF (ASSOCIATED(this%dativarattr%i)) THEN
5710 DO i = 1, SIZE(this%dativar%d)
5711 this%dativar%d(i)%i = &
5712 firsttrue(this%dativar%d(i)%btable == this%dativarattr%i(:)%btable)
5713 ENDDO
5714 ENDIF
5715
5716 IF (ASSOCIATED(this%dativarattr%b)) THEN
5717 DO i = 1, SIZE(this%dativar%d)
5718 this%dativar%d(i)%b = &
5719 firsttrue(this%dativar%d(i)%btable == this%dativarattr%b(:)%btable)
5720 ENDDO
5721 ENDIF
5722
5723 IF (ASSOCIATED(this%dativarattr%c)) THEN
5724 DO i = 1, SIZE(this%dativar%d)
5725 this%dativar%d(i)%c = &
5726 firsttrue(this%dativar%d(i)%btable == this%dativarattr%c(:)%btable)
5727 ENDDO
5728 ENDIF
5729ENDIF
5730! integer
5731IF (ASSOCIATED(this%dativar%i)) THEN
5732 IF (ASSOCIATED(this%dativarattr%r)) THEN
5733 DO i = 1, SIZE(this%dativar%i)
5734 this%dativar%i(i)%r = &
5735 firsttrue(this%dativar%i(i)%btable == this%dativarattr%r(:)%btable)
5736 ENDDO
5737 ENDIF
5738
5739 IF (ASSOCIATED(this%dativarattr%d)) THEN
5740 DO i = 1, SIZE(this%dativar%i)
5741 this%dativar%i(i)%d = &
5742 firsttrue(this%dativar%i(i)%btable == this%dativarattr%d(:)%btable)
5743 ENDDO
5744 ENDIF
5745
5746 IF (ASSOCIATED(this%dativarattr%i)) THEN
5747 DO i = 1, SIZE(this%dativar%i)
5748 this%dativar%i(i)%i = &
5749 firsttrue(this%dativar%i(i)%btable == this%dativarattr%i(:)%btable)
5750 ENDDO
5751 ENDIF
5752
5753 IF (ASSOCIATED(this%dativarattr%b)) THEN
5754 DO i = 1, SIZE(this%dativar%i)
5755 this%dativar%i(i)%b = &
5756 firsttrue(this%dativar%i(i)%btable == this%dativarattr%b(:)%btable)
5757 ENDDO
5758 ENDIF
5759
5760 IF (ASSOCIATED(this%dativarattr%c)) THEN
5761 DO i = 1, SIZE(this%dativar%i)
5762 this%dativar%i(i)%c = &
5763 firsttrue(this%dativar%i(i)%btable == this%dativarattr%c(:)%btable)
5764 ENDDO
5765 ENDIF
5766ENDIF
5767! byte
5768IF (ASSOCIATED(this%dativar%b)) THEN
5769 IF (ASSOCIATED(this%dativarattr%r)) THEN
5770 DO i = 1, SIZE(this%dativar%b)
5771 this%dativar%b(i)%r = &
5772 firsttrue(this%dativar%b(i)%btable == this%dativarattr%r(:)%btable)
5773 ENDDO
5774 ENDIF
5775
5776 IF (ASSOCIATED(this%dativarattr%d)) THEN
5777 DO i = 1, SIZE(this%dativar%b)
5778 this%dativar%b(i)%d = &
5779 firsttrue(this%dativar%b(i)%btable == this%dativarattr%d(:)%btable)
5780 ENDDO
5781 ENDIF
5782
5783 IF (ASSOCIATED(this%dativarattr%i)) THEN
5784 DO i = 1, SIZE(this%dativar%b)
5785 this%dativar%b(i)%i = &
5786 firsttrue(this%dativar%b(i)%btable == this%dativarattr%i(:)%btable)
5787 ENDDO
5788 ENDIF
5789
5790 IF (ASSOCIATED(this%dativarattr%b)) THEN
5791 DO i = 1, SIZE(this%dativar%b)
5792 this%dativar%b(i)%b = &
5793 firsttrue(this%dativar%b(i)%btable == this%dativarattr%b(:)%btable)
5794 ENDDO
5795 ENDIF
5796
5797 IF (ASSOCIATED(this%dativarattr%c)) THEN
5798 DO i = 1, SIZE(this%dativar%b)
5799 this%dativar%b(i)%c = &
5800 firsttrue(this%dativar%b(i)%btable == this%dativarattr%c(:)%btable)
5801 ENDDO
5802 ENDIF
5803ENDIF
5804! character
5805IF (ASSOCIATED(this%dativar%c)) THEN
5806 IF (ASSOCIATED(this%dativarattr%r)) THEN
5807 DO i = 1, SIZE(this%dativar%c)
5808 this%dativar%c(i)%r = &
5809 firsttrue(this%dativar%c(i)%btable == this%dativarattr%r(:)%btable)
5810 ENDDO
5811 ENDIF
5812
5813 IF (ASSOCIATED(this%dativarattr%d)) THEN
5814 DO i = 1, SIZE(this%dativar%c)
5815 this%dativar%c(i)%d = &
5816 firsttrue(this%dativar%c(i)%btable == this%dativarattr%d(:)%btable)
5817 ENDDO
5818 ENDIF
5819
5820 IF (ASSOCIATED(this%dativarattr%i)) THEN
5821 DO i = 1, SIZE(this%dativar%c)
5822 this%dativar%c(i)%i = &
5823 firsttrue(this%dativar%c(i)%btable == this%dativarattr%i(:)%btable)
5824 ENDDO
5825 ENDIF
5826
5827 IF (ASSOCIATED(this%dativarattr%b)) THEN
5828 DO i = 1, SIZE(this%dativar%c)
5829 this%dativar%c(i)%b = &
5830 firsttrue(this%dativar%c(i)%btable == this%dativarattr%b(:)%btable)
5831 ENDDO
5832 ENDIF
5833
5834 IF (ASSOCIATED(this%dativarattr%c)) THEN
5835 DO i = 1, SIZE(this%dativar%c)
5836 this%dativar%c(i)%c = &
5837 firsttrue(this%dativar%c(i)%btable == this%dativarattr%c(:)%btable)
5838 ENDDO
5839 ENDIF
5840ENDIF
5841
5842END SUBROUTINE vol7d_set_attr_ind
5843
5844
5845!> Metodo per fondere 2 oggetti vol7d.
5846!! Il secondo volume viene accodato al primo e poi distrutto, si veda
5847!! quindi la descrizione di ::vol7d_append. Se uno degli oggetti \a
5848!! this o \a that sono vuoti non perde tempo inutile,
5849SUBROUTINE vol7d_merge(this, that, sort, bestdata, &
5850 ltimesimple, ltimerangesimple, llevelsimple, lanasimple)
5851TYPE(vol7d),INTENT(INOUT) :: this !< primo oggetto in ingresso, alla fine conterrà il risultato della fusione
5852TYPE(vol7d),INTENT(INOUT) :: that !< secondo oggetto in ingresso, alla fine sarà distrutto
5853LOGICAL,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
5854LOGICAL,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
5855LOGICAL,INTENT(IN),OPTIONAL :: ltimesimple, ltimerangesimple, llevelsimple, lanasimple ! experimental, please do not use outside the library now
5856
5857TYPE(vol7d) :: v7d_clean
5858
5859
5861 this = that
5863 that = v7d_clean ! destroy that without deallocating
5864ELSE ! Append that to this and destroy that
5866 ltimesimple, ltimerangesimple, llevelsimple, lanasimple)
5868ENDIF
5869
5870END SUBROUTINE vol7d_merge
5871
5872
5873!> Metodo per accodare un oggetto vol7d ad un altro.
5874!! Si tratta di un metodo molto potente e versatile;
5875!! i descrittori delle dimensioni del volume finale conterranno i valori
5876!! dei corrispondenti descrittori del primo e del secondo volume
5877!! e i volumi di anagrafica e dati conterranno i valori dei due volumi
5878!! ai posti giusti, e valori mancanti per le nuove combinazioni che
5879!! eventualmente si verranno a creare.
5880!! Se i volumi multidimensionali di anagrafica e/o dati dei 2 oggetti
5881!! hanno un'intersezione non nulla, negli elementi comuni il volume finale
5882!! conterrà il corrispondente elemento del \b secondo volume.
5883!! Attenzione che, durante l'esecuzione del metodo, la memoria richiesta è
5884!! pari alla memoria complessiva occupata dai 2 volumi iniziali più
5885!! la memoria complessiva del volume finale, per cui, nel caso di volumi grandi,
5886!! ci potrebbero essere problemi di esaurimento della memoria centrale.
5887!! Se l'oggetto \a that è vuoto non perde tempo inutile,
5888!!
5889!! \todo nel caso di elementi comuni inserire la possibiità (opzionale per
5890!! non penalizzare le prestazioni quando ciò non serve) di effettuare una scelta
5891!! più ragionata dell'elemento da tenere, almeno controllando i dati mancanti
5892!! se non le flag di qualità
5893!!
5894!! \todo "rateizzare" l'allocazione dei volumi per ridurre l'occupazione di
5895!! memoria nel caso siano allocati contemporaneamente volumi di variabili e
5896!! di attributi o più volumi di tipi diversi
5897!!
5898!! \todo il parametro \a that è dichiarato \a INOUT perché la vol7d_alloc_vol
5899!! può modificarlo, bisognerebbe implementare una vol7d_check_vol che restituisca
5900!! errore anziché usare la vol7d_alloc_vol.
5901SUBROUTINE vol7d_append(this, that, sort, bestdata, &
5902 ltimesimple, ltimerangesimple, llevelsimple, lanasimple, lnetworksimple)
5903TYPE(vol7d),INTENT(INOUT) :: this !< primo oggetto in ingresso, a cui sarà accodato il secondo
5904TYPE(vol7d),INTENT(IN) :: that !< secondo oggetto in ingresso, non viene modificato dal metodo
5905LOGICAL,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
5906! experimental, please do not use outside the library now, they force the use
5907! of a simplified mapping algorithm which is valid only whene the dimension
5908! content is the same in both volumes , or when one of them is empty
5909LOGICAL,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
5910LOGICAL,INTENT(IN),OPTIONAL :: ltimesimple, ltimerangesimple, llevelsimple, lanasimple, lnetworksimple
5911
5912
5913TYPE(vol7d) :: v7dtmp
5914LOGICAL :: lsort, lbestdata
5915INTEGER,POINTER :: remapt1(:), remapt2(:), remaptr1(:), remaptr2(:), &
5916 remapl1(:), remapl2(:), remapa1(:), remapa2(:), remapn1(:), remapn2(:)
5917
5919IF (.NOT.vol7d_check_vol(that)) RETURN ! be safe
5922 RETURN
5923ENDIF
5924
5925IF (this%time_definition /= that%time_definition) THEN
5926 CALL l4f_log(l4f_fatal, &
5927 'in vol7d_append, cannot append volumes with different &
5928 &time definition')
5929 CALL raise_fatal_error()
5930ENDIF
5931
5932! Completo l'allocazione per avere volumi a norma
5933CALL vol7d_alloc_vol(this)
5934
5938
5939! Calcolo le mappature tra volumi vecchi e volume nuovo
5940! I puntatori remap* vengono tutti o allocati o nullificati
5941IF (optio_log(ltimesimple)) THEN
5942 CALL vol7d_remap2simple_datetime(this%time, that%time, v7dtmp%time, &
5943 lsort, remapt1, remapt2)
5944ELSE
5945 CALL vol7d_remap2_datetime(this%time, that%time, v7dtmp%time, &
5946 lsort, remapt1, remapt2)
5947ENDIF
5948IF (optio_log(ltimerangesimple)) THEN
5949 CALL vol7d_remap2simple_vol7d_timerange(this%timerange, that%timerange, &
5950 v7dtmp%timerange, lsort, remaptr1, remaptr2)
5951ELSE
5952 CALL vol7d_remap2_vol7d_timerange(this%timerange, that%timerange, &
5953 v7dtmp%timerange, lsort, remaptr1, remaptr2)
5954ENDIF
5955IF (optio_log(llevelsimple)) THEN
5956 CALL vol7d_remap2simple_vol7d_level(this%level, that%level, v7dtmp%level, &
5957 lsort, remapl1, remapl2)
5958ELSE
5959 CALL vol7d_remap2_vol7d_level(this%level, that%level, v7dtmp%level, &
5960 lsort, remapl1, remapl2)
5961ENDIF
5962IF (optio_log(lanasimple)) THEN
5963 CALL vol7d_remap2simple_vol7d_ana(this%ana, that%ana, v7dtmp%ana, &
5964 .false., remapa1, remapa2)
5965ELSE
5966 CALL vol7d_remap2_vol7d_ana(this%ana, that%ana, v7dtmp%ana, &
5967 .false., remapa1, remapa2)
5968ENDIF
5969IF (optio_log(lnetworksimple)) THEN
5970 CALL vol7d_remap2simple_vol7d_network(this%network, that%network, v7dtmp%network, &
5971 .false., remapn1, remapn2)
5972ELSE
5973 CALL vol7d_remap2_vol7d_network(this%network, that%network, v7dtmp%network, &
5974 .false., remapn1, remapn2)
5975ENDIF
5976
5977! Faccio la fusione fisica dei volumi
5978CALL vol7d_merge_finalr(this, that, v7dtmp, &
5979 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
5980 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
5981CALL vol7d_merge_finald(this, that, v7dtmp, &
5982 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
5983 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
5984CALL vol7d_merge_finali(this, that, v7dtmp, &
5985 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
5986 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
5987CALL vol7d_merge_finalb(this, that, v7dtmp, &
5988 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
5989 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
5990CALL vol7d_merge_finalc(this, that, v7dtmp, &
5991 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
5992 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
5993
5994! Dealloco i vettori di rimappatura
5995IF (ASSOCIATED(remapt1)) DEALLOCATE(remapt1)
5996IF (ASSOCIATED(remapt2)) DEALLOCATE(remapt2)
5997IF (ASSOCIATED(remaptr1)) DEALLOCATE(remaptr1)
5998IF (ASSOCIATED(remaptr2)) DEALLOCATE(remaptr2)
5999IF (ASSOCIATED(remapl1)) DEALLOCATE(remapl1)
6000IF (ASSOCIATED(remapl2)) DEALLOCATE(remapl2)
6001IF (ASSOCIATED(remapa1)) DEALLOCATE(remapa1)
6002IF (ASSOCIATED(remapa2)) DEALLOCATE(remapa2)
6003IF (ASSOCIATED(remapn1)) DEALLOCATE(remapn1)
6004IF (ASSOCIATED(remapn2)) DEALLOCATE(remapn2)
6005
6006! Distruggo il vecchio volume e assegno il nuovo a this
6008this = v7dtmp
6009! Ricreo gli indici var-attr
6010CALL vol7d_set_attr_ind(this)
6011
6012END SUBROUTINE vol7d_append
6013
6014
6015!> Metodo per creare una copia completa e indipendente di un oggetto vol7d.
6016!! Questo metodo crea un duplicato di tutti i membri di un oggetto vol7d,
6017!! con la possibilità di rielaborarlo durante la copia. Se l'oggetto da copiare
6018!! è vuoto non perde tempo inutile.
6019!! Attenzione, il codice:
6020!! \code
6021!! USE vol7d_class
6022!! TYPE(vol7d) :: vol1, vol2
6023!! CALL init(vol1)
6024!! CALL init(vol2)
6025!! ... ! riempio vol1
6026!! vol2 = vol1
6027!! \endcode
6028!! fa una cosa diversa rispetto a:
6029!! \code
6030!! USE vol7d_class
6031!! TYPE(vol7d) :: vol1, vol2
6032!! CALL init(vol1)
6033!! CALL init(vol2)
6034!! ... ! riempio vol1
6035!! CALL vol7d_copy(vol1, vol2)
6036!! \endcode
6037!! nel primo caso, infatti, l'operatore di assegnazione copia solo i componenti
6038!! statici di \a vol1 nei corrispondenti elementi di \a vol2, mentre i componenti che
6039!! sono allocati dinamicamente (cioè quelli che in ::vol7d hanno l'attributo
6040!! \c POINTER, in pratica quasi tutti) non vengono duplicati, ma per essi vol2
6041!! conterrà un puntatore al corrispondente elemento a cui già punta vol1, e quindi
6042!! eventuali cambiamenti al contenuto di uno dei due oggetti influenzerà il
6043!! contenuto dell'altro; nel secondo caso, invece, vol1 e vol2 sono, dopo la
6044!! vol7d_copy, 2 istanze
6045!! completamente indipendenti, ma uguali tra loro per contenuto, della classe
6046!! vol7d, e quindi hanno vita indipendente.
6047SUBROUTINE vol7d_copy(this, that, sort, unique, miss, &
6048 lsort_time, lsort_timerange, lsort_level, &
6049 ltime, ltimerange, llevel, lana, lnetwork, &
6050 lanavarr, lanavard, lanavari, lanavarb, lanavarc, &
6051 lanaattrr, lanaattrd, lanaattri, lanaattrb, lanaattrc, &
6052 lanavarattrr, lanavarattrd, lanavarattri, lanavarattrb, lanavarattrc, &
6053 ldativarr, ldativard, ldativari, ldativarb, ldativarc, &
6054 ldatiattrr, ldatiattrd, ldatiattri, ldatiattrb, ldatiattrc, &
6055 ldativarattrr, ldativarattrd, ldativarattri, ldativarattrb, ldativarattrc)
6056TYPE(vol7d),INTENT(IN) :: this !< oggetto origine
6057TYPE(vol7d),INTENT(INOUT) :: that !< oggetto destinazione
6058LOGICAL,INTENT(IN),OPTIONAL :: sort !< if present and \a .TRUE., sort all the sortable dimensions
6059LOGICAL,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)
6060LOGICAL,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
6061LOGICAL,INTENT(IN),OPTIONAL :: lsort_time !< if present and \a .TRUE., sort only time dimension (alternative to \a sort )
6062LOGICAL,INTENT(IN),OPTIONAL :: lsort_timerange !< if present and \a .TRUE., sort only timerange dimension (alternative to \a sort )
6063LOGICAL,INTENT(IN),OPTIONAL :: lsort_level !< if present and \a .TRUE., sort only level dimension (alternative to \a sort )
6064!> se fornito, deve essere un vettore logico della stessa lunghezza di
6065!! this%time indicante quali elementi della dimensione \a time
6066!! mantenere (valori \c .TRUE.) e quali scartare (valori \c .FALSE.)
6067!! nel volume copiato; in alternativa può essere un vettore di
6068!! lunghezza 1, in tal caso, se \c .FALSE. , equivale a scartare tutti
6069!! gli elementi (utile principalmente per le variabili); è compatibile
6070!! col parametro \a miss
6071LOGICAL,INTENT(IN),OPTIONAL :: ltime(:)
6072!> come il precedente per la dimensione \a timerange
6073LOGICAL,INTENT(IN),OPTIONAL :: ltimerange(:)
6074!> come il precedente per la dimensione \a level
6075LOGICAL,INTENT(IN),OPTIONAL :: llevel(:)
6076!> come il precedente per la dimensione \a ana
6077LOGICAL,INTENT(IN),OPTIONAL :: lana(:)
6078!> come il precedente per la dimensione \a network
6079LOGICAL,INTENT(IN),OPTIONAL :: lnetwork(:)
6080!> come il precedente per tutte le possibili dimensioni variabile
6081LOGICAL,INTENT(in),OPTIONAL :: &
6082 lanavarr(:), lanavard(:), lanavari(:), lanavarb(:), lanavarc(:), &
6083 lanaattrr(:), lanaattrd(:), lanaattri(:), lanaattrb(:), lanaattrc(:), &
6084 lanavarattrr(:), lanavarattrd(:), lanavarattri(:), lanavarattrb(:), lanavarattrc(:), &
6085 ldativarr(:), ldativard(:), ldativari(:), ldativarb(:), ldativarc(:), &
6086 ldatiattrr(:), ldatiattrd(:), ldatiattri(:), ldatiattrb(:), ldatiattrc(:), &
6087 ldativarattrr(:), ldativarattrd(:), ldativarattri(:), ldativarattrb(:), ldativarattrc(:)
6088
6089LOGICAL :: lsort, lunique, lmiss
6090INTEGER,POINTER :: remapt(:), remaptr(:), remapl(:), remapa(:), remapn(:)
6091
6094IF (.NOT.vol7d_check_vol(this)) RETURN ! be safe
6095
6099
6100! Calcolo le mappature tra volume vecchio e volume nuovo
6101! I puntatori remap* vengono tutti o allocati o nullificati
6102CALL vol7d_remap1_datetime(this%time, that%time, &
6103 lsort.OR.optio_log(lsort_time), lunique, lmiss, remapt, ltime)
6104CALL vol7d_remap1_vol7d_timerange(this%timerange, that%timerange, &
6105 lsort.OR.optio_log(lsort_timerange), lunique, lmiss, remaptr, ltimerange)
6106CALL vol7d_remap1_vol7d_level(this%level, that%level, &
6107 lsort.OR.optio_log(lsort_level), lunique, lmiss, remapl, llevel)
6108CALL vol7d_remap1_vol7d_ana(this%ana, that%ana, &
6109 lsort, lunique, lmiss, remapa, lana)
6110CALL vol7d_remap1_vol7d_network(this%network, that%network, &
6111 lsort, lunique, lmiss, remapn, lnetwork)
6112
6113! lanavari, lanavarb, lanavarc, &
6114! lanaattri, lanaattrb, lanaattrc, &
6115! lanavarattri, lanavarattrb, lanavarattrc, &
6116! ldativari, ldativarb, ldativarc, &
6117! ldatiattri, ldatiattrb, ldatiattrc, &
6118! ldativarattri, ldativarattrb, ldativarattrc
6119! Faccio la riforma fisica dei volumi
6120CALL vol7d_reform_finalr(this, that, &
6121 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
6122 lanavarr, lanaattrr, lanavarattrr, ldativarr, ldatiattrr, ldativarattrr)
6123CALL vol7d_reform_finald(this, that, &
6124 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
6125 lanavard, lanaattrd, lanavarattrd, ldativard, ldatiattrd, ldativarattrd)
6126CALL vol7d_reform_finali(this, that, &
6127 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
6128 lanavari, lanaattri, lanavarattri, ldativari, ldatiattri, ldativarattri)
6129CALL vol7d_reform_finalb(this, that, &
6130 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
6131 lanavarb, lanaattrb, lanavarattrb, ldativarb, ldatiattrb, ldativarattrb)
6132CALL vol7d_reform_finalc(this, that, &
6133 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
6134 lanavarc, lanaattrc, lanavarattrc, ldativarc, ldatiattrc, ldativarattrc)
6135
6136! Dealloco i vettori di rimappatura
6137IF (ASSOCIATED(remapt)) DEALLOCATE(remapt)
6138IF (ASSOCIATED(remaptr)) DEALLOCATE(remaptr)
6139IF (ASSOCIATED(remapl)) DEALLOCATE(remapl)
6140IF (ASSOCIATED(remapa)) DEALLOCATE(remapa)
6141IF (ASSOCIATED(remapn)) DEALLOCATE(remapn)
6142
6143! Ricreo gli indici var-attr
6144CALL vol7d_set_attr_ind(that)
6145that%time_definition = this%time_definition
6146
6147END SUBROUTINE vol7d_copy
6148
6149
6150!> Metodo per riformare in varie maniere un oggetto vol7d.
6151!! Equivale ad una copia (vedi ::vol7d_copy)
6152!! seguita dalla distruzione del volume iniziale e alla
6153!! sua riassegnazione al volume copiato. Ha senso se almeno uno dei parametri
6154!! \a sort, \a uniq o \a miss è fornito uguale a \c .TRUE., altrimenti
6155!! è solo una perdita di tempo.
6156!! Può essere utile, ad esempio, per eliminare stazioni
6157!! o istanti temporali indesiderati, basta assegnare il loro corrispondente
6158!! elemento del descrittore a valore mancante e chiamare vol7d_reform
6159!! con miss=.TRUE. .
6160SUBROUTINE vol7d_reform(this, sort, unique, miss, &
6161 lsort_time, lsort_timerange, lsort_level, &
6162 ltime, ltimerange, llevel, lana, lnetwork, &
6163 lanavarr, lanavard, lanavari, lanavarb, lanavarc, &
6164 lanaattrr, lanaattrd, lanaattri, lanaattrb, lanaattrc, &
6165 lanavarattrr, lanavarattrd, lanavarattri, lanavarattrb, lanavarattrc, &
6166 ldativarr, ldativard, ldativari, ldativarb, ldativarc, &
6167 ldatiattrr, ldatiattrd, ldatiattri, ldatiattrb, ldatiattrc, &
6168 ldativarattrr, ldativarattrd, ldativarattri, ldativarattrb, ldativarattrc&
6169 ,purgeana)
6170TYPE(vol7d),INTENT(INOUT) :: this !< oggetto da riformare
6171LOGICAL,INTENT(IN),OPTIONAL :: sort !< if present and \a .TRUE., sort all the sortable dimensions
6172LOGICAL,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)
6173LOGICAL,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
6174LOGICAL,INTENT(IN),OPTIONAL :: lsort_time !< if present and \a .TRUE., sort only time dimension (alternative to \a sort )
6175LOGICAL,INTENT(IN),OPTIONAL :: lsort_timerange !< if present and \a .TRUE., sort only timerange dimension (alternative to \a sort )
6176LOGICAL,INTENT(IN),OPTIONAL :: lsort_level !< if present and \a .TRUE., sort only level dimension (alternative to \a sort )
6177!> se fornito, deve essere un vettore logico della stessa lunghezza di
6178!! this%time indicante quali elementi della dimensione \a time
6179!! mantenere (valori \c .TRUE.) e quali scartare (valori \c .FALSE.)
6180!! nel volume copiato; in alternativa può essere un vettore di
6181!! lunghezza 1, in tal caso, se \c .FALSE. , equivale a scartare tutti
6182!! gli elementi (utile principalmente per le variabili); è compatibile
6183!! col parametro \a miss
6184LOGICAL,INTENT(IN),OPTIONAL :: ltime(:)
6185LOGICAL,INTENT(IN),OPTIONAL :: ltimerange(:) !< come il precedente per la dimensione \a timerange
6186LOGICAL,INTENT(IN),OPTIONAL :: llevel(:) !< come il precedente per la dimensione \a level
6187LOGICAL,INTENT(IN),OPTIONAL :: lana(:) !< come il precedente per la dimensione \a ana
6188LOGICAL,INTENT(IN),OPTIONAL :: lnetwork(:) !< come il precedente per la dimensione \a network
6189!> come il precedente per tutte le possibili dimensioni variabile
6190LOGICAL,INTENT(in),OPTIONAL :: &
6191 lanavarr(:), lanavard(:), lanavari(:), lanavarb(:), lanavarc(:), &
6192 lanaattrr(:), lanaattrd(:), lanaattri(:), lanaattrb(:), lanaattrc(:), &
6193 lanavarattrr(:), lanavarattrd(:), lanavarattri(:), lanavarattrb(:), lanavarattrc(:), &
6194 ldativarr(:), ldativard(:), ldativari(:), ldativarb(:), ldativarc(:), &
6195 ldatiattrr(:), ldatiattrd(:), ldatiattri(:), ldatiattrb(:), ldatiattrc(:), &
6196 ldativarattrr(:), ldativarattrd(:), ldativarattri(:), ldativarattrb(:), ldativarattrc(:)
6197LOGICAL,INTENT(IN),OPTIONAL :: purgeana !< if true remove ana with all data missing
6198
6199TYPE(vol7d) :: v7dtmp
6200logical,allocatable :: llana(:)
6201integer :: i
6202
6204 lsort_time, lsort_timerange, lsort_level, &
6205 ltime, ltimerange, llevel, lana, lnetwork, &
6206 lanavarr, lanavard, lanavari, lanavarb, lanavarc, &
6207 lanaattrr, lanaattrd, lanaattri, lanaattrb, lanaattrc, &
6208 lanavarattrr, lanavarattrd, lanavarattri, lanavarattrb, lanavarattrc, &
6209 ldativarr, ldativard, ldativari, ldativarb, ldativarc, &
6210 ldatiattrr, ldatiattrd, ldatiattri, ldatiattrb, ldatiattrc, &
6211 ldativarattrr, ldativarattrd, ldativarattri, ldativarattrb, ldativarattrc)
6212
6213! destroy old volume
6215
6216if (optio_log(purgeana)) then
6217 allocate(llana(size(v7dtmp%ana)))
6218 llana =.false.
6219 do i =1,size(v7dtmp%ana)
6220 if (associated(v7dtmp%voldatii)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatii(i,:,:,:,:,:)))
6221 if (associated(v7dtmp%voldatir)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatir(i,:,:,:,:,:)))
6222 if (associated(v7dtmp%voldatid)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatid(i,:,:,:,:,:)))
6223 if (associated(v7dtmp%voldatib)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatib(i,:,:,:,:,:)))
6224 if (associated(v7dtmp%voldatic)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatic(i,:,:,:,:,:)))
6225 end do
6226 CALL vol7d_copy(v7dtmp, this,lana=llana)
6228 deallocate(llana)
6229else
6230 this=v7dtmp
6231end if
6232
6233END SUBROUTINE vol7d_reform
6234
6235
6236!> Sorts the sortable dimensions in the volume \a this only when necessary.
6237!! Most of the times, the time, timerange and level dimensions in a
6238!! vol7d object are correctly sorted; on the other side many methods
6239!! strictly rely on this fact in order to work correctly. This method
6240!! performs a quick check and sorts the required dimensions only if
6241!! they are not sorted in ascending order yet, improving safety
6242!! without impairing much performance.
6243SUBROUTINE vol7d_smart_sort(this, lsort_time, lsort_timerange, lsort_level)
6244TYPE(vol7d),INTENT(INOUT) :: this !< object to be sorted
6245LOGICAL,OPTIONAL,INTENT(in) :: lsort_time !< if present and \a .TRUE., sort time dimension if it is not sorted in ascending order
6246LOGICAL,OPTIONAL,INTENT(in) :: lsort_timerange !< if present and \a .TRUE., sort timerange dimension if it is not sorted in ascending order
6247LOGICAL,OPTIONAL,INTENT(in) :: lsort_level !< if present and \a .TRUE., sort vertical level dimension if it is not sorted in ascending order
6248
6249INTEGER :: i
6250LOGICAL :: to_be_sorted
6251
6252to_be_sorted = .false.
6253CALL vol7d_alloc_vol(this) ! usual safety check
6254
6255IF (optio_log(lsort_time)) THEN
6256 DO i = 2, SIZE(this%time)
6257 IF (this%time(i) < this%time(i-1)) THEN
6258 to_be_sorted = .true.
6259 EXIT
6260 ENDIF
6261 ENDDO
6262ENDIF
6263IF (optio_log(lsort_timerange)) THEN
6264 DO i = 2, SIZE(this%timerange)
6265 IF (this%timerange(i) < this%timerange(i-1)) THEN
6266 to_be_sorted = .true.
6267 EXIT
6268 ENDIF
6269 ENDDO
6270ENDIF
6271IF (optio_log(lsort_level)) THEN
6272 DO i = 2, SIZE(this%level)
6273 IF (this%level(i) < this%level(i-1)) THEN
6274 to_be_sorted = .true.
6275 EXIT
6276 ENDIF
6277 ENDDO
6278ENDIF
6279
6280IF (to_be_sorted) CALL vol7d_reform(this, &
6281 lsort_time=lsort_time, lsort_timerange=lsort_timerange, lsort_level=lsort_level )
6282
6283END SUBROUTINE vol7d_smart_sort
6284
6285!> Filter the contents of a volume keeping only desired data.
6286!! This subroutine filters a vol7d object by keeping only a subset of
6287!! the data contained. It can keep only times within a specified
6288!! interval, only station networks contained in a list and only
6289!! specified station or data variables. If a filter parameter is not
6290!! provided, no filtering will take place according to that criterion.
6291!! The volume is reallocated keeping only the desired data.
6292SUBROUTINE vol7d_filter(this, avl, vl, nl, s_d, e_d)
6293TYPE(vol7d),INTENT(inout) :: this !< volume to be filtered
6294CHARACTER(len=*),INTENT(in),OPTIONAL :: avl(:) !< list of station variables to be kept, if not provided or of zero length, all variables are kept
6295CHARACTER(len=*),INTENT(in),OPTIONAL :: vl(:) !< list of data variables to be kept, if not provided or of zero length, all variables are kept
6296TYPE(vol7d_network),OPTIONAL :: nl(:) !< list of station networks to be kept, if not provided or of zero length, all networks are kept
6297TYPE(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
6298TYPE(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
6299
6300INTEGER :: i
6301
6302IF (PRESENT(avl)) THEN
6303 IF (SIZE(avl) > 0) THEN
6304
6305 IF (ASSOCIATED(this%anavar%r)) THEN
6306 DO i = 1, SIZE(this%anavar%r)
6307 IF (all(this%anavar%r(i)%btable /= avl)) this%anavar%r(i) = vol7d_var_miss
6308 ENDDO
6309 ENDIF
6310
6311 IF (ASSOCIATED(this%anavar%i)) THEN
6312 DO i = 1, SIZE(this%anavar%i)
6313 IF (all(this%anavar%i(i)%btable /= avl)) this%anavar%i(i) = vol7d_var_miss
6314 ENDDO
6315 ENDIF
6316
6317 IF (ASSOCIATED(this%anavar%b)) THEN
6318 DO i = 1, SIZE(this%anavar%b)
6319 IF (all(this%anavar%b(i)%btable /= avl)) this%anavar%b(i) = vol7d_var_miss
6320 ENDDO
6321 ENDIF
6322
6323 IF (ASSOCIATED(this%anavar%d)) THEN
6324 DO i = 1, SIZE(this%anavar%d)
6325 IF (all(this%anavar%d(i)%btable /= avl)) this%anavar%d(i) = vol7d_var_miss
6326 ENDDO
6327 ENDIF
6328
6329 IF (ASSOCIATED(this%anavar%c)) THEN
6330 DO i = 1, SIZE(this%anavar%c)
6331 IF (all(this%anavar%c(i)%btable /= avl)) this%anavar%c(i) = vol7d_var_miss
6332 ENDDO
6333 ENDIF
6334
6335 ENDIF
6336ENDIF
6337
6338
6339IF (PRESENT(vl)) THEN
6340 IF (size(vl) > 0) THEN
6341 IF (ASSOCIATED(this%dativar%r)) THEN
6342 DO i = 1, SIZE(this%dativar%r)
6343 IF (all(this%dativar%r(i)%btable /= vl)) this%dativar%r(i) = vol7d_var_miss
6344 ENDDO
6345 ENDIF
6346
6347 IF (ASSOCIATED(this%dativar%i)) THEN
6348 DO i = 1, SIZE(this%dativar%i)
6349 IF (all(this%dativar%i(i)%btable /= vl)) this%dativar%i(i) = vol7d_var_miss
6350 ENDDO
6351 ENDIF
6352
6353 IF (ASSOCIATED(this%dativar%b)) THEN
6354 DO i = 1, SIZE(this%dativar%b)
6355 IF (all(this%dativar%b(i)%btable /= vl)) this%dativar%b(i) = vol7d_var_miss
6356 ENDDO
6357 ENDIF
6358
6359 IF (ASSOCIATED(this%dativar%d)) THEN
6360 DO i = 1, SIZE(this%dativar%d)
6361 IF (all(this%dativar%d(i)%btable /= vl)) this%dativar%d(i) = vol7d_var_miss
6362 ENDDO
6363 ENDIF
6364
6365 IF (ASSOCIATED(this%dativar%c)) THEN
6366 DO i = 1, SIZE(this%dativar%c)
6367 IF (all(this%dativar%c(i)%btable /= vl)) this%dativar%c(i) = vol7d_var_miss
6368 ENDDO
6369 ENDIF
6370
6371 IF (ASSOCIATED(this%dativar%c)) THEN
6372 DO i = 1, SIZE(this%dativar%c)
6373 IF (all(this%dativar%c(i)%btable /= vl)) this%dativar%c(i) = vol7d_var_miss
6374 ENDDO
6375 ENDIF
6376
6377 ENDIF
6378ENDIF
6379
6380IF (PRESENT(nl)) THEN
6381 IF (SIZE(nl) > 0) THEN
6382 DO i = 1, SIZE(this%network)
6383 IF (all(this%network(i) /= nl)) this%network(i) = vol7d_network_miss
6384 ENDDO
6385 ENDIF
6386ENDIF
6387
6388IF (PRESENT(s_d)) THEN
6390 WHERE (this%time < s_d)
6391 this%time = datetime_miss
6392 END WHERE
6393 ENDIF
6394ENDIF
6395
6396IF (PRESENT(e_d)) THEN
6398 WHERE (this%time > e_d)
6399 this%time = datetime_miss
6400 END WHERE
6401 ENDIF
6402ENDIF
6403
6404CALL vol7d_reform(this, miss=.true.)
6405
6406END SUBROUTINE vol7d_filter
6407
6408
6409!> Metodo per convertire i volumi di dati di un oggetto vol7d in dati
6410!! reali dove possibile. L'oggetto convertito è una copia completa
6411!! dell'originale che può essere quindi distrutto dopo la chiamata.
6412!! Per i dati di anagrafica, al momento sono convertiti solo
6413!! i dati CHARACTER se è passato \a anaconv=.TRUE.
6414!! Gli attributi non sono toccati.
6415SUBROUTINE vol7d_convr(this, that, anaconv)
6416TYPE(vol7d),INTENT(IN) :: this !< oggetto origine
6417TYPE(vol7d),INTENT(INOUT) :: that !< oggetto convertito
6418LOGICAL,OPTIONAL,INTENT(in) :: anaconv !< converti anche anagrafica
6419INTEGER :: i
6420LOGICAL :: fv(1)=(/.false./), tv(1)=(/.true./), acp(1), acn(1)
6421TYPE(vol7d) :: v7d_tmp
6422
6423IF (optio_log(anaconv)) THEN
6424 acp=fv
6425 acn=tv
6426ELSE
6427 acp=tv
6428 acn=fv
6429ENDIF
6430
6431! Volume con solo i dati reali e tutti gli attributi
6432! l'anagrafica e` copiata interamente se necessario
6433CALL vol7d_copy(this, that, &
6434 lanavarr=tv, lanavard=acp, lanavari=acp, lanavarb=acp, lanavarc=acp, &
6435 ldativarr=tv, ldativard=fv, ldativari=fv, ldativarb=fv, ldativarc=fv)
6436
6437! Volume solo di dati double
6438CALL vol7d_copy(this, v7d_tmp, &
6439 lanavarr=fv, lanavard=acn, lanavari=fv, lanavarb=fv, lanavarc=fv, &
6440 lanaattrr=fv, lanaattrd=fv, lanaattri=fv, lanaattrb=fv, lanaattrc=fv, &
6441 lanavarattrr=fv, lanavarattrd=fv, lanavarattri=fv, lanavarattrb=fv, lanavarattrc=fv, &
6442 ldativarr=fv, ldativard=tv, ldativari=fv, ldativarb=fv, ldativarc=fv, &
6443 ldatiattrr=fv, ldatiattrd=fv, ldatiattri=fv, ldatiattrb=fv, ldatiattrc=fv, &
6444 ldativarattrr=fv, ldativarattrd=fv, ldativarattri=fv, ldativarattrb=fv, ldativarattrc=fv)
6445
6446! converto a dati reali
6447IF (ASSOCIATED(v7d_tmp%anavar%d) .OR. ASSOCIATED(v7d_tmp%dativar%d)) THEN
6448
6449 IF (ASSOCIATED(v7d_tmp%anavar%d)) THEN
6450! alloco i dati reali e vi trasferisco i double
6451 ALLOCATE(v7d_tmp%volanar(SIZE(v7d_tmp%volanad, 1), SIZE(v7d_tmp%volanad, 2), &
6452 SIZE(v7d_tmp%volanad, 3)))
6453 DO i = 1, SIZE(v7d_tmp%anavar%d)
6454 v7d_tmp%volanar(:,i,:) = &
6455 realdat(v7d_tmp%volanad(:,i,:), v7d_tmp%anavar%d(i))
6456 ENDDO
6457 DEALLOCATE(v7d_tmp%volanad)
6458! trasferisco le variabili
6459 v7d_tmp%anavar%r => v7d_tmp%anavar%d
6460 NULLIFY(v7d_tmp%anavar%d)
6461 ENDIF
6462
6463 IF (ASSOCIATED(v7d_tmp%dativar%d)) THEN
6464! alloco i dati reali e vi trasferisco i double
6465 ALLOCATE(v7d_tmp%voldatir(SIZE(v7d_tmp%voldatid, 1), SIZE(v7d_tmp%voldatid, 2), &
6466 SIZE(v7d_tmp%voldatid, 3), SIZE(v7d_tmp%voldatid, 4), SIZE(v7d_tmp%voldatid, 5), &
6467 SIZE(v7d_tmp%voldatid, 6)))
6468 DO i = 1, SIZE(v7d_tmp%dativar%d)
6469 v7d_tmp%voldatir(:,:,:,:,i,:) = &
6470 realdat(v7d_tmp%voldatid(:,:,:,:,i,:), v7d_tmp%dativar%d(i))
6471 ENDDO
6472 DEALLOCATE(v7d_tmp%voldatid)
6473! trasferisco le variabili
6474 v7d_tmp%dativar%r => v7d_tmp%dativar%d
6475 NULLIFY(v7d_tmp%dativar%d)
6476 ENDIF
6477
6478! fondo con il volume definitivo
6479 CALL vol7d_merge(that, v7d_tmp)
6480ELSE
6482ENDIF
6483
6484
6485! Volume solo di dati interi
6486CALL vol7d_copy(this, v7d_tmp, &
6487 lanavarr=fv, lanavard=fv, lanavari=acn, lanavarb=fv, lanavarc=fv, &
6488 lanaattrr=fv, lanaattrd=fv, lanaattri=fv, lanaattrb=fv, lanaattrc=fv, &
6489 lanavarattrr=fv, lanavarattrd=fv, lanavarattri=fv, lanavarattrb=fv, lanavarattrc=fv, &
6490 ldativarr=fv, ldativard=fv, ldativari=tv, ldativarb=fv, ldativarc=fv, &
6491 ldatiattrr=fv, ldatiattrd=fv, ldatiattri=fv, ldatiattrb=fv, ldatiattrc=fv, &
6492 ldativarattrr=fv, ldativarattrd=fv, ldativarattri=fv, ldativarattrb=fv, ldativarattrc=fv)
6493
6494! converto a dati reali
6495IF (ASSOCIATED(v7d_tmp%anavar%i) .OR. ASSOCIATED(v7d_tmp%dativar%i)) THEN
6496
6497 IF (ASSOCIATED(v7d_tmp%anavar%i)) THEN
6498! alloco i dati reali e vi trasferisco gli interi
6499 ALLOCATE(v7d_tmp%volanar(SIZE(v7d_tmp%volanai, 1), SIZE(v7d_tmp%volanai, 2), &
6500 SIZE(v7d_tmp%volanai, 3)))
6501 DO i = 1, SIZE(v7d_tmp%anavar%i)
6502 v7d_tmp%volanar(:,i,:) = &
6503 realdat(v7d_tmp%volanai(:,i,:), v7d_tmp%anavar%i(i))
6504 ENDDO
6505 DEALLOCATE(v7d_tmp%volanai)
6506! trasferisco le variabili
6507 v7d_tmp%anavar%r => v7d_tmp%anavar%i
6508 NULLIFY(v7d_tmp%anavar%i)
6509 ENDIF
6510
6511 IF (ASSOCIATED(v7d_tmp%dativar%i)) THEN
6512! alloco i dati reali e vi trasferisco gli interi
6513 ALLOCATE(v7d_tmp%voldatir(SIZE(v7d_tmp%voldatii, 1), SIZE(v7d_tmp%voldatii, 2), &
6514 SIZE(v7d_tmp%voldatii, 3), SIZE(v7d_tmp%voldatii, 4), SIZE(v7d_tmp%voldatii, 5), &
6515 SIZE(v7d_tmp%voldatii, 6)))
6516 DO i = 1, SIZE(v7d_tmp%dativar%i)
6517 v7d_tmp%voldatir(:,:,:,:,i,:) = &
6518 realdat(v7d_tmp%voldatii(:,:,:,:,i,:), v7d_tmp%dativar%i(i))
6519 ENDDO
6520 DEALLOCATE(v7d_tmp%voldatii)
6521! trasferisco le variabili
6522 v7d_tmp%dativar%r => v7d_tmp%dativar%i
6523 NULLIFY(v7d_tmp%dativar%i)
6524 ENDIF
6525
6526! fondo con il volume definitivo
6527 CALL vol7d_merge(that, v7d_tmp)
6528ELSE
6530ENDIF
6531
6532
6533! Volume solo di dati byte
6534CALL vol7d_copy(this, v7d_tmp, &
6535 lanavarr=fv, lanavard=fv, lanavari=fv, lanavarb=acn, lanavarc=fv, &
6536 lanaattrr=fv, lanaattrd=fv, lanaattri=fv, lanaattrb=fv, lanaattrc=fv, &
6537 lanavarattrr=fv, lanavarattrd=fv, lanavarattri=fv, lanavarattrb=fv, lanavarattrc=fv, &
6538 ldativarr=fv, ldativard=fv, ldativari=fv, ldativarb=tv, ldativarc=fv, &
6539 ldatiattrr=fv, ldatiattrd=fv, ldatiattri=fv, ldatiattrb=fv, ldatiattrc=fv, &
6540 ldativarattrr=fv, ldativarattrd=fv, ldativarattri=fv, ldativarattrb=fv, ldativarattrc=fv)
6541
6542! converto a dati reali
6543IF (ASSOCIATED(v7d_tmp%anavar%b) .OR. ASSOCIATED(v7d_tmp%dativar%b)) THEN
6544
6545 IF (ASSOCIATED(v7d_tmp%anavar%b)) THEN
6546! alloco i dati reali e vi trasferisco i byte
6547 ALLOCATE(v7d_tmp%volanar(SIZE(v7d_tmp%volanab, 1), SIZE(v7d_tmp%volanab, 2), &
6548 SIZE(v7d_tmp%volanab, 3)))
6549 DO i = 1, SIZE(v7d_tmp%anavar%b)
6550 v7d_tmp%volanar(:,i,:) = &
6551 realdat(v7d_tmp%volanab(:,i,:), v7d_tmp%anavar%b(i))
6552 ENDDO
6553 DEALLOCATE(v7d_tmp%volanab)
6554! trasferisco le variabili
6555 v7d_tmp%anavar%r => v7d_tmp%anavar%b
6556 NULLIFY(v7d_tmp%anavar%b)
6557 ENDIF
6558
6559 IF (ASSOCIATED(v7d_tmp%dativar%b)) THEN
6560! alloco i dati reali e vi trasferisco i byte
6561 ALLOCATE(v7d_tmp%voldatir(SIZE(v7d_tmp%voldatib, 1), SIZE(v7d_tmp%voldatib, 2), &
6562 SIZE(v7d_tmp%voldatib, 3), SIZE(v7d_tmp%voldatib, 4), SIZE(v7d_tmp%voldatib, 5), &
6563 SIZE(v7d_tmp%voldatib, 6)))
6564 DO i = 1, SIZE(v7d_tmp%dativar%b)
6565 v7d_tmp%voldatir(:,:,:,:,i,:) = &
6566 realdat(v7d_tmp%voldatib(:,:,:,:,i,:), v7d_tmp%dativar%b(i))
6567 ENDDO
6568 DEALLOCATE(v7d_tmp%voldatib)
6569! trasferisco le variabili
6570 v7d_tmp%dativar%r => v7d_tmp%dativar%b
6571 NULLIFY(v7d_tmp%dativar%b)
6572 ENDIF
6573
6574! fondo con il volume definitivo
6575 CALL vol7d_merge(that, v7d_tmp)
6576ELSE
6578ENDIF
6579
6580
6581! Volume solo di dati character
6582CALL vol7d_copy(this, v7d_tmp, &
6583 lanavarr=fv, lanavard=fv, lanavari=fv, lanavarb=fv, lanavarc=acn, &
6584 lanaattrr=fv, lanaattrd=fv, lanaattri=fv, lanaattrb=fv, lanaattrc=fv, &
6585 lanavarattrr=fv, lanavarattrd=fv, lanavarattri=fv, lanavarattrb=fv, lanavarattrc=fv, &
6586 ldativarr=fv, ldativard=fv, ldativari=fv, ldativarb=fv, ldativarc=tv, &
6587 ldatiattrr=fv, ldatiattrd=fv, ldatiattri=fv, ldatiattrb=fv, ldatiattrc=fv, &
6588 ldativarattrr=fv, ldativarattrd=fv, ldativarattri=fv, ldativarattrb=fv, ldativarattrc=fv)
6589
6590! converto a dati reali
6591IF (ASSOCIATED(v7d_tmp%anavar%c) .OR. ASSOCIATED(v7d_tmp%dativar%c)) THEN
6592
6593 IF (ASSOCIATED(v7d_tmp%anavar%c)) THEN
6594! alloco i dati reali e vi trasferisco i character
6595 ALLOCATE(v7d_tmp%volanar(SIZE(v7d_tmp%volanac, 1), SIZE(v7d_tmp%volanac, 2), &
6596 SIZE(v7d_tmp%volanac, 3)))
6597 DO i = 1, SIZE(v7d_tmp%anavar%c)
6598 v7d_tmp%volanar(:,i,:) = &
6599 realdat(v7d_tmp%volanac(:,i,:), v7d_tmp%anavar%c(i))
6600 ENDDO
6601 DEALLOCATE(v7d_tmp%volanac)
6602! trasferisco le variabili
6603 v7d_tmp%anavar%r => v7d_tmp%anavar%c
6604 NULLIFY(v7d_tmp%anavar%c)
6605 ENDIF
6606
6607 IF (ASSOCIATED(v7d_tmp%dativar%c)) THEN
6608! alloco i dati reali e vi trasferisco i character
6609 ALLOCATE(v7d_tmp%voldatir(SIZE(v7d_tmp%voldatic, 1), SIZE(v7d_tmp%voldatic, 2), &
6610 SIZE(v7d_tmp%voldatic, 3), SIZE(v7d_tmp%voldatic, 4), SIZE(v7d_tmp%voldatic, 5), &
6611 SIZE(v7d_tmp%voldatic, 6)))
6612 DO i = 1, SIZE(v7d_tmp%dativar%c)
6613 v7d_tmp%voldatir(:,:,:,:,i,:) = &
6614 realdat(v7d_tmp%voldatic(:,:,:,:,i,:), v7d_tmp%dativar%c(i))
6615 ENDDO
6616 DEALLOCATE(v7d_tmp%voldatic)
6617! trasferisco le variabili
6618 v7d_tmp%dativar%r => v7d_tmp%dativar%c
6619 NULLIFY(v7d_tmp%dativar%c)
6620 ENDIF
6621
6622! fondo con il volume definitivo
6623 CALL vol7d_merge(that, v7d_tmp)
6624ELSE
6626ENDIF
6627
6628END SUBROUTINE vol7d_convr
6629
6630
6631!> Metodo per ottenere solo le differenze tra due oggetti vol7d.
6632!! Il primo volume viene confrontato col secondo; nel secondo volume ovunque
6633!! i dati confrontati siano coincidenti viene impostato valore mancante.
6634SUBROUTINE vol7d_diff_only (this, that, data_only,ana)
6635TYPE(vol7d),INTENT(IN) :: this !< primo volume da confrontare
6636TYPE(vol7d),INTENT(OUT) :: that !< secondo volume da confrontare in cui eliminare i dati coincidenti
6637logical , optional, intent(in) :: data_only !< attiva l'elaborazione dei soli dati e non dell'anagrafica (default: .false.)
6638logical , optional, intent(in) :: ana !< attiva l'elaborazione dell'anagrafica (coordinate e ident) (default: .false.)
6639logical :: ldata_only,lana
6640
6641IF (PRESENT(data_only)) THEN
6642 ldata_only = data_only
6643ELSE
6644 ldata_only = .false.
6645ENDIF
6646
6647IF (PRESENT(ana)) THEN
6648 lana = ana
6649ELSE
6650 lana = .false.
6651ENDIF
6652
6653
6654#undef VOL7D_POLY_ARRAY
6655#define VOL7D_POLY_ARRAY voldati
6656#include "vol7d_class_diff.F90"
6657#undef VOL7D_POLY_ARRAY
6658#define VOL7D_POLY_ARRAY voldatiattr
6659#include "vol7d_class_diff.F90"
6660#undef VOL7D_POLY_ARRAY
6661
6662if ( .not. ldata_only) then
6663
6664#define VOL7D_POLY_ARRAY volana
6665#include "vol7d_class_diff.F90"
6666#undef VOL7D_POLY_ARRAY
6667#define VOL7D_POLY_ARRAY volanaattr
6668#include "vol7d_class_diff.F90"
6669#undef VOL7D_POLY_ARRAY
6670
6671 if(lana)then
6672 where ( this%ana == that%ana )
6673 that%ana = vol7d_ana_miss
6674 end where
6675 end if
6676
6677end if
6678
6679
6680
6681END SUBROUTINE vol7d_diff_only
6682
6683
6684
6685! Creo le routine da ripetere per i vari tipi di dati di v7d
6686! tramite un template e il preprocessore
6687#undef VOL7D_POLY_TYPE
6688#undef VOL7D_POLY_TYPES
6689#define VOL7D_POLY_TYPE REAL
6690#define VOL7D_POLY_TYPES r
6691#include "vol7d_class_type_templ.F90"
6692#undef VOL7D_POLY_TYPE
6693#undef VOL7D_POLY_TYPES
6694#define VOL7D_POLY_TYPE DOUBLE PRECISION
6695#define VOL7D_POLY_TYPES d
6696#include "vol7d_class_type_templ.F90"
6697#undef VOL7D_POLY_TYPE
6698#undef VOL7D_POLY_TYPES
6699#define VOL7D_POLY_TYPE INTEGER
6700#define VOL7D_POLY_TYPES i
6701#include "vol7d_class_type_templ.F90"
6702#undef VOL7D_POLY_TYPE
6703#undef VOL7D_POLY_TYPES
6704#define VOL7D_POLY_TYPE INTEGER(kind=int_b)
6705#define VOL7D_POLY_TYPES b
6706#include "vol7d_class_type_templ.F90"
6707#undef VOL7D_POLY_TYPE
6708#undef VOL7D_POLY_TYPES
6709#define VOL7D_POLY_TYPE CHARACTER(len=vol7d_cdatalen)
6710#define VOL7D_POLY_TYPES c
6711#include "vol7d_class_type_templ.F90"
6712
6713! Creo le routine da ripetere per i vari descrittori di dimensioni di v7d
6714! tramite un template e il preprocessore
6715#define VOL7D_SORT
6716#undef VOL7D_NO_ZERO_ALLOC
6717#undef VOL7D_POLY_TYPE
6718#define VOL7D_POLY_TYPE datetime
6719#include "vol7d_class_desc_templ.F90"
6720#undef VOL7D_POLY_TYPE
6721#define VOL7D_POLY_TYPE vol7d_timerange
6722#include "vol7d_class_desc_templ.F90"
6723#undef VOL7D_POLY_TYPE
6724#define VOL7D_POLY_TYPE vol7d_level
6725#include "vol7d_class_desc_templ.F90"
6726#undef VOL7D_SORT
6727#undef VOL7D_POLY_TYPE
6728#define VOL7D_POLY_TYPE vol7d_network
6729#include "vol7d_class_desc_templ.F90"
6730#undef VOL7D_POLY_TYPE
6731#define VOL7D_POLY_TYPE vol7d_ana
6732#include "vol7d_class_desc_templ.F90"
6733#define VOL7D_NO_ZERO_ALLOC
6734#undef VOL7D_POLY_TYPE
6735#define VOL7D_POLY_TYPE vol7d_var
6736#include "vol7d_class_desc_templ.F90"
6737
6738!>\brief Scrittura su file di un volume Vol7d.
6739!! Scrittura su file unformatted di un intero volume Vol7d.
6740!! Il volume viene serializzato e scritto su file.
6741!! Il file puo' essere aperto opzionalmente dall'utente. Si possono passare
6742!! opzionalmente unità e nome del file altrimenti assegnati internamente a dei default; se assegnati internamente
6743!! tali parametri saranno in output.
6744!! Se non viene fornito il nome file viene utilizzato un file di default con nome pari al nome del programma in
6745!! esecuzione con postfisso ".v7d".
6746!! Come parametro opzionale c'è la description che insieme alla data corrente viene inserita nell'header del file.
6747subroutine vol7d_write_on_file (this,unit,description,filename,filename_auto)
6748
6749TYPE(vol7d),INTENT(IN) :: this !< volume vol7d da scrivere
6750integer,optional,intent(inout) :: unit !< unità su cui scrivere; se passata =0 ritorna il valore rielaborato (default =rielaborato internamente con getlun )
6751character(len=*),intent(in),optional :: filename !< nome del file su cui scrivere
6752character(len=*),intent(out),optional :: filename_auto !< nome del file generato se "filename" è omesso
6753character(len=*),INTENT(IN),optional :: description !< descrizione del volume
6754
6755integer :: lunit
6756character(len=254) :: ldescription,arg,lfilename
6757integer :: nana, ntime, ntimerange, nlevel, nnetwork, &
6758 ndativarr, ndativari, ndativarb, ndativard, ndativarc,&
6759 ndatiattrr, ndatiattri, ndatiattrb, ndatiattrd, ndatiattrc,&
6760 ndativarattrr, ndativarattri, ndativarattrb, ndativarattrd, ndativarattrc,&
6761 nanavarr, nanavari, nanavarb, nanavard, nanavarc,&
6762 nanaattrr, nanaattri, nanaattrb, nanaattrd, nanaattrc,&
6763 nanavarattrr, nanavarattri, nanavarattrb, nanavarattrd, nanavarattrc
6764!integer :: im,id,iy
6765integer :: tarray(8)
6766logical :: opened,exist
6767
6768 nana=0
6769 ntime=0
6770 ntimerange=0
6771 nlevel=0
6772 nnetwork=0
6773 ndativarr=0
6774 ndativari=0
6775 ndativarb=0
6776 ndativard=0
6777 ndativarc=0
6778 ndatiattrr=0
6779 ndatiattri=0
6780 ndatiattrb=0
6781 ndatiattrd=0
6782 ndatiattrc=0
6783 ndativarattrr=0
6784 ndativarattri=0
6785 ndativarattrb=0
6786 ndativarattrd=0
6787 ndativarattrc=0
6788 nanavarr=0
6789 nanavari=0
6790 nanavarb=0
6791 nanavard=0
6792 nanavarc=0
6793 nanaattrr=0
6794 nanaattri=0
6795 nanaattrb=0
6796 nanaattrd=0
6797 nanaattrc=0
6798 nanavarattrr=0
6799 nanavarattri=0
6800 nanavarattrb=0
6801 nanavarattrd=0
6802 nanavarattrc=0
6803
6804
6805!call idate(im,id,iy)
6806call date_and_time(values=tarray)
6807call getarg(0,arg)
6808
6809if (present(description))then
6810 ldescription=description
6811else
6812 ldescription="Vol7d generated by: "//trim(arg)
6813end if
6814
6815if (.not. present(unit))then
6816 lunit=getunit()
6817else
6818 if (unit==0)then
6819 lunit=getunit()
6820 unit=lunit
6821 else
6822 lunit=unit
6823 end if
6824end if
6825
6826lfilename=trim(arg)//".v7d"
6828
6829if (present(filename))then
6830 if (filename /= "")then
6831 lfilename=filename
6832 end if
6833end if
6834
6835if (present(filename_auto))filename_auto=lfilename
6836
6837
6838inquire(unit=lunit,opened=opened)
6839if (.not. opened) then
6840! inquire(file=lfilename, EXIST=exist)
6841! IF (exist) THEN
6842! CALL l4f_log(L4F_FATAL, &
6843! 'in vol7d_write_on_file, file exists, cannot open file '//TRIM(lfilename))
6844! CALL raise_fatal_error()
6845! ENDIF
6846 OPEN(unit=lunit, file=lfilename, form='UNFORMATTED', access='STREAM')
6847 CALL l4f_log(l4f_info, 'opened: '//trim(lfilename))
6848end if
6849
6850if (associated(this%ana)) nana=size(this%ana)
6851if (associated(this%time)) ntime=size(this%time)
6852if (associated(this%timerange)) ntimerange=size(this%timerange)
6853if (associated(this%level)) nlevel=size(this%level)
6854if (associated(this%network)) nnetwork=size(this%network)
6855
6856if (associated(this%dativar%r)) ndativarr=size(this%dativar%r)
6857if (associated(this%dativar%i)) ndativari=size(this%dativar%i)
6858if (associated(this%dativar%b)) ndativarb=size(this%dativar%b)
6859if (associated(this%dativar%d)) ndativard=size(this%dativar%d)
6860if (associated(this%dativar%c)) ndativarc=size(this%dativar%c)
6861
6862if (associated(this%datiattr%r)) ndatiattrr=size(this%datiattr%r)
6863if (associated(this%datiattr%i)) ndatiattri=size(this%datiattr%i)
6864if (associated(this%datiattr%b)) ndatiattrb=size(this%datiattr%b)
6865if (associated(this%datiattr%d)) ndatiattrd=size(this%datiattr%d)
6866if (associated(this%datiattr%c)) ndatiattrc=size(this%datiattr%c)
6867
6868if (associated(this%dativarattr%r)) ndativarattrr=size(this%dativarattr%r)
6869if (associated(this%dativarattr%i)) ndativarattri=size(this%dativarattr%i)
6870if (associated(this%dativarattr%b)) ndativarattrb=size(this%dativarattr%b)
6871if (associated(this%dativarattr%d)) ndativarattrd=size(this%dativarattr%d)
6872if (associated(this%dativarattr%c)) ndativarattrc=size(this%dativarattr%c)
6873
6874if (associated(this%anavar%r)) nanavarr=size(this%anavar%r)
6875if (associated(this%anavar%i)) nanavari=size(this%anavar%i)
6876if (associated(this%anavar%b)) nanavarb=size(this%anavar%b)
6877if (associated(this%anavar%d)) nanavard=size(this%anavar%d)
6878if (associated(this%anavar%c)) nanavarc=size(this%anavar%c)
6879
6880if (associated(this%anaattr%r)) nanaattrr=size(this%anaattr%r)
6881if (associated(this%anaattr%i)) nanaattri=size(this%anaattr%i)
6882if (associated(this%anaattr%b)) nanaattrb=size(this%anaattr%b)
6883if (associated(this%anaattr%d)) nanaattrd=size(this%anaattr%d)
6884if (associated(this%anaattr%c)) nanaattrc=size(this%anaattr%c)
6885
6886if (associated(this%anavarattr%r)) nanavarattrr=size(this%anavarattr%r)
6887if (associated(this%anavarattr%i)) nanavarattri=size(this%anavarattr%i)
6888if (associated(this%anavarattr%b)) nanavarattrb=size(this%anavarattr%b)
6889if (associated(this%anavarattr%d)) nanavarattrd=size(this%anavarattr%d)
6890if (associated(this%anavarattr%c)) nanavarattrc=size(this%anavarattr%c)
6891
6892write(unit=lunit)ldescription
6893write(unit=lunit)tarray
6894
6895write(unit=lunit)&
6896 nana, ntime, ntimerange, nlevel, nnetwork, &
6897 ndativarr, ndativari, ndativarb, ndativard, ndativarc,&
6898 ndatiattrr, ndatiattri, ndatiattrb, ndatiattrd, ndatiattrc,&
6899 ndativarattrr, ndativarattri, ndativarattrb, ndativarattrd, ndativarattrc,&
6900 nanavarr, nanavari, nanavarb, nanavard, nanavarc,&
6901 nanaattrr, nanaattri, nanaattrb, nanaattrd, nanaattrc,&
6902 nanavarattrr, nanavarattri, nanavarattrb, nanavarattrd, nanavarattrc, &
6903 this%time_definition
6904
6905
6906!write(unit=lunit)this
6907
6908
6909!! prime 5 dimensioni
6912if (associated(this%level)) write(unit=lunit)this%level
6913if (associated(this%timerange)) write(unit=lunit)this%timerange
6914if (associated(this%network)) write(unit=lunit)this%network
6915
6916 !! 6a dimensione: variabile dell'anagrafica e dei dati
6917 !! con relativi attributi e in 5 tipi diversi
6918
6919if (associated(this%anavar%r)) write(unit=lunit)this%anavar%r
6920if (associated(this%anavar%i)) write(unit=lunit)this%anavar%i
6921if (associated(this%anavar%b)) write(unit=lunit)this%anavar%b
6922if (associated(this%anavar%d)) write(unit=lunit)this%anavar%d
6923if (associated(this%anavar%c)) write(unit=lunit)this%anavar%c
6924
6925if (associated(this%anaattr%r)) write(unit=lunit)this%anaattr%r
6926if (associated(this%anaattr%i)) write(unit=lunit)this%anaattr%i
6927if (associated(this%anaattr%b)) write(unit=lunit)this%anaattr%b
6928if (associated(this%anaattr%d)) write(unit=lunit)this%anaattr%d
6929if (associated(this%anaattr%c)) write(unit=lunit)this%anaattr%c
6930
6931if (associated(this%anavarattr%r)) write(unit=lunit)this%anavarattr%r
6932if (associated(this%anavarattr%i)) write(unit=lunit)this%anavarattr%i
6933if (associated(this%anavarattr%b)) write(unit=lunit)this%anavarattr%b
6934if (associated(this%anavarattr%d)) write(unit=lunit)this%anavarattr%d
6935if (associated(this%anavarattr%c)) write(unit=lunit)this%anavarattr%c
6936
6937if (associated(this%dativar%r)) write(unit=lunit)this%dativar%r
6938if (associated(this%dativar%i)) write(unit=lunit)this%dativar%i
6939if (associated(this%dativar%b)) write(unit=lunit)this%dativar%b
6940if (associated(this%dativar%d)) write(unit=lunit)this%dativar%d
6941if (associated(this%dativar%c)) write(unit=lunit)this%dativar%c
6942
6943if (associated(this%datiattr%r)) write(unit=lunit)this%datiattr%r
6944if (associated(this%datiattr%i)) write(unit=lunit)this%datiattr%i
6945if (associated(this%datiattr%b)) write(unit=lunit)this%datiattr%b
6946if (associated(this%datiattr%d)) write(unit=lunit)this%datiattr%d
6947if (associated(this%datiattr%c)) write(unit=lunit)this%datiattr%c
6948
6949if (associated(this%dativarattr%r)) write(unit=lunit)this%dativarattr%r
6950if (associated(this%dativarattr%i)) write(unit=lunit)this%dativarattr%i
6951if (associated(this%dativarattr%b)) write(unit=lunit)this%dativarattr%b
6952if (associated(this%dativarattr%d)) write(unit=lunit)this%dativarattr%d
6953if (associated(this%dativarattr%c)) write(unit=lunit)this%dativarattr%c
6954
6955!! Volumi di valori e attributi per anagrafica e dati
6956
6957if (associated(this%volanar)) write(unit=lunit)this%volanar
6958if (associated(this%volanaattrr)) write(unit=lunit)this%volanaattrr
6959if (associated(this%voldatir)) write(unit=lunit)this%voldatir
6960if (associated(this%voldatiattrr)) write(unit=lunit)this%voldatiattrr
6961
6962if (associated(this%volanai)) write(unit=lunit)this%volanai
6963if (associated(this%volanaattri)) write(unit=lunit)this%volanaattri
6964if (associated(this%voldatii)) write(unit=lunit)this%voldatii
6965if (associated(this%voldatiattri)) write(unit=lunit)this%voldatiattri
6966
6967if (associated(this%volanab)) write(unit=lunit)this%volanab
6968if (associated(this%volanaattrb)) write(unit=lunit)this%volanaattrb
6969if (associated(this%voldatib)) write(unit=lunit)this%voldatib
6970if (associated(this%voldatiattrb)) write(unit=lunit)this%voldatiattrb
6971
6972if (associated(this%volanad)) write(unit=lunit)this%volanad
6973if (associated(this%volanaattrd)) write(unit=lunit)this%volanaattrd
6974if (associated(this%voldatid)) write(unit=lunit)this%voldatid
6975if (associated(this%voldatiattrd)) write(unit=lunit)this%voldatiattrd
6976
6977if (associated(this%volanac)) write(unit=lunit)this%volanac
6978if (associated(this%volanaattrc)) write(unit=lunit)this%volanaattrc
6979if (associated(this%voldatic)) write(unit=lunit)this%voldatic
6980if (associated(this%voldatiattrc)) write(unit=lunit)this%voldatiattrc
6981
6982if (.not. present(unit)) close(unit=lunit)
6983
6984end subroutine vol7d_write_on_file
6985
6986
6987!>\brief Lettura da file di un volume Vol7d.
6988!! Lettura da file unformatted di un intero volume Vol7d.
6989!! Questa subroutine comprende vol7d_alloc e vol7d_alloc_vol.
6990!! Il file puo' essere aperto opzionalmente dall'utente. Si possono passare
6991!! opzionalmente unità e nome del file altrimenti assegnati internamente a dei default; se assegnati internamente
6992!! tali parametri saranno in output.
6993
6994
6995subroutine vol7d_read_from_file (this,unit,filename,description,tarray,filename_auto)
6996
6997TYPE(vol7d),INTENT(OUT) :: this !< Volume vol7d da leggere
6998integer,intent(inout),optional :: unit !< unità su cui è stato aperto un file; se =0 rielaborato internamente (default = elaborato internamente con getunit)
6999character(len=*),INTENT(in),optional :: filename !< nome del file eventualmente da aprire (default = (nome dell'eseguibile)//.v7d )
7000character(len=*),intent(out),optional :: filename_auto !< nome del file generato se "filename" è omesso
7001character(len=*),INTENT(out),optional :: description !< descrizione del volume letto
7002integer,intent(out),optional :: tarray(8) !< vettore come definito da "date_and_time" della data di scrittura del volume
7003
7004
7005integer :: nana, ntime, ntimerange, nlevel, nnetwork, &
7006 ndativarr, ndativari, ndativarb, ndativard, ndativarc,&
7007 ndatiattrr, ndatiattri, ndatiattrb, ndatiattrd, ndatiattrc,&
7008 ndativarattrr, ndativarattri, ndativarattrb, ndativarattrd, ndativarattrc,&
7009 nanavarr, nanavari, nanavarb, nanavard, nanavarc,&
7010 nanaattrr, nanaattri, nanaattrb, nanaattrd, nanaattrc,&
7011 nanavarattrr, nanavarattri, nanavarattrb, nanavarattrd, nanavarattrc
7012
7013character(len=254) :: ldescription,lfilename,arg
7014integer :: ltarray(8),lunit,ios
7015logical :: opened,exist
7016
7017
7018call getarg(0,arg)
7019
7020if (.not. present(unit))then
7021 lunit=getunit()
7022else
7023 if (unit==0)then
7024 lunit=getunit()
7025 unit=lunit
7026 else
7027 lunit=unit
7028 end if
7029end if
7030
7031lfilename=trim(arg)//".v7d"
7033
7034if (present(filename))then
7035 if (filename /= "")then
7036 lfilename=filename
7037 end if
7038end if
7039
7040if (present(filename_auto))filename_auto=lfilename
7041
7042
7043inquire(unit=lunit,opened=opened)
7044IF (.NOT. opened) THEN
7045 inquire(file=lfilename,exist=exist)
7046 IF (.NOT.exist) THEN
7047 CALL l4f_log(l4f_fatal, &
7048 'in vol7d_read_from_file, file does not exists, cannot open')
7049 CALL raise_fatal_error()
7050 ENDIF
7051 OPEN(unit=lunit, file=lfilename, form='UNFORMATTED', access='STREAM', &
7052 status='OLD', action='READ')
7053 CALL l4f_log(l4f_info, 'opened: '//trim(lfilename))
7054end if
7055
7056
7058read(unit=lunit,iostat=ios)ldescription
7059
7060if (ios < 0) then ! A negative value indicates that the End of File or End of Record
7061 call vol7d_alloc (this)
7062 call vol7d_alloc_vol (this)
7063 if (present(description))description=ldescription
7064 if (present(tarray))tarray=ltarray
7065 if (.not. present(unit)) close(unit=lunit)
7066end if
7067
7068read(unit=lunit)ltarray
7069
7070CALL l4f_log(l4f_info, 'Reading vol7d from file')
7071CALL l4f_log(l4f_info, 'description: '//trim(ldescription))
7074
7075if (present(description))description=ldescription
7076if (present(tarray))tarray=ltarray
7077
7078read(unit=lunit)&
7079 nana, ntime, ntimerange, nlevel, nnetwork, &
7080 ndativarr, ndativari, ndativarb, ndativard, ndativarc,&
7081 ndatiattrr, ndatiattri, ndatiattrb, ndatiattrd, ndatiattrc,&
7082 ndativarattrr, ndativarattri, ndativarattrb, ndativarattrd, ndativarattrc,&
7083 nanavarr, nanavari, nanavarb, nanavard, nanavarc,&
7084 nanaattrr, nanaattri, nanaattrb, nanaattrd, nanaattrc,&
7085 nanavarattrr, nanavarattri, nanavarattrb, nanavarattrd, nanavarattrc, &
7086 this%time_definition
7087
7088call vol7d_alloc (this, &
7089 nana=nana, ntime=ntime, ntimerange=ntimerange, nlevel=nlevel, nnetwork=nnetwork,&
7090 ndativarr=ndativarr, ndativari=ndativari, ndativarb=ndativarb,&
7091 ndativard=ndativard, ndativarc=ndativarc,&
7092 ndatiattrr=ndatiattrr, ndatiattri=ndatiattri, ndatiattrb=ndatiattrb,&
7093 ndatiattrd=ndatiattrd, ndatiattrc=ndatiattrc,&
7094 ndativarattrr=ndativarattrr, ndativarattri=ndativarattri, ndativarattrb=ndativarattrb, &
7095 ndativarattrd=ndativarattrd, ndativarattrc=ndativarattrc,&
7096 nanavarr=nanavarr, nanavari=nanavari, nanavarb=nanavarb, &
7097 nanavard=nanavard, nanavarc=nanavarc,&
7098 nanaattrr=nanaattrr, nanaattri=nanaattri, nanaattrb=nanaattrb,&
7099 nanaattrd=nanaattrd, nanaattrc=nanaattrc,&
7100 nanavarattrr=nanavarattrr, nanavarattri=nanavarattri, nanavarattrb=nanavarattrb, &
7101 nanavarattrd=nanavarattrd, nanavarattrc=nanavarattrc)
7102
7103
7106if (associated(this%level)) read(unit=lunit)this%level
7107if (associated(this%timerange)) read(unit=lunit)this%timerange
7108if (associated(this%network)) read(unit=lunit)this%network
7109
7110if (associated(this%anavar%r)) read(unit=lunit)this%anavar%r
7111if (associated(this%anavar%i)) read(unit=lunit)this%anavar%i
7112if (associated(this%anavar%b)) read(unit=lunit)this%anavar%b
7113if (associated(this%anavar%d)) read(unit=lunit)this%anavar%d
7114if (associated(this%anavar%c)) read(unit=lunit)this%anavar%c
7115
7116if (associated(this%anaattr%r)) read(unit=lunit)this%anaattr%r
7117if (associated(this%anaattr%i)) read(unit=lunit)this%anaattr%i
7118if (associated(this%anaattr%b)) read(unit=lunit)this%anaattr%b
7119if (associated(this%anaattr%d)) read(unit=lunit)this%anaattr%d
7120if (associated(this%anaattr%c)) read(unit=lunit)this%anaattr%c
7121
7122if (associated(this%anavarattr%r)) read(unit=lunit)this%anavarattr%r
7123if (associated(this%anavarattr%i)) read(unit=lunit)this%anavarattr%i
7124if (associated(this%anavarattr%b)) read(unit=lunit)this%anavarattr%b
7125if (associated(this%anavarattr%d)) read(unit=lunit)this%anavarattr%d
7126if (associated(this%anavarattr%c)) read(unit=lunit)this%anavarattr%c
7127
7128if (associated(this%dativar%r)) read(unit=lunit)this%dativar%r
7129if (associated(this%dativar%i)) read(unit=lunit)this%dativar%i
7130if (associated(this%dativar%b)) read(unit=lunit)this%dativar%b
7131if (associated(this%dativar%d)) read(unit=lunit)this%dativar%d
7132if (associated(this%dativar%c)) read(unit=lunit)this%dativar%c
7133
7134if (associated(this%datiattr%r)) read(unit=lunit)this%datiattr%r
7135if (associated(this%datiattr%i)) read(unit=lunit)this%datiattr%i
7136if (associated(this%datiattr%b)) read(unit=lunit)this%datiattr%b
7137if (associated(this%datiattr%d)) read(unit=lunit)this%datiattr%d
7138if (associated(this%datiattr%c)) read(unit=lunit)this%datiattr%c
7139
7140if (associated(this%dativarattr%r)) read(unit=lunit)this%dativarattr%r
7141if (associated(this%dativarattr%i)) read(unit=lunit)this%dativarattr%i
7142if (associated(this%dativarattr%b)) read(unit=lunit)this%dativarattr%b
7143if (associated(this%dativarattr%d)) read(unit=lunit)this%dativarattr%d
7144if (associated(this%dativarattr%c)) read(unit=lunit)this%dativarattr%c
7145
7146call vol7d_alloc_vol (this)
7147
7148!! Volumi di valori e attributi per anagrafica e dati
7149
7150if (associated(this%volanar)) read(unit=lunit)this%volanar
7151if (associated(this%volanaattrr)) read(unit=lunit)this%volanaattrr
7152if (associated(this%voldatir)) read(unit=lunit)this%voldatir
7153if (associated(this%voldatiattrr)) read(unit=lunit)this%voldatiattrr
7154
7155if (associated(this%volanai)) read(unit=lunit)this%volanai
7156if (associated(this%volanaattri)) read(unit=lunit)this%volanaattri
7157if (associated(this%voldatii)) read(unit=lunit)this%voldatii
7158if (associated(this%voldatiattri)) read(unit=lunit)this%voldatiattri
7159
7160if (associated(this%volanab)) read(unit=lunit)this%volanab
7161if (associated(this%volanaattrb)) read(unit=lunit)this%volanaattrb
7162if (associated(this%voldatib)) read(unit=lunit)this%voldatib
7163if (associated(this%voldatiattrb)) read(unit=lunit)this%voldatiattrb
7164
7165if (associated(this%volanad)) read(unit=lunit)this%volanad
7166if (associated(this%volanaattrd)) read(unit=lunit)this%volanaattrd
7167if (associated(this%voldatid)) read(unit=lunit)this%voldatid
7168if (associated(this%voldatiattrd)) read(unit=lunit)this%voldatiattrd
7169
7170if (associated(this%volanac)) read(unit=lunit)this%volanac
7171if (associated(this%volanaattrc)) read(unit=lunit)this%volanaattrc
7172if (associated(this%voldatic)) read(unit=lunit)this%voldatic
7173if (associated(this%voldatiattrc)) read(unit=lunit)this%voldatiattrc
7174
7175if (.not. present(unit)) close(unit=lunit)
7176
7177end subroutine vol7d_read_from_file
7178
7179
7180! to double precision
7181elemental doubleprecision function doubledatd(voldat,var)
7182doubleprecision,intent(in) :: voldat
7183type(vol7d_var),intent(in) :: var
7184
7185doubledatd=voldat
7186
7187end function doubledatd
7188
7189
7190elemental doubleprecision function doubledatr(voldat,var)
7191real,intent(in) :: voldat
7192type(vol7d_var),intent(in) :: var
7193
7195 doubledatr=dble(voldat)
7196else
7197 doubledatr=dmiss
7198end if
7199
7200end function doubledatr
7201
7202
7203elemental doubleprecision function doubledati(voldat,var)
7204integer,intent(in) :: voldat
7205type(vol7d_var),intent(in) :: var
7206
7209 doubledati=dble(voldat)/10.d0**var%scalefactor
7210 else
7211 doubledati=dble(voldat)
7212 endif
7213else
7214 doubledati=dmiss
7215end if
7216
7217end function doubledati
7218
7219
7220elemental doubleprecision function doubledatb(voldat,var)
7221integer(kind=int_b),intent(in) :: voldat
7222type(vol7d_var),intent(in) :: var
7223
7226 doubledatb=dble(voldat)/10.d0**var%scalefactor
7227 else
7228 doubledatb=dble(voldat)
7229 endif
7230else
7231 doubledatb=dmiss
7232end if
7233
7234end function doubledatb
7235
7236
7237elemental doubleprecision function doubledatc(voldat,var)
7238CHARACTER(len=vol7d_cdatalen),intent(in) :: voldat
7239type(vol7d_var),intent(in) :: var
7240
7241doubledatc = c2d(voldat)
7243 doubledatc=doubledatc/10.d0**var%scalefactor
7244end if
7245
7246end function doubledatc
7247
7248
7249! to integer
7250elemental integer function integerdatd(voldat,var)
7251doubleprecision,intent(in) :: voldat
7252type(vol7d_var),intent(in) :: var
7253
7256 integerdatd=nint(voldat*10d0**var%scalefactor)
7257 else
7258 integerdatd=nint(voldat)
7259 endif
7260else
7261 integerdatd=imiss
7262end if
7263
7264end function integerdatd
7265
7266
7267elemental integer function integerdatr(voldat,var)
7268real,intent(in) :: voldat
7269type(vol7d_var),intent(in) :: var
7270
7273 integerdatr=nint(voldat*10d0**var%scalefactor)
7274 else
7275 integerdatr=nint(voldat)
7276 endif
7277else
7278 integerdatr=imiss
7279end if
7280
7281end function integerdatr
7282
7283
7284elemental integer function integerdati(voldat,var)
7285integer,intent(in) :: voldat
7286type(vol7d_var),intent(in) :: var
7287
7288integerdati=voldat
7289
7290end function integerdati
7291
7292
7293elemental integer function integerdatb(voldat,var)
7294integer(kind=int_b),intent(in) :: voldat
7295type(vol7d_var),intent(in) :: var
7296
7298 integerdatb=voldat
7299else
7300 integerdatb=imiss
7301end if
7302
7303end function integerdatb
7304
7305
7306elemental integer function integerdatc(voldat,var)
7307CHARACTER(len=vol7d_cdatalen),intent(in) :: voldat
7308type(vol7d_var),intent(in) :: var
7309
7310integerdatc=c2i(voldat)
7311
7312end function integerdatc
7313
7314
7315! to real
7316elemental real function realdatd(voldat,var)
7317doubleprecision,intent(in) :: voldat
7318type(vol7d_var),intent(in) :: var
7319
7321 realdatd=real(voldat)
7322else
7323 realdatd=rmiss
7324end if
7325
7326end function realdatd
7327
7328
7329elemental real function realdatr(voldat,var)
7330real,intent(in) :: voldat
7331type(vol7d_var),intent(in) :: var
7332
7333realdatr=voldat
7334
7335end function realdatr
7336
7337
7338elemental real function realdati(voldat,var)
7339integer,intent(in) :: voldat
7340type(vol7d_var),intent(in) :: var
7341
7344 realdati=float(voldat)/10.**var%scalefactor
7345 else
7346 realdati=float(voldat)
7347 endif
7348else
7349 realdati=rmiss
7350end if
7351
7352end function realdati
7353
7354
7355elemental real function realdatb(voldat,var)
7356integer(kind=int_b),intent(in) :: voldat
7357type(vol7d_var),intent(in) :: var
7358
7361 realdatb=float(voldat)/10**var%scalefactor
7362 else
7363 realdatb=float(voldat)
7364 endif
7365else
7366 realdatb=rmiss
7367end if
7368
7369end function realdatb
7370
7371
7372elemental real function realdatc(voldat,var)
7373CHARACTER(len=vol7d_cdatalen),intent(in) :: voldat
7374type(vol7d_var),intent(in) :: var
7375
7376realdatc=c2r(voldat)
7378 realdatc=realdatc/10.**var%scalefactor
7379end if
7380
7381end function realdatc
7382
7383
7384!> Return an ana volume of a requested variable as real data.
7385!! It returns a 2-d array of the proper shape (ana x network) for the
7386!! ana variable requested, converted to real type. If the conversion
7387!! fails or if the variable is not contained in the ana volume,
7388!! missing data are returned.
7389FUNCTION realanavol(this, var) RESULT(vol)
7390TYPE(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
7391TYPE(vol7d_var),INTENT(in) :: var !< the ana variable to be returned
7392REAL :: vol(SIZE(this%ana),size(this%network))
7393
7394CHARACTER(len=1) :: dtype
7395INTEGER :: indvar
7396
7397dtype = cmiss
7398indvar = index(this%anavar, var, type=dtype)
7399
7400IF (indvar > 0) THEN
7401 SELECT CASE (dtype)
7402 CASE("d")
7403 vol = realdat(this%volanad(:,indvar,:), var)
7404 CASE("r")
7405 vol = this%volanar(:,indvar,:)
7406 CASE("i")
7407 vol = realdat(this%volanai(:,indvar,:), var)
7408 CASE("b")
7409 vol = realdat(this%volanab(:,indvar,:), var)
7410 CASE("c")
7411 vol = realdat(this%volanac(:,indvar,:), var)
7412 CASE default
7413 vol = rmiss
7414 END SELECT
7415ELSE
7416 vol = rmiss
7417ENDIF
7418
7419END FUNCTION realanavol
7420
7421
7422!> Return an ana volume of a requested variable as integer data.
7423!! It returns a 2-d array of the proper shape (ana x network) for the
7424!! ana variable requested, converted to integer type. If the conversion
7425!! fails or if the variable is not contained in the ana volume,
7426!! missing data are returned.
7427FUNCTION integeranavol(this, var) RESULT(vol)
7428TYPE(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
7429TYPE(vol7d_var),INTENT(in) :: var !< the ana variable to be returned
7430INTEGER :: vol(SIZE(this%ana),size(this%network))
7431
7432CHARACTER(len=1) :: dtype
7433INTEGER :: indvar
7434
7435dtype = cmiss
7436indvar = index(this%anavar, var, type=dtype)
7437
7438IF (indvar > 0) THEN
7439 SELECT CASE (dtype)
7440 CASE("d")
7441 vol = integerdat(this%volanad(:,indvar,:), var)
7442 CASE("r")
7443 vol = integerdat(this%volanar(:,indvar,:), var)
7444 CASE("i")
7445 vol = this%volanai(:,indvar,:)
7446 CASE("b")
7447 vol = integerdat(this%volanab(:,indvar,:), var)
7448 CASE("c")
7449 vol = integerdat(this%volanac(:,indvar,:), var)
7450 CASE default
7451 vol = imiss
7452 END SELECT
7453ELSE
7454 vol = imiss
7455ENDIF
7456
7457END FUNCTION integeranavol
7458
7459
7460!> Move data for all variables from one coordinate in the character volume to other.
7461!! Only not missing data will be copyed and all attributes will be moved together.
7462!! Usefull to colapse data spread in more indices (level or time or ....).
7463!! After the move is possible to set to missing some descriptor and make a copy with miss=.true.
7464!! to obtain a new vol7d with less data shape.
7465subroutine move_datac (v7d,&
7466 indana,indtime,indlevel,indtimerange,indnetwork,&
7467 indananew,indtimenew,indlevelnew,indtimerangenew,indnetworknew)
7468
7469TYPE(vol7d),intent(inout) :: v7d !< data in form of character in this object will be moved
7470
7471integer,intent(in) :: indana,indtime,indlevel,indtimerange,indnetwork !< source coordinate of the data
7472integer,intent(in) :: indananew,indtimenew,indlevelnew,indtimerangenew,indnetworknew !< destination coordinate of data
7473integer :: inddativar,inddativarattr
7474
7475
7476do inddativar=1,size(v7d%dativar%c)
7477
7479 .not. c_e(v7d%voldatic(indananew,indtimenew,indlevelnew,indtimerangenew,inddativar,indnetworknew))&
7480 ) then
7481
7482 ! dati
7483 v7d%voldatic &
7484 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativar,indnetworknew) = &
7485 v7d%voldatic &
7486 (indana,indtime,indlevel,indtimerange,inddativar,indnetwork)
7487
7488
7489 ! attributi
7490 if (associated (v7d%dativarattr%i)) then
7491 inddativarattr = index(v7d%dativarattr%i,v7d%dativar%c(inddativar))
7492 if (inddativarattr > 0 ) then
7493 v7d%voldatiattri &
7494 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
7495 v7d%voldatiattri &
7496 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
7497 end if
7498 end if
7499
7500 if (associated (v7d%dativarattr%r)) then
7501 inddativarattr = index(v7d%dativarattr%r,v7d%dativar%c(inddativar))
7502 if (inddativarattr > 0 ) then
7503 v7d%voldatiattrr &
7504 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
7505 v7d%voldatiattrr &
7506 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
7507 end if
7508 end if
7509
7510 if (associated (v7d%dativarattr%d)) then
7511 inddativarattr = index(v7d%dativarattr%d,v7d%dativar%c(inddativar))
7512 if (inddativarattr > 0 ) then
7513 v7d%voldatiattrd &
7514 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
7515 v7d%voldatiattrd &
7516 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
7517 end if
7518 end if
7519
7520 if (associated (v7d%dativarattr%b)) then
7521 inddativarattr = index(v7d%dativarattr%b,v7d%dativar%c(inddativar))
7522 if (inddativarattr > 0 ) then
7523 v7d%voldatiattrb &
7524 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
7525 v7d%voldatiattrb &
7526 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
7527 end if
7528 end if
7529
7530 if (associated (v7d%dativarattr%c)) then
7531 inddativarattr = index(v7d%dativarattr%c,v7d%dativar%c(inddativar))
7532 if (inddativarattr > 0 ) then
7533 v7d%voldatiattrc &
7534 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
7535 v7d%voldatiattrc &
7536 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
7537 end if
7538 end if
7539
7540 end if
7541
7542end do
7543
7544end subroutine move_datac
7545
7546!> Move data for all variables from one coordinate in the real volume to other.
7547!! Only not missing data will be copyed and all attributes will be moved together.
7548!! Usefull to colapse data spread in more indices (level or time or ....).
7549!! After the move is possible to set to missing some descriptor and make a copy with miss=.true.
7550!! to obtain a new vol7d with less data shape.
7551subroutine move_datar (v7d,&
7552 indana,indtime,indlevel,indtimerange,indnetwork,&
7553 indananew,indtimenew,indlevelnew,indtimerangenew,indnetworknew)
7554
7555TYPE(vol7d),intent(inout) :: v7d !< data in form of character in this object will be moved
7556
7557integer,intent(in) :: indana,indtime,indlevel,indtimerange,indnetwork !< source coordinate of the data
7558integer,intent(in) :: indananew,indtimenew,indlevelnew,indtimerangenew,indnetworknew !< destination coordinate of data
7559integer :: inddativar,inddativarattr
7560
7561
7562do inddativar=1,size(v7d%dativar%r)
7563
7565 .not. c_e(v7d%voldatir(indananew,indtimenew,indlevelnew,indtimerangenew,inddativar,indnetworknew))&
7566 ) then
7567
7568 ! dati
7569 v7d%voldatir &
7570 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativar,indnetworknew) = &
7571 v7d%voldatir &
7572 (indana,indtime,indlevel,indtimerange,inddativar,indnetwork)
7573
7574
7575 ! attributi
7576 if (associated (v7d%dativarattr%i)) then
7577 inddativarattr = index(v7d%dativarattr%i,v7d%dativar%r(inddativar))
7578 if (inddativarattr > 0 ) then
7579 v7d%voldatiattri &
7580 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
7581 v7d%voldatiattri &
7582 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
7583 end if
7584 end if
7585
7586 if (associated (v7d%dativarattr%r)) then
7587 inddativarattr = index(v7d%dativarattr%r,v7d%dativar%r(inddativar))
7588 if (inddativarattr > 0 ) then
7589 v7d%voldatiattrr &
7590 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
7591 v7d%voldatiattrr &
7592 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
7593 end if
7594 end if
7595
7596 if (associated (v7d%dativarattr%d)) then
7597 inddativarattr = index(v7d%dativarattr%d,v7d%dativar%r(inddativar))
7598 if (inddativarattr > 0 ) then
7599 v7d%voldatiattrd &
7600 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
7601 v7d%voldatiattrd &
7602 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
7603 end if
7604 end if
7605
7606 if (associated (v7d%dativarattr%b)) then
7607 inddativarattr = index(v7d%dativarattr%b,v7d%dativar%r(inddativar))
7608 if (inddativarattr > 0 ) then
7609 v7d%voldatiattrb &
7610 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
7611 v7d%voldatiattrb &
7612 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
7613 end if
7614 end if
7615
7616 if (associated (v7d%dativarattr%c)) then
7617 inddativarattr = index(v7d%dativarattr%c,v7d%dativar%r(inddativar))
7618 if (inddativarattr > 0 ) then
7619 v7d%voldatiattrc &
7620 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
7621 v7d%voldatiattrc &
7622 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
7623 end if
7624 end if
7625
7626 end if
7627
7628end do
7629
7630end subroutine move_datar
7631
7632
7633!> Reduce some dimensions (level and timerage) for semplification (rounding).
7634!! You can use this for simplify and use variables in computation like alchimia
7635!! where fields have to be on the same coordinate
7636!! It return real or character data only: if input is charcter data only it return character otherwise il return
7637!! all the data converted to real.
7638!! examples:
7639!! means in time for short periods and istantaneous values
7640!! 2 meter and surface levels
7641!! If there are data on more then one almost equal levels or timeranges, the first var present (at least one point)
7642!! will be taken (order is by icreasing var index).
7643!! You can use predefined values for classic semplification
7644!! almost_equal_levels and almost_equal_timeranges
7645!! The level or timerange in output will be defined by the first element of level and timerange list
7646subroutine v7d_rounding(v7din,v7dout,level,timerange,nostatproc)
7647type(vol7d),intent(inout) :: v7din !< input volume
7648type(vol7d),intent(out) :: v7dout !> output volume
7649type(vol7d_level),intent(in),optional :: level(:) !< almost equal level list
7650type(vol7d_timerange),intent(in),optional :: timerange(:) !< almost equal timerange list
7651!logical,intent(in),optional :: merge !< if there are data on more then one almost equal levels or timeranges
7652!! will be merged POINT BY POINT with priority for the fird data found ordered by icreasing var index
7653logical,intent(in),optional :: nostatproc !< do not take in account statistical processing code in timerange and P2
7654
7655integer :: nana,nlevel,ntime,ntimerange,nnetwork,nbin
7656integer :: iana,ilevel,itimerange,indl,indt,itime,inetwork
7657type(vol7d_level) :: roundlevel(size(v7din%level))
7658type(vol7d_timerange) :: roundtimerange(size(v7din%timerange))
7659type(vol7d) :: v7d_tmp
7660
7661
7662nbin=0
7663
7664if (associated(v7din%dativar%r)) nbin = nbin + size(v7din%dativar%r)
7665if (associated(v7din%dativar%i)) nbin = nbin + size(v7din%dativar%i)
7666if (associated(v7din%dativar%d)) nbin = nbin + size(v7din%dativar%d)
7667if (associated(v7din%dativar%b)) nbin = nbin + size(v7din%dativar%b)
7668
7670
7671roundlevel=v7din%level
7672
7673if (present(level))then
7674 do ilevel = 1, size(v7din%level)
7675 if ((any(v7din%level(ilevel) .almosteq. level))) then
7676 roundlevel(ilevel)=level(1)
7677 end if
7678 end do
7679end if
7680
7681roundtimerange=v7din%timerange
7682
7683if (present(timerange))then
7684 do itimerange = 1, size(v7din%timerange)
7685 if ((any(v7din%timerange(itimerange) .almosteq. timerange))) then
7686 roundtimerange(itimerange)=timerange(1)
7687 end if
7688 end do
7689end if
7690
7691!set istantaneous values everywere
7692!preserve p1 for forecast time
7693if (optio_log(nostatproc)) then
7694 roundtimerange(:)%timerange=254
7695 roundtimerange(:)%p2=0
7696end if
7697
7698
7699nana=size(v7din%ana)
7700nlevel=count_distinct(roundlevel,back=.true.)
7701ntime=size(v7din%time)
7702ntimerange=count_distinct(roundtimerange,back=.true.)
7703nnetwork=size(v7din%network)
7704
7706
7707if (nbin == 0) then
7709else
7710 call vol7d_convr(v7din,v7d_tmp)
7711end if
7712
7713v7d_tmp%level=roundlevel
7714v7d_tmp%timerange=roundtimerange
7715
7716do ilevel=1, size(v7d_tmp%level)
7717 indl=index(v7d_tmp%level,roundlevel(ilevel))
7718 do itimerange=1,size(v7d_tmp%timerange)
7719 indt=index(v7d_tmp%timerange,roundtimerange(itimerange))
7720
7721 if (indl /= ilevel .or. indt /= itimerange) then
7722
7723 do iana=1, nana
7724 do itime=1,ntime
7725 do inetwork=1,nnetwork
7726
7727 if (nbin > 0) then
7728 call move_datar (v7d_tmp,&
7729 iana,itime,ilevel,itimerange,inetwork,&
7730 iana,itime,indl,indt,inetwork)
7731 else
7732 call move_datac (v7d_tmp,&
7733 iana,itime,ilevel,itimerange,inetwork,&
7734 iana,itime,indl,indt,inetwork)
7735 end if
7736
7737 end do
7738 end do
7739 end do
7740
7741 end if
7742
7743 end do
7744end do
7745
7746! set to missing level and time > nlevel
7747do ilevel=nlevel+1,size(v7d_tmp%level)
7749end do
7750
7751do itimerange=ntimerange+1,size(v7d_tmp%timerange)
7753end do
7754
7755!copy with remove
7758
7759!call display(v7dout)
7760
7761end subroutine v7d_rounding
7762
7763
7765
7766!>\example esempio_qc_convert.f90
7767!!\brief Programma esempio semplice per la scrittura su file di un volume vol7d
7768!!
7769!!Programma che scrive su file un volume vol7d letto da una serie di file ASCII.
7770!!Questo programma scrive i dati del clima che poi verranno letti da modqccli
7771
7772
7773!>\example esempio_v7ddballe_move_and_collapse.f90
7774!!\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. Definition char_utilities.F90:278 Legge un oggetto datetime/timedelta o un vettore di oggetti datetime/timedelta da un file FORMATTED o... Definition datetime_class.F90:478 Scrive un oggetto datetime/timedelta o un vettore di oggetti datetime/timedelta su un file FORMATTED ... Definition datetime_class.F90:485 Generic subroutine for checking OPTIONAL parameters. Definition optional_values.f90:36 Check for problems return 0 if all check passed print diagnostics with log4f. Definition vol7d_class.F90:445 Reduce some dimensions (level and timerage) for semplification (rounding). Definition vol7d_class.F90:462 This module defines usefull general purpose function and subroutine. Definition array_utilities.F90:212 Definition of constants to be used for declaring variables of a desired type. Definition kinds.F90:245 Module for quickly interpreting the OPTIONAL parameters passed to a subprogram. Definition optional_values.f90:28 Classe per la gestione dell'anagrafica di stazioni meteo e affini. Definition vol7d_ana_class.F90:212 Classe per la gestione di un volume completo di dati osservati. Definition vol7d_class.F90:273 Classe per la gestione dei livelli verticali in osservazioni meteo e affini. Definition vol7d_level_class.F90:213 Classe per la gestione delle reti di stazioni per osservazioni meteo e affini. Definition vol7d_network_class.F90:214 Classe per la gestione degli intervalli temporali di osservazioni meteo e affini. Definition vol7d_timerange_class.F90:215 Classe per gestire un vettore di oggetti di tipo vol7d_var_class::vol7d_var. Definition vol7d_varvect_class.f90:22 Definisce un oggetto contenente i volumi anagrafica e dati e tutti i descrittori delle loro dimension... Definition vol7d_class.F90:312 |