libsim Versione 8.0.0

◆ move_datac()

subroutine move_datac ( type(vol7d), intent(inout) v7d,
integer, intent(in) indana,
integer, intent(in) indtime,
integer, intent(in) indlevel,
integer, intent(in) indtimerange,
integer, intent(in) indnetwork,
integer, intent(in) indananew,
integer, intent(in) indtimenew,
integer, intent(in) indlevelnew,
integer, intent(in) indtimerangenew,
integer, intent(in) indnetworknew )

Move data for all variables from one coordinate in the character volume to other.

Only not missing data will be copyed and all attributes will be moved together. Usefull to colapse data spread in more indices (level or time or ....). After the move is possible to set to missing some descriptor and make a copy with miss=.true. to obtain a new vol7d with less data shape.

Parametri
[in,out]v7ddata in form of character in this object will be moved
[in]indnetworksource coordinate of the data
[in]indnetworknewdestination coordinate of data

Definizione alla linea 9187 del file vol7d_class.F90.

9190! Copyright (C) 2010 ARPA-SIM <urpsim@smr.arpa.emr.it>
9191! authors:
9192! Davide Cesari <dcesari@arpa.emr.it>
9193! Paolo Patruno <ppatruno@arpa.emr.it>
9194
9195! This program is free software; you can redistribute it and/or
9196! modify it under the terms of the GNU General Public License as
9197! published by the Free Software Foundation; either version 2 of
9198! the License, or (at your option) any later version.
9199
9200! This program is distributed in the hope that it will be useful,
9201! but WITHOUT ANY WARRANTY; without even the implied warranty of
9202! MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
9203! GNU General Public License for more details.
9204
9205! You should have received a copy of the GNU General Public License
9206! along with this program. If not, see <http://www.gnu.org/licenses/>.
9207#include "config.h"
9208
9209!> \defgroup vol7d Libsim package, vol7d library.
9210!! The libsim vol7d library contains classes for managing pointwise
9211!! data, tipically weather observations, and for their import from a
9212!! Db-All.e database or from a WMO BUFR file. In order to compile and
9213!! link programs using this library, you have to insert the required
9214!! \c USE statements in the program units involved, specify the
9215!! location of module files when compiling (tipically \c
9216!! -I/usr/lib/gfortran/modules or \c -I/usr/lib64/gfortran/modules or
9217!! \c -I/usr/include) and indicate the library name \c -lsim_vol7d
9218!! when linking, assuming that the library has been installed in a
9219!! default location.
9220
9221!> Classe per la gestione di un volume completo di dati osservati.
9222!! Questo modulo definisce gli oggetti e i metodi per gestire
9223!! volumi di dati meteorologici sparsi.
9224!! I volumi definiti sono principalmente di 4 categorie:
9225!! - volumi di anagrafica (vol7d::volanar & c.), hanno 3 dimensioni:
9226!! - anagrafica
9227!! - variabile di anagrafica
9228!! - rete
9229!! - volumi di attributi di anagrafica (vol7d::volanaattrr & c.), hanno 4 dimensioni:
9230!! - anagrafica
9231!! - variabile di anagrafica
9232!! - rete
9233!! - variabile di attributi delle variabili di anagrafica
9234!! - volumi di dati (vol7d::voldatir & c.), hanno 6 dimensioni:
9235!! - anagrafica
9236!! - tempo
9237!! - livello verticale
9238!! - intervallo temporale (timerange)
9239!! - variabile di dati
9240!! - rete
9241!! - volumi di attributi di dati (vol7d::voldatiattrr & c.), hanno 7 dimensioni:
9242!! - anagrafica
9243!! - tempo
9244!! - livello verticale
9245!! - intervallo temporale (timerange)
9246!! - variabile di dati
9247!! - rete
9248!! - variabile di attributi delle variabili di dati
9249!!
9250!! Tutte le variabili sono inoltre disponibil1 in 5 tipi diversi:
9251!! - reale (abbreviato r)
9252!! - doppia precisione (abbreviato d)
9253!! - intero (abbreviato i)
9254!! - byte (abbreviato b)
9255!! - carattere (abbreviato c)
9256!!
9257!! Per ognuna delle dimensioni possibili, incluse le variabili e gli
9258!! attributi con i loro diversi tipi,
9259!! è definito un cosiddetto "vettore di descrittori", con un
9260!! numero di elementi pari all'estensione della dimensione stessa,
9261!! che contiene le informazioni necessarie a descrivere
9262!! gli elementi di quella dimensione.
9263!! In realtà l'utente non dovrà generalmente occuparsi di costruire
9264!! un oggetto vol7d con le proprie mani ma utilizzerà nella maggior parte
9265!! dei casi i metodi di importazione preconfezionati che importano dati da
9266!! DB-All.e (vol7d_dballe_class) o dal DB Oracle del SIM (vol7d_oraclesim_class).
9267!!
9268!!
9269!! Il programma esempio_v7d.f90 contiene un esempio elementare di uso
9270!! della classe vol7d:
9271!! \include esempio_v7d.f90
9272!!
9273!! \ingroup vol7d
9274MODULE vol7d_class
9275USE kinds
9279USE log4fortran
9280USE err_handling
9281USE io_units
9288IMPLICIT NONE
9289
9290
9291INTEGER, PARAMETER :: vol7d_maxdim_a = 3, vol7d_maxdim_aa = 4, &
9292 vol7d_maxdim_d = 6, vol7d_maxdim_ad = 7
9293
9294INTEGER, PARAMETER :: vol7d_ana_a=1 !< indice della dimensione "anagrafica" nei volumi di anagrafica, da usare nei metodi vol7d_get_volana*
9295INTEGER, PARAMETER :: vol7d_var_a=2 !< indice della dimensione "variabile" nei volumi di anagrafica, da usare nei metodi vol7d_get_volana*
9296INTEGER, PARAMETER :: vol7d_network_a=3 !< indice della dimensione "rete" nei volumi di anagrafica, da usare nei metodi vol7d_get_volana*
9297INTEGER, PARAMETER :: vol7d_attr_a=4 !< indice della dimensione "attributo" nei volumi di anagrafica, da usare nei metodi vol7d_get_volana*
9298INTEGER, PARAMETER :: vol7d_ana_d=1 !< indice della dimensione "anagrafica" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
9299INTEGER, PARAMETER :: vol7d_time_d=2 !< indice della dimensione "tempo" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
9300INTEGER, PARAMETER :: vol7d_level_d=3 !< indice della dimensione "livello verticale" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
9301INTEGER, PARAMETER :: vol7d_timerange_d=4 !< indice della dimensione "intervallo temporale" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
9302INTEGER, PARAMETER :: vol7d_var_d=5 !< indice della dimensione "variabile" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
9303INTEGER, PARAMETER :: vol7d_network_d=6 !< indice della dimensione "rete" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
9304INTEGER, PARAMETER :: vol7d_attr_d=7 !< indice della dimensione "attributo" nei volumi di dati, da usare nei metodi vol7d_get_voldati*
9305INTEGER, PARAMETER :: vol7d_cdatalen=32
9306
9307TYPE vol7d_varmap
9308 INTEGER :: r, d, i, b, c
9309END TYPE vol7d_varmap
9310
9311!> Definisce un oggetto contenente i volumi anagrafica e dati e tutti
9312!! i descrittori delle loro dimensioni.
9313TYPE vol7d
9314!> vettore descrittore della dimensione anagrafica
9315 TYPE(vol7d_ana),POINTER :: ana(:)
9316!> vettore descrittore della dimensione tempo
9317 TYPE(datetime),POINTER :: time(:)
9318!> vettore descrittore della dimensione livello verticale
9319 TYPE(vol7d_level),POINTER :: level(:)
9320!> vettore descrittore della dimensione intervallo temporale (timerange)
9321 TYPE(vol7d_timerange),POINTER :: timerange(:)
9322!> vettore descrittore della dimensione rete
9323 TYPE(vol7d_network),POINTER :: network(:)
9324!> vettore descrittore della dimensione variabile di anagrafica
9325 TYPE(vol7d_varvect) :: anavar
9326!> vettore descrittore della dimensione attributo delle variabili di anagrafica
9327 TYPE(vol7d_varvect) :: anaattr
9328!> vettore descrittore della dimensione variabile di anagrafica che ha tali attributi
9329 TYPE(vol7d_varvect) :: anavarattr
9330!> vettore descrittore della dimensione variabile di dati
9331 TYPE(vol7d_varvect) :: dativar
9332!> vettore descrittore della dimensione attributo delle variabili di dati
9333 TYPE(vol7d_varvect) :: datiattr
9334!> vettore descrittore della dimensione variabile di dati che ha tali attributi
9335 TYPE(vol7d_varvect) :: dativarattr
9336
9337!> volume di anagrafica a valori reali
9338 REAL,POINTER :: volanar(:,:,:)
9339!> volume di anagrafica a valori a doppia precisione
9340 DOUBLE PRECISION,POINTER :: volanad(:,:,:)
9341!> volume di anagrafica a valori interi
9342 INTEGER,POINTER :: volanai(:,:,:)
9343!> volume di anagrafica a valori byte
9344 INTEGER(kind=int_b),POINTER :: volanab(:,:,:)
9345!> volume di anagrafica a valori carattere
9346 CHARACTER(len=vol7d_cdatalen),POINTER :: volanac(:,:,:)
9347
9348!> volume di attributi di anagrafica a valori reali
9349 REAL,POINTER :: volanaattrr(:,:,:,:)
9350!> volume di attributi di anagrafica a valori a doppia precisione
9351 DOUBLE PRECISION,POINTER :: volanaattrd(:,:,:,:)
9352!> volume di attributi di anagrafica a valori interi
9353 INTEGER,POINTER :: volanaattri(:,:,:,:)
9354!> volume di attributi di anagrafica a valori byte
9355 INTEGER(kind=int_b),POINTER :: volanaattrb(:,:,:,:)
9356!> volume di attributi di anagrafica a valori carattere
9357 CHARACTER(len=vol7d_cdatalen),POINTER :: volanaattrc(:,:,:,:)
9358
9359!> volume di dati a valori reali
9360 REAL,POINTER :: voldatir(:,:,:,:,:,:) ! sono i dati
9361!> volume di dati a valori a doppia precisione
9362 DOUBLE PRECISION,POINTER :: voldatid(:,:,:,:,:,:)
9363!> volume di dati a valori interi
9364 INTEGER,POINTER :: voldatii(:,:,:,:,:,:)
9365!> volume di dati a valori byte
9366 INTEGER(kind=int_b),POINTER :: voldatib(:,:,:,:,:,:)
9367!> volume di dati a valori carattere
9368 CHARACTER(len=vol7d_cdatalen),POINTER :: voldatic(:,:,:,:,:,:)
9369
9370!> volume di attributi di dati a valori reali
9371 REAL,POINTER :: voldatiattrr(:,:,:,:,:,:,:)
9372!> volume di attributi di dati a valori a doppia precisione
9373 DOUBLE PRECISION,POINTER :: voldatiattrd(:,:,:,:,:,:,:)
9374!> volume di attributi di dati a valori interi
9375 INTEGER,POINTER :: voldatiattri(:,:,:,:,:,:,:)
9376!> volume di attributi di dati a valori byte
9377 INTEGER(kind=int_b),POINTER :: voldatiattrb(:,:,:,:,:,:,:)
9378!> volume di attributi di dati a valori carattere
9379 CHARACTER(len=vol7d_cdatalen),POINTER :: voldatiattrc(:,:,:,:,:,:,:)
9380
9381!> time definition; 0=time is reference time, 1=time is validity time
9382 integer :: time_definition
9383
9384END TYPE vol7d
9385
9386!> Costruttore per la classe vol7d.
9387!! Deve essere richiamato
9388!! per tutti gli oggetti di questo tipo definiti in un programma.
9389INTERFACE init
9390 MODULE PROCEDURE vol7d_init
9391END INTERFACE
9392
9393!> Distruttore per la classe vol7d.
9394INTERFACE delete
9395 MODULE PROCEDURE vol7d_delete
9396END INTERFACE
9397
9398!> Scrittura su file.
9399INTERFACE export
9400 MODULE PROCEDURE vol7d_write_on_file
9401END INTERFACE
9402
9403!> Lettura da file.
9404INTERFACE import
9405 MODULE PROCEDURE vol7d_read_from_file
9406END INTERFACE
9407
9408!>Print object
9409INTERFACE display
9410 MODULE PROCEDURE vol7d_display, dat_display, dat_vect_display
9411END INTERFACE
9412
9413!>Represent data in a pretty string
9414INTERFACE to_char
9415 MODULE PROCEDURE to_char_dat
9416END INTERFACE
9417
9418!>doubleprecision data conversion
9419INTERFACE doubledat
9420 MODULE PROCEDURE doubledatd,doubledatr,doubledati,doubledatb,doubledatc
9421END INTERFACE
9422
9423!>real data conversion
9424INTERFACE realdat
9425 MODULE PROCEDURE realdatd,realdatr,realdati,realdatb,realdatc
9426END INTERFACE
9427
9428!>integer data conversion
9429INTERFACE integerdat
9430 MODULE PROCEDURE integerdatd,integerdatr,integerdati,integerdatb,integerdatc
9431END INTERFACE
9432
9433!>copy object
9434INTERFACE copy
9435 MODULE PROCEDURE vol7d_copy
9436END INTERFACE
9437
9438!> Test for a missing volume
9439INTERFACE c_e
9440 MODULE PROCEDURE vol7d_c_e
9441END INTERFACE
9442
9443!> Check for problems
9444!! return 0 if all check passed
9445!! print diagnostics with log4f
9446INTERFACE check
9447 MODULE PROCEDURE vol7d_check
9448END INTERFACE
9449
9450!> Reduce some dimensions (level and timerage) for semplification (rounding).
9451!! You can use this for simplify and use variables in computation like alchimia
9452!! where fields have to be on the same coordinate
9453!! It return real or character data only: if input is charcter data only it return character otherwise il return
9454!! all the data converted to real.
9455!! examples:
9456!! means in time for short periods and istantaneous values
9457!! 2 meter and surface levels
9458!! If there are data on more then one almost equal levels or timeranges, the first var present (at least one point)
9459!! will be taken (order is by icreasing var index).
9460!! You can use predefined values for classic semplification
9461!! almost_equal_levels and almost_equal_timeranges
9462!! The level or timerange in output will be defined by the first element of level and timerange list
9463INTERFACE rounding
9464 MODULE PROCEDURE v7d_rounding
9465END INTERFACE
9466
9467!!$INTERFACE get_volana
9468!!$ MODULE PROCEDURE vol7d_get_volanar, vol7d_get_volanad, vol7d_get_volanai, &
9469!!$ vol7d_get_volanab, vol7d_get_volanac
9470!!$END INTERFACE
9471!!$
9472!!$INTERFACE get_voldati
9473!!$ MODULE PROCEDURE vol7d_get_voldatir, vol7d_get_voldatid, vol7d_get_voldatii, &
9474!!$ vol7d_get_voldatib, vol7d_get_voldatic
9475!!$END INTERFACE
9476!!$
9477!!$INTERFACE get_volanaattr
9478!!$ MODULE PROCEDURE vol7d_get_volanaattrr, vol7d_get_volanaattrd, &
9479!!$ vol7d_get_volanaattri, vol7d_get_volanaattrb, vol7d_get_volanaattrc
9480!!$END INTERFACE
9481!!$
9482!!$INTERFACE get_voldatiattr
9483!!$ MODULE PROCEDURE vol7d_get_voldatiattrr, vol7d_get_voldatiattrd, &
9484!!$ vol7d_get_voldatiattri, vol7d_get_voldatiattrb, vol7d_get_voldatiattrc
9485!!$END INTERFACE
9486
9487PRIVATE vol7d_get_volr, vol7d_get_vold, vol7d_get_voli, vol7d_get_volb, &
9488 vol7d_get_volc, &
9489 volptr1dr, volptr2dr, volptr3dr, volptr4dr, volptr5dr, volptr6dr, volptr7dr, &
9490 volptr1dd, volptr2dd, volptr3dd, volptr4dd, volptr5dd, volptr6dd, volptr7dd, &
9491 volptr1di, volptr2di, volptr3di, volptr4di, volptr5di, volptr6di, volptr7di, &
9492 volptr1db, volptr2db, volptr3db, volptr4db, volptr5db, volptr6db, volptr7db, &
9493 volptr1dc, volptr2dc, volptr3dc, volptr4dc, volptr5dc, volptr6dc, volptr7dc, &
9494 vol7d_nullifyr, vol7d_nullifyd, vol7d_nullifyi, vol7d_nullifyb, vol7d_nullifyc, &
9495 vol7d_init, vol7d_delete, vol7d_write_on_file, vol7d_read_from_file, &
9496 vol7d_check_alloc_ana, vol7d_force_alloc_ana, &
9497 vol7d_check_alloc_dati, vol7d_force_alloc_dati, vol7d_force_alloc, &
9498 vol7d_display, dat_display, dat_vect_display, &
9499 to_char_dat, vol7d_check
9500
9501PRIVATE doubledatd,doubledatr,doubledati,doubledatb,doubledatc
9502
9503PRIVATE vol7d_c_e
9504
9505CONTAINS
9506
9507
9508!> Inizializza un oggetto di tipo vol7d.
9509!! Non riceve alcun parametro tranne l'oggetto stesso. Attenzione, è necessario
9510!! comunque chiamare sempre il costruttore per evitare di avere dei puntatori in
9511!! uno stato indefinito.
9512SUBROUTINE vol7d_init(this,time_definition)
9513TYPE(vol7d),intent(out) :: this !< oggetto da inizializzare
9514INTEGER,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)
9515
9516CALL init(this%anavar)
9517CALL init(this%anaattr)
9518CALL init(this%anavarattr)
9519CALL init(this%dativar)
9520CALL init(this%datiattr)
9521CALL init(this%dativarattr)
9522
9523NULLIFY(this%ana, this%time, this%level, this%timerange, this%network)
9524
9525NULLIFY(this%volanar, this%volanaattrr, this%voldatir, this%voldatiattrr)
9526NULLIFY(this%volanad, this%volanaattrd, this%voldatid, this%voldatiattrd)
9527NULLIFY(this%volanai, this%volanaattri, this%voldatii, this%voldatiattri)
9528NULLIFY(this%volanab, this%volanaattrb, this%voldatib, this%voldatiattrb)
9529NULLIFY(this%volanac, this%volanaattrc, this%voldatic, this%voldatiattrc)
9530
9531if(present(time_definition)) then
9532 this%time_definition=time_definition
9533else
9534 this%time_definition=1 !default to validity time
9535end if
9536
9537END SUBROUTINE vol7d_init
9538
9539
9540!> Distrugge l'oggetto in maniera pulita, liberando l'eventuale memoria
9541!! dinamicamente allocata. Permette di distruggere la sola parte di dati
9542!! mantenendo l'anagrafica.
9543ELEMENTAL SUBROUTINE vol7d_delete(this, dataonly)
9544TYPE(vol7d),intent(inout) :: this !< oggetto da distruggere
9545LOGICAL, INTENT(in), OPTIONAL :: dataonly !< dealloca solo i dati, tenendo l'anagrafica, (default \c .FALSE.)
9546
9547
9548IF (.NOT. optio_log(dataonly)) THEN
9549 IF (ASSOCIATED(this%volanar)) DEALLOCATE(this%volanar)
9550 IF (ASSOCIATED(this%volanad)) DEALLOCATE(this%volanad)
9551 IF (ASSOCIATED(this%volanai)) DEALLOCATE(this%volanai)
9552 IF (ASSOCIATED(this%volanab)) DEALLOCATE(this%volanab)
9553 IF (ASSOCIATED(this%volanac)) DEALLOCATE(this%volanac)
9554 IF (ASSOCIATED(this%volanaattrr)) DEALLOCATE(this%volanaattrr)
9555 IF (ASSOCIATED(this%volanaattrd)) DEALLOCATE(this%volanaattrd)
9556 IF (ASSOCIATED(this%volanaattri)) DEALLOCATE(this%volanaattri)
9557 IF (ASSOCIATED(this%volanaattrb)) DEALLOCATE(this%volanaattrb)
9558 IF (ASSOCIATED(this%volanaattrc)) DEALLOCATE(this%volanaattrc)
9559ENDIF
9560IF (ASSOCIATED(this%voldatir)) DEALLOCATE(this%voldatir)
9561IF (ASSOCIATED(this%voldatid)) DEALLOCATE(this%voldatid)
9562IF (ASSOCIATED(this%voldatii)) DEALLOCATE(this%voldatii)
9563IF (ASSOCIATED(this%voldatib)) DEALLOCATE(this%voldatib)
9564IF (ASSOCIATED(this%voldatic)) DEALLOCATE(this%voldatic)
9565IF (ASSOCIATED(this%voldatiattrr)) DEALLOCATE(this%voldatiattrr)
9566IF (ASSOCIATED(this%voldatiattrd)) DEALLOCATE(this%voldatiattrd)
9567IF (ASSOCIATED(this%voldatiattri)) DEALLOCATE(this%voldatiattri)
9568IF (ASSOCIATED(this%voldatiattrb)) DEALLOCATE(this%voldatiattrb)
9569IF (ASSOCIATED(this%voldatiattrc)) DEALLOCATE(this%voldatiattrc)
9570
9571IF (.NOT. optio_log(dataonly)) THEN
9572 IF (ASSOCIATED(this%ana)) DEALLOCATE(this%ana)
9573 IF (ASSOCIATED(this%network)) DEALLOCATE(this%network)
9574ENDIF
9575IF (ASSOCIATED(this%time)) DEALLOCATE(this%time)
9576IF (ASSOCIATED(this%level)) DEALLOCATE(this%level)
9577IF (ASSOCIATED(this%timerange)) DEALLOCATE(this%timerange)
9578
9579IF (.NOT. optio_log(dataonly)) THEN
9580 CALL delete(this%anavar)
9581 CALL delete(this%anaattr)
9582 CALL delete(this%anavarattr)
9583ENDIF
9584CALL delete(this%dativar)
9585CALL delete(this%datiattr)
9586CALL delete(this%dativarattr)
9587
9588END SUBROUTINE vol7d_delete
9589
9590
9591
9592integer function vol7d_check(this)
9593TYPE(vol7d),intent(in) :: this !< object to check
9594integer :: i,j,k,l,m,n
9595
9596vol7d_check=0
9597
9598if (associated(this%voldatii)) then
9599do i = 1,size(this%voldatii,1)
9600 do j = 1,size(this%voldatii,2)
9601 do k = 1,size(this%voldatii,3)
9602 do l = 1,size(this%voldatii,4)
9603 do m = 1,size(this%voldatii,5)
9604 do n = 1,size(this%voldatii,6)
9605 if (this%voldatii(i,j,k,l,m,n) /= this%voldatii(i,j,k,l,m,n) ) then
9606 CALL l4f_log(l4f_warn,"check: abnormal value at voldatii("&
9607 //t2c(i)//","//t2c(j)//","//t2c(k)//","//t2c(l)//","//t2c(m)//","//t2c(n)//",)")
9608 vol7d_check=1
9609 end if
9610 end do
9611 end do
9612 end do
9613 end do
9614 end do
9615end do
9616end if
9617
9618
9619if (associated(this%voldatir)) then
9620do i = 1,size(this%voldatir,1)
9621 do j = 1,size(this%voldatir,2)
9622 do k = 1,size(this%voldatir,3)
9623 do l = 1,size(this%voldatir,4)
9624 do m = 1,size(this%voldatir,5)
9625 do n = 1,size(this%voldatir,6)
9626 if (this%voldatir(i,j,k,l,m,n) /= this%voldatir(i,j,k,l,m,n) ) then
9627 CALL l4f_log(l4f_warn,"check: abnormal value at voldatir("&
9628 //t2c(i)//","//t2c(j)//","//t2c(k)//","//t2c(l)//","//t2c(m)//","//t2c(n)//",)")
9629 vol7d_check=2
9630 end if
9631 end do
9632 end do
9633 end do
9634 end do
9635 end do
9636end do
9637end if
9638
9639if (associated(this%voldatid)) then
9640do i = 1,size(this%voldatid,1)
9641 do j = 1,size(this%voldatid,2)
9642 do k = 1,size(this%voldatid,3)
9643 do l = 1,size(this%voldatid,4)
9644 do m = 1,size(this%voldatid,5)
9645 do n = 1,size(this%voldatid,6)
9646 if (this%voldatid(i,j,k,l,m,n) /= this%voldatid(i,j,k,l,m,n) ) then
9647 CALL l4f_log(l4f_warn,"check: abnormal value at voldatid("&
9648 //t2c(i)//","//t2c(j)//","//t2c(k)//","//t2c(l)//","//t2c(m)//","//t2c(n)//",)")
9649 vol7d_check=3
9650 end if
9651 end do
9652 end do
9653 end do
9654 end do
9655 end do
9656end do
9657end if
9658
9659if (associated(this%voldatib)) then
9660do i = 1,size(this%voldatib,1)
9661 do j = 1,size(this%voldatib,2)
9662 do k = 1,size(this%voldatib,3)
9663 do l = 1,size(this%voldatib,4)
9664 do m = 1,size(this%voldatib,5)
9665 do n = 1,size(this%voldatib,6)
9666 if (this%voldatib(i,j,k,l,m,n) /= this%voldatib(i,j,k,l,m,n) ) then
9667 CALL l4f_log(l4f_warn,"check: abnormal value at voldatib("&
9668 //t2c(i)//","//t2c(j)//","//t2c(k)//","//t2c(l)//","//t2c(m)//","//t2c(n)//",)")
9669 vol7d_check=4
9670 end if
9671 end do
9672 end do
9673 end do
9674 end do
9675 end do
9676end do
9677end if
9678
9679end function vol7d_check
9680
9681
9682
9683!TODO da completare ! aborta se i volumi sono allocati a dimensione 0
9684!> stampa a video una sintesi del contenuto
9685SUBROUTINE vol7d_display(this)
9686TYPE(vol7d),intent(in) :: this !< oggetto da visualizzare
9687integer :: i
9688
9689REAL :: rdat
9690DOUBLE PRECISION :: ddat
9691INTEGER :: idat
9692INTEGER(kind=int_b) :: bdat
9693CHARACTER(len=vol7d_cdatalen) :: cdat
9694
9695
9696print*,"<<<<<<<<<<<<<<<<<<< vol7d object >>>>>>>>>>>>>>>>>>>>"
9697if (this%time_definition == 0) then
9698 print*,"TIME DEFINITION: time is reference time"
9699else if (this%time_definition == 1) then
9700 print*,"TIME DEFINITION: time is validity time"
9701else if (this%time_definition == 2) then
9702 print*,"TIME DEFINITION: time is validity time, forecast range forced to 0"
9703else
9704 print*,"Time definition has a wrong walue:", this%time_definition
9705end if
9706
9707IF (ASSOCIATED(this%network))then
9708 print*,"---- network vector ----"
9709 print*,"elements=",size(this%network)
9710 do i=1, size(this%network)
9711 call display(this%network(i))
9712 end do
9713end IF
9714
9715IF (ASSOCIATED(this%ana))then
9716 print*,"---- ana vector ----"
9717 print*,"elements=",size(this%ana)
9718 do i=1, size(this%ana)
9719 call display(this%ana(i))
9720 end do
9721end IF
9722
9723IF (ASSOCIATED(this%time))then
9724 print*,"---- time vector ----"
9725 print*,"elements=",size(this%time)
9726 do i=1, size(this%time)
9727 call display(this%time(i))
9728 end do
9729end if
9730
9731IF (ASSOCIATED(this%level)) then
9732 print*,"---- level vector ----"
9733 print*,"elements=",size(this%level)
9734 do i =1,size(this%level)
9735 call display(this%level(i))
9736 end do
9737end if
9738
9739IF (ASSOCIATED(this%timerange))then
9740 print*,"---- timerange vector ----"
9741 print*,"elements=",size(this%timerange)
9742 do i =1,size(this%timerange)
9743 call display(this%timerange(i))
9744 end do
9745end if
9746
9747
9748print*,"---- ana vector ----"
9749print*,""
9750print*,"->>>>>>>>> anavar -"
9751call display(this%anavar)
9752print*,""
9753print*,"->>>>>>>>> anaattr -"
9754call display(this%anaattr)
9755print*,""
9756print*,"->>>>>>>>> anavarattr -"
9757call display(this%anavarattr)
9758
9759print*,"-- ana data section (first point) --"
9760
9761idat=imiss
9762rdat=rmiss
9763ddat=dmiss
9764bdat=ibmiss
9765cdat=cmiss
9766
9767!ntime = MIN(SIZE(this%time),nprint)
9768!ntimerange = MIN(SIZE(this%timerange),nprint)
9769!nlevel = MIN(SIZE(this%level),nprint)
9770!nnetwork = MIN(SIZE(this%network),nprint)
9771!nana = MIN(SIZE(this%ana),nprint)
9772
9773IF (SIZE(this%ana) > 0 .AND. SIZE(this%network) > 0) THEN
9774if (associated(this%volanai)) then
9775 do i=1,size(this%anavar%i)
9776 idat=this%volanai(1,i,1)
9777 if (associated(this%anavar%i)) call display(this%anavar%i(i),idat,rdat,ddat,bdat,cdat)
9778 end do
9779end if
9780idat=imiss
9781
9782if (associated(this%volanar)) then
9783 do i=1,size(this%anavar%r)
9784 rdat=this%volanar(1,i,1)
9785 if (associated(this%anavar%r)) call display(this%anavar%r(i),idat,rdat,ddat,bdat,cdat)
9786 end do
9787end if
9788rdat=rmiss
9789
9790if (associated(this%volanad)) then
9791 do i=1,size(this%anavar%d)
9792 ddat=this%volanad(1,i,1)
9793 if (associated(this%anavar%d)) call display(this%anavar%d(i),idat,rdat,ddat,bdat,cdat)
9794 end do
9795end if
9796ddat=dmiss
9797
9798if (associated(this%volanab)) then
9799 do i=1,size(this%anavar%b)
9800 bdat=this%volanab(1,i,1)
9801 if (associated(this%anavar%b)) call display(this%anavar%b(i),idat,rdat,ddat,bdat,cdat)
9802 end do
9803end if
9804bdat=ibmiss
9805
9806if (associated(this%volanac)) then
9807 do i=1,size(this%anavar%c)
9808 cdat=this%volanac(1,i,1)
9809 if (associated(this%anavar%c)) call display(this%anavar%c(i),idat,rdat,ddat,bdat,cdat)
9810 end do
9811end if
9812cdat=cmiss
9813ENDIF
9814
9815print*,"---- data vector ----"
9816print*,""
9817print*,"->>>>>>>>> dativar -"
9818call display(this%dativar)
9819print*,""
9820print*,"->>>>>>>>> datiattr -"
9821call display(this%datiattr)
9822print*,""
9823print*,"->>>>>>>>> dativarattr -"
9824call display(this%dativarattr)
9825
9826print*,"-- data data section (first point) --"
9827
9828idat=imiss
9829rdat=rmiss
9830ddat=dmiss
9831bdat=ibmiss
9832cdat=cmiss
9833
9834IF (SIZE(this%ana) > 0 .AND. SIZE(this%network) > 0 .AND. size(this%time) > 0 &
9835 .AND. size(this%level) > 0 .AND. size(this%timerange) > 0) THEN
9836if (associated(this%voldatii)) then
9837 do i=1,size(this%dativar%i)
9838 idat=this%voldatii(1,1,1,1,i,1)
9839 if (associated(this%dativar%i)) call display(this%dativar%i(i),idat,rdat,ddat,bdat,cdat)
9840 end do
9841end if
9842idat=imiss
9843
9844if (associated(this%voldatir)) then
9845 do i=1,size(this%dativar%r)
9846 rdat=this%voldatir(1,1,1,1,i,1)
9847 if (associated(this%dativar%r)) call display(this%dativar%r(i),idat,rdat,ddat,bdat,cdat)
9848 end do
9849end if
9850rdat=rmiss
9851
9852if (associated(this%voldatid)) then
9853 do i=1,size(this%dativar%d)
9854 ddat=this%voldatid(1,1,1,1,i,1)
9855 if (associated(this%dativar%d)) call display(this%dativar%d(i),idat,rdat,ddat,bdat,cdat)
9856 end do
9857end if
9858ddat=dmiss
9859
9860if (associated(this%voldatib)) then
9861 do i=1,size(this%dativar%b)
9862 bdat=this%voldatib(1,1,1,1,i,1)
9863 if (associated(this%dativar%b)) call display(this%dativar%b(i),idat,rdat,ddat,bdat,cdat)
9864 end do
9865end if
9866bdat=ibmiss
9867
9868if (associated(this%voldatic)) then
9869 do i=1,size(this%dativar%c)
9870 cdat=this%voldatic(1,1,1,1,i,1)
9871 if (associated(this%dativar%c)) call display(this%dativar%c(i),idat,rdat,ddat,bdat,cdat)
9872 end do
9873end if
9874cdat=cmiss
9875ENDIF
9876
9877print*,"<<<<<<<<<<<<<<<<<<< END vol7d object >>>>>>>>>>>>>>>>>>>>"
9878
9879END SUBROUTINE vol7d_display
9880
9881
9882!> stampa a video una sintesi del contenuto
9883SUBROUTINE dat_display(this,idat,rdat,ddat,bdat,cdat)
9884TYPE(vol7d_var),intent(in) :: this !< oggetto da visualizzare
9885!> real
9886REAL :: rdat
9887!> double precision
9888DOUBLE PRECISION :: ddat
9889!> integer
9890INTEGER :: idat
9891!> byte
9892INTEGER(kind=int_b) :: bdat
9893!> character
9894CHARACTER(len=*) :: cdat
9895
9896print *, to_char_dat(this,idat,rdat,ddat,bdat,cdat)
9897
9898end SUBROUTINE dat_display
9899
9900!> stampa a video una sintesi del contenuto
9901SUBROUTINE dat_vect_display(this,idat,rdat,ddat,bdat,cdat)
9902
9903TYPE(vol7d_var),intent(in) :: this(:) !< oggetto da visualizzare
9904!> real
9905REAL :: rdat(:)
9906!> double precision
9907DOUBLE PRECISION :: ddat(:)
9908!> integer
9909INTEGER :: idat(:)
9910!> byte
9911INTEGER(kind=int_b) :: bdat(:)
9912!> character
9913CHARACTER(len=*):: cdat(:)
9914
9915integer :: i
9916
9917do i =1,size(this)
9918 call display(this(i),idat(i),rdat(i),ddat(i),bdat(i),cdat(i))
9919end do
9920
9921end SUBROUTINE dat_vect_display
9922
9923
9924FUNCTION to_char_dat(this,idat,rdat,ddat,bdat,cdat)
9925#ifdef HAVE_DBALLE
9926USE dballef
9927#endif
9928TYPE(vol7d_var),INTENT(in) :: this
9929!> real
9930REAL :: rdat
9931!> double precision
9932DOUBLE PRECISION :: ddat
9933!> integer
9934INTEGER :: idat
9935!> byte
9936INTEGER(kind=int_b) :: bdat
9937!> character
9938CHARACTER(len=*) :: cdat
9939CHARACTER(len=80) :: to_char_dat
9940
9941CHARACTER(len=LEN(to_char_dat)) :: to_char_tmp
9942
9943
9944#ifdef HAVE_DBALLE
9945INTEGER :: handle, ier
9946
9947handle = 0
9948to_char_dat="VALUE: "
9949
9950if (c_e(idat)) to_char_dat=trim(to_char_dat)//" ;int> "//trim(to_char(idat))
9951if (c_e(rdat)) to_char_dat=trim(to_char_dat)//" ;real> "//trim(to_char(rdat))
9952if (c_e(ddat)) to_char_dat=trim(to_char_dat)//" ;double> "//trim(to_char(ddat))
9953if (c_e(bdat)) to_char_dat=trim(to_char_dat)//" ;byte> "//trim(to_char(bdat))
9954
9955if ( c_e(cdat))then
9956 ier = idba_messaggi(handle,"/dev/null", "w", "BUFR")
9957 ier = idba_spiegab(handle,this%btable,cdat,to_char_tmp)
9958 ier = idba_fatto(handle)
9959 to_char_dat=trim(to_char_dat)//" ;char> "//trim(to_char_tmp)
9960endif
9961
9962#else
9963
9964to_char_dat="VALUE: "
9965if (c_e(idat)) to_char_dat=trim(to_char_dat)//" ;int> "//trim(to_char(idat))
9966if (c_e(rdat)) to_char_dat=trim(to_char_dat)//" ;real> "//trim(to_char(rdat))
9967if (c_e(ddat)) to_char_dat=trim(to_char_dat)//" ;double> "//trim(to_char(ddat))
9968if (c_e(bdat)) to_char_dat=trim(to_char_dat)//" ;byte> "//trim(to_char(bdat))
9969if (c_e(cdat)) to_char_dat=trim(to_char_dat)//" ;char> "//trim(cdat)
9970
9971#endif
9972
9973END FUNCTION to_char_dat
9974
9975
9976!> Tests whether anything has ever been assigned to a vol7d object
9977!! (.TRUE.) or it is as clean as after an init (.FALSE.).
9978FUNCTION vol7d_c_e(this) RESULT(c_e)
9979TYPE(vol7d), INTENT(in) :: this
9980
9981LOGICAL :: c_e
9982
9983c_e = ASSOCIATED(this%ana) .OR. ASSOCIATED(this%time) .OR. &
9984 ASSOCIATED(this%level) .OR. ASSOCIATED(this%timerange) .OR. &
9985 ASSOCIATED(this%network) .OR. &
9986 ASSOCIATED(this%anavar%r) .OR. ASSOCIATED(this%anavar%d) .OR. &
9987 ASSOCIATED(this%anavar%i) .OR. ASSOCIATED(this%anavar%b) .OR. &
9988 ASSOCIATED(this%anavar%c) .OR. &
9989 ASSOCIATED(this%anaattr%r) .OR. ASSOCIATED(this%anaattr%d) .OR. &
9990 ASSOCIATED(this%anaattr%i) .OR. ASSOCIATED(this%anaattr%b) .OR. &
9991 ASSOCIATED(this%anaattr%c) .OR. &
9992 ASSOCIATED(this%dativar%r) .OR. ASSOCIATED(this%dativar%d) .OR. &
9993 ASSOCIATED(this%dativar%i) .OR. ASSOCIATED(this%dativar%b) .OR. &
9994 ASSOCIATED(this%dativar%c) .OR. &
9995 ASSOCIATED(this%datiattr%r) .OR. ASSOCIATED(this%datiattr%d) .OR. &
9996 ASSOCIATED(this%datiattr%i) .OR. ASSOCIATED(this%datiattr%b) .OR. &
9997 ASSOCIATED(this%datiattr%c)
9998
9999END FUNCTION vol7d_c_e
10000
10001
10002!> Metodo per allocare i descrittori delle 7 dimensioni.
10003!! Riceve un grande numero di parametri opzionali che
10004!! indicano quali descrittori allocare e con quale estensione;
10005!! i descrittori non specificati non vengono toccati.
10006!! Può essere quindi chiamato più volte allocando via via
10007!! descrittori relativi a dimensioni diverse.
10008!! Se un descrittore richiesto è già allocato, viene deallocato
10009!! (perdendone l'eventuale contenuto) e riallocato con l'estensione
10010!! richiesta.
10011!! Per i descrittori relativi a dimensioni che non siano variabili o attributi,
10012!! è possibile specificare l'estensione di una dimensione a 0,
10013!! in tal caso il descrittore viene comunque allocato con lunghezza nulla,
10014!! che è diverso da non allocarlo. Per i descrittori di variabili e attributi
10015!! passare un'estensione 0 equivale a non fornire il parametro.
10016!! Avere uno o più descrittori dimensionati con estensione nulla fa sì
10017!! che anche il volume dati successivamente allocato abbia estensione nulla;
10018!! sebbene ciò appaia inutile, un volume del genere può in realtà servire,
10019!! in associazione ai metodi ::vol7d_merge o ::vol7d_append per estendere
10020!! un volume esistente aggiungendo elementi in alcune dimensioni (quelle
10021!! a estensione non nulla, ovviamente) e mantenendo invariato tutto il resto.
10022!! Per quanto riguarda i descrittori delle dimensioni relative alle
10023!! variabili, la relativa estensione è specificata con la nomenclatura
10024!! \a n&lt;x&gt;&lt;y&gt;&lt;z&gt; dove &lt;x&gt; può valere:
10025!! - \a ana per variabili relative a voumi di anagrafica
10026!! - \a dati per variabili relative a voumi di dati
10027!!
10028!! &lt;y&gt; può valere:
10029!! - \a var per variabili
10030!! - \a attr per attributi
10031!! - \a varattr variabili aventi attributi nei volumi di attributi
10032!!
10033!! &lt;z&gt; può valere:
10034!! - \a r per variabili o attributi a valori reali
10035!! - \a d per variabili o attributi a valori a doppia precisione
10036!! - \a i per variabili o attributi a valori interi
10037!! - \a b per variabili o attributi a valori byte
10038!! - \a c per variabili o attributi a valori carattere
10039!!
10040SUBROUTINE vol7d_alloc(this, nana, ntime, nlevel, ntimerange, nnetwork, &
10041 nanavarr, nanavard, nanavari, nanavarb, nanavarc, &
10042 nanaattrr, nanaattrd, nanaattri, nanaattrb, nanaattrc, &
10043 nanavarattrr, nanavarattrd, nanavarattri, nanavarattrb, nanavarattrc, &
10044 ndativarr, ndativard, ndativari, ndativarb, ndativarc, &
10045 ndatiattrr, ndatiattrd, ndatiattri, ndatiattrb, ndatiattrc, &
10046 ndativarattrr, ndativarattrd, ndativarattri, ndativarattrb, ndativarattrc, &
10047 ini)
10048TYPE(vol7d),INTENT(inout) :: this !< oggetto di cui allocare i descrittori
10049INTEGER,INTENT(in),OPTIONAL :: nana !< estensione della dimensione anagrafica
10050INTEGER,INTENT(in),OPTIONAL :: ntime !< estensione della dimensione tempo
10051INTEGER,INTENT(in),OPTIONAL :: nlevel !< estensione della dimensione livello varticale
10052INTEGER,INTENT(in),OPTIONAL :: ntimerange !< estensione della dimensione intervallo temporale (timerange)
10053INTEGER,INTENT(in),OPTIONAL :: nnetwork !< estensione della dimensione rete
10054!> estensione delle possibili dimensioni variabile
10055INTEGER,INTENT(in),OPTIONAL :: &
10056 nanavarr, nanavard, nanavari, nanavarb, nanavarc, &
10057 nanaattrr, nanaattrd, nanaattri, nanaattrb, nanaattrc, &
10058 nanavarattrr, nanavarattrd, nanavarattri, nanavarattrb, nanavarattrc, &
10059 ndativarr, ndativard, ndativari, ndativarb, ndativarc, &
10060 ndatiattrr, ndatiattrd, ndatiattri, ndatiattrb, ndatiattrc, &
10061 ndativarattrr, ndativarattrd, ndativarattri, ndativarattrb, ndativarattrc
10062LOGICAL,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
10063
10064INTEGER :: i
10065LOGICAL :: linit
10066
10067IF (PRESENT(ini)) THEN
10068 linit = ini
10069ELSE
10070 linit = .false.
10071ENDIF
10072
10073! Dimensioni principali
10074IF (PRESENT(nana)) THEN
10075 IF (nana >= 0) THEN
10076 IF (ASSOCIATED(this%ana)) DEALLOCATE(this%ana)
10077 ALLOCATE(this%ana(nana))
10078 IF (linit) THEN
10079 DO i = 1, nana
10080 CALL init(this%ana(i))
10081 ENDDO
10082 ENDIF
10083 ENDIF
10084ENDIF
10085IF (PRESENT(ntime)) THEN
10086 IF (ntime >= 0) THEN
10087 IF (ASSOCIATED(this%time)) DEALLOCATE(this%time)
10088 ALLOCATE(this%time(ntime))
10089 IF (linit) THEN
10090 DO i = 1, ntime
10091 CALL init(this%time(i))
10092 ENDDO
10093 ENDIF
10094 ENDIF
10095ENDIF
10096IF (PRESENT(nlevel)) THEN
10097 IF (nlevel >= 0) THEN
10098 IF (ASSOCIATED(this%level)) DEALLOCATE(this%level)
10099 ALLOCATE(this%level(nlevel))
10100 IF (linit) THEN
10101 DO i = 1, nlevel
10102 CALL init(this%level(i))
10103 ENDDO
10104 ENDIF
10105 ENDIF
10106ENDIF
10107IF (PRESENT(ntimerange)) THEN
10108 IF (ntimerange >= 0) THEN
10109 IF (ASSOCIATED(this%timerange)) DEALLOCATE(this%timerange)
10110 ALLOCATE(this%timerange(ntimerange))
10111 IF (linit) THEN
10112 DO i = 1, ntimerange
10113 CALL init(this%timerange(i))
10114 ENDDO
10115 ENDIF
10116 ENDIF
10117ENDIF
10118IF (PRESENT(nnetwork)) THEN
10119 IF (nnetwork >= 0) THEN
10120 IF (ASSOCIATED(this%network)) DEALLOCATE(this%network)
10121 ALLOCATE(this%network(nnetwork))
10122 IF (linit) THEN
10123 DO i = 1, nnetwork
10124 CALL init(this%network(i))
10125 ENDDO
10126 ENDIF
10127 ENDIF
10128ENDIF
10129! Dimensioni dei tipi delle variabili
10130CALL vol7d_varvect_alloc(this%anavar, nanavarr, nanavard, &
10131 nanavari, nanavarb, nanavarc, ini)
10132CALL vol7d_varvect_alloc(this%anaattr, nanaattrr, nanaattrd, &
10133 nanaattri, nanaattrb, nanaattrc, ini)
10134CALL vol7d_varvect_alloc(this%anavarattr, nanavarattrr, nanavarattrd, &
10135 nanavarattri, nanavarattrb, nanavarattrc, ini)
10136CALL vol7d_varvect_alloc(this%dativar, ndativarr, ndativard, &
10137 ndativari, ndativarb, ndativarc, ini)
10138CALL vol7d_varvect_alloc(this%datiattr, ndatiattrr, ndatiattrd, &
10139 ndatiattri, ndatiattrb, ndatiattrc, ini)
10140CALL vol7d_varvect_alloc(this%dativarattr, ndativarattrr, ndativarattrd, &
10141 ndativarattri, ndativarattrb, ndativarattrc, ini)
10142
10143END SUBROUTINE vol7d_alloc
10144
10145
10146FUNCTION vol7d_check_alloc_ana(this)
10147TYPE(vol7d),INTENT(in) :: this
10148LOGICAL :: vol7d_check_alloc_ana
10149
10150vol7d_check_alloc_ana = ASSOCIATED(this%ana) .AND. ASSOCIATED(this%network)
10151
10152END FUNCTION vol7d_check_alloc_ana
10153
10154SUBROUTINE vol7d_force_alloc_ana(this, ini)
10155TYPE(vol7d),INTENT(inout) :: this
10156LOGICAL,INTENT(in),OPTIONAL :: ini
10157
10158! Alloco i descrittori minimi per avere un volume di anagrafica
10159IF (.NOT. ASSOCIATED(this%ana)) CALL vol7d_alloc(this, nana=1, ini=ini)
10160IF (.NOT. ASSOCIATED(this%network)) CALL vol7d_alloc(this, nnetwork=1, ini=ini)
10161
10162END SUBROUTINE vol7d_force_alloc_ana
10163
10164
10165FUNCTION vol7d_check_alloc_dati(this)
10166TYPE(vol7d),INTENT(in) :: this
10167LOGICAL :: vol7d_check_alloc_dati
10168
10169vol7d_check_alloc_dati = vol7d_check_alloc_ana(this) .AND. &
10170 ASSOCIATED(this%time) .AND. ASSOCIATED(this%level) .AND. &
10171 ASSOCIATED(this%timerange)
10172
10173END FUNCTION vol7d_check_alloc_dati
10174
10175SUBROUTINE vol7d_force_alloc_dati(this, ini)
10176TYPE(vol7d),INTENT(inout) :: this
10177LOGICAL,INTENT(in),OPTIONAL :: ini
10178
10179! Alloco i descrittori minimi per avere un volume di dati
10180CALL vol7d_force_alloc_ana(this, ini)
10181IF (.NOT. ASSOCIATED(this%time)) CALL vol7d_alloc(this, ntime=1, ini=ini)
10182IF (.NOT. ASSOCIATED(this%level)) CALL vol7d_alloc(this, nlevel=1, ini=ini)
10183IF (.NOT. ASSOCIATED(this%timerange)) CALL vol7d_alloc(this, ntimerange=1, ini=ini)
10184
10185END SUBROUTINE vol7d_force_alloc_dati
10186
10187
10188SUBROUTINE vol7d_force_alloc(this)
10189TYPE(vol7d),INTENT(inout) :: this
10190
10191! If anything really not allocated yet, allocate with size 0
10192IF (.NOT. ASSOCIATED(this%ana)) CALL vol7d_alloc(this, nana=0)
10193IF (.NOT. ASSOCIATED(this%network)) CALL vol7d_alloc(this, nnetwork=0)
10194IF (.NOT. ASSOCIATED(this%time)) CALL vol7d_alloc(this, ntime=0)
10195IF (.NOT. ASSOCIATED(this%level)) CALL vol7d_alloc(this, nlevel=0)
10196IF (.NOT. ASSOCIATED(this%timerange)) CALL vol7d_alloc(this, ntimerange=0)
10197
10198END SUBROUTINE vol7d_force_alloc
10199
10200
10201FUNCTION vol7d_check_vol(this)
10202TYPE(vol7d),INTENT(in) :: this !< oggetto da controllare
10203LOGICAL :: vol7d_check_vol
10204
10205vol7d_check_vol = c_e(this)
10206
10207! Anagrafica
10208IF (ASSOCIATED(this%anavar%r) .AND. .NOT.ASSOCIATED(this%volanar)) THEN
10209 vol7d_check_vol = .false.
10210ENDIF
10211
10212IF (ASSOCIATED(this%anavar%d) .AND. .NOT.ASSOCIATED(this%volanad)) THEN
10213 vol7d_check_vol = .false.
10214ENDIF
10215
10216IF (ASSOCIATED(this%anavar%i) .AND. .NOT.ASSOCIATED(this%volanai)) THEN
10217 vol7d_check_vol = .false.
10218ENDIF
10219
10220IF (ASSOCIATED(this%anavar%b) .AND. .NOT.ASSOCIATED(this%volanab)) THEN
10221 vol7d_check_vol = .false.
10222ENDIF
10223
10224IF (ASSOCIATED(this%anavar%c) .AND. .NOT.ASSOCIATED(this%volanac)) THEN
10225 vol7d_check_vol = .false.
10226ENDIF
10227IF (ASSOCIATED(this%anavar%r) .OR. ASSOCIATED(this%anavar%d) .OR. &
10228 ASSOCIATED(this%anavar%i) .OR. ASSOCIATED(this%anavar%b) .OR. &
10229 ASSOCIATED(this%anavar%c)) THEN
10230 vol7d_check_vol = vol7d_check_vol .AND. vol7d_check_alloc_ana(this)
10231ENDIF
10232
10233! Attributi dell'anagrafica
10234IF (ASSOCIATED(this%anaattr%r) .AND. ASSOCIATED(this%anavarattr%r) .AND. &
10235 .NOT.ASSOCIATED(this%volanaattrr)) THEN
10236 vol7d_check_vol = .false.
10237ENDIF
10238
10239IF (ASSOCIATED(this%anaattr%d) .AND. ASSOCIATED(this%anavarattr%d) .AND. &
10240 .NOT.ASSOCIATED(this%volanaattrd)) THEN
10241 vol7d_check_vol = .false.
10242ENDIF
10243
10244IF (ASSOCIATED(this%anaattr%i) .AND. ASSOCIATED(this%anavarattr%i) .AND. &
10245 .NOT.ASSOCIATED(this%volanaattri)) THEN
10246 vol7d_check_vol = .false.
10247ENDIF
10248
10249IF (ASSOCIATED(this%anaattr%b) .AND. ASSOCIATED(this%anavarattr%b) .AND. &
10250 .NOT.ASSOCIATED(this%volanaattrb)) THEN
10251 vol7d_check_vol = .false.
10252ENDIF
10253
10254IF (ASSOCIATED(this%anaattr%c) .AND. ASSOCIATED(this%anavarattr%c) .AND. &
10255 .NOT.ASSOCIATED(this%volanaattrc)) THEN
10256 vol7d_check_vol = .false.
10257ENDIF
10258
10259! Dati
10260IF (ASSOCIATED(this%dativar%r) .AND. .NOT.ASSOCIATED(this%voldatir)) THEN
10261 vol7d_check_vol = .false.
10262ENDIF
10263
10264IF (ASSOCIATED(this%dativar%d) .AND. .NOT.ASSOCIATED(this%voldatid)) THEN
10265 vol7d_check_vol = .false.
10266ENDIF
10267
10268IF (ASSOCIATED(this%dativar%i) .AND. .NOT.ASSOCIATED(this%voldatii)) THEN
10269 vol7d_check_vol = .false.
10270ENDIF
10271
10272IF (ASSOCIATED(this%dativar%b) .AND. .NOT.ASSOCIATED(this%voldatib)) THEN
10273 vol7d_check_vol = .false.
10274ENDIF
10275
10276IF (ASSOCIATED(this%dativar%c) .AND. .NOT.ASSOCIATED(this%voldatic)) THEN
10277 vol7d_check_vol = .false.
10278ENDIF
10279
10280! Attributi dei dati
10281IF (ASSOCIATED(this%datiattr%r) .AND. ASSOCIATED(this%dativarattr%r) .AND. &
10282 .NOT.ASSOCIATED(this%voldatiattrr)) THEN
10283 vol7d_check_vol = .false.
10284ENDIF
10285
10286IF (ASSOCIATED(this%datiattr%d) .AND. ASSOCIATED(this%dativarattr%d) .AND. &
10287 .NOT.ASSOCIATED(this%voldatiattrd)) THEN
10288 vol7d_check_vol = .false.
10289ENDIF
10290
10291IF (ASSOCIATED(this%datiattr%i) .AND. ASSOCIATED(this%dativarattr%i) .AND. &
10292 .NOT.ASSOCIATED(this%voldatiattri)) THEN
10293 vol7d_check_vol = .false.
10294ENDIF
10295
10296IF (ASSOCIATED(this%datiattr%b) .AND. ASSOCIATED(this%dativarattr%b) .AND. &
10297 .NOT.ASSOCIATED(this%voldatiattrb)) THEN
10298 vol7d_check_vol = .false.
10299ENDIF
10300
10301IF (ASSOCIATED(this%datiattr%c) .AND. ASSOCIATED(this%dativarattr%c) .AND. &
10302 .NOT.ASSOCIATED(this%voldatiattrc)) THEN
10303 vol7d_check_vol = .false.
10304ENDIF
10305IF (ASSOCIATED(this%dativar%r) .OR. ASSOCIATED(this%dativar%d) .OR. &
10306 ASSOCIATED(this%dativar%i) .OR. ASSOCIATED(this%dativar%b) .OR. &
10307 ASSOCIATED(this%dativar%c)) THEN
10308 vol7d_check_vol = vol7d_check_vol .AND. vol7d_check_alloc_dati(this)
10309ENDIF
10310
10311END FUNCTION vol7d_check_vol
10312
10313
10314!> Metodo per allocare i volumi richiesti di variabili e attributi per
10315!! anagrafica e dati.
10316!! Se alcuni dei descrittori relativi alle dimensioni anagrafica,
10317!! livello verticale, tempo, intervallo temporale (timerange), rete non sono
10318!! stati richiesti preventivamente con la ::vol7d_alloc, essi vengono allocati
10319!! automaticamente da questo metodo
10320!! con estensione di default pari a 1 (non 0!), questo significa, ad esempio,
10321!! che se prevedo di avere soli dati superficiali, cioè ad un solo livello
10322!! verticale, o una sola rete di stazioni, non devo preoccuparmi di
10323!! specificare questa informazione.
10324!! Tra i 20 possibili volumi allocabili
10325!! ((variabili,attributi)*(anagrafica,dati)*(r,d,i,b,c)=20)
10326!! saranno allocati solo quelli per cui è stato precedentemente richiesto il
10327!! corrispondente descrittore variabili/attributi con la ::vol7d_alloc.
10328SUBROUTINE vol7d_alloc_vol(this, ini, inivol)
10329TYPE(vol7d),INTENT(inout) :: this !< oggetto di cui allocare i volumi
10330LOGICAL,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
10331LOGICAL,INTENT(in),OPTIONAL :: inivol !< se fornito e vale \c .TRUE., i volumi allocati saranno inizializzati a valore mancante
10332
10333LOGICAL :: linivol
10334
10335IF (PRESENT(inivol)) THEN
10336 linivol = inivol
10337ELSE
10338 linivol = .true.
10339ENDIF
10340
10341! Anagrafica
10342IF (ASSOCIATED(this%anavar%r) .AND. .NOT.ASSOCIATED(this%volanar)) THEN
10343 CALL vol7d_force_alloc_ana(this, ini)
10344 ALLOCATE(this%volanar(SIZE(this%ana), SIZE(this%anavar%r), SIZE(this%network)))
10345 IF (linivol) this%volanar(:,:,:) = rmiss
10346ENDIF
10347
10348IF (ASSOCIATED(this%anavar%d) .AND. .NOT.ASSOCIATED(this%volanad)) THEN
10349 CALL vol7d_force_alloc_ana(this, ini)
10350 ALLOCATE(this%volanad(SIZE(this%ana), SIZE(this%anavar%d), SIZE(this%network)))
10351 IF (linivol) this%volanad(:,:,:) = rdmiss
10352ENDIF
10353
10354IF (ASSOCIATED(this%anavar%i) .AND. .NOT.ASSOCIATED(this%volanai)) THEN
10355 CALL vol7d_force_alloc_ana(this, ini)
10356 ALLOCATE(this%volanai(SIZE(this%ana), SIZE(this%anavar%i), SIZE(this%network)))
10357 IF (linivol) this%volanai(:,:,:) = imiss
10358ENDIF
10359
10360IF (ASSOCIATED(this%anavar%b) .AND. .NOT.ASSOCIATED(this%volanab)) THEN
10361 CALL vol7d_force_alloc_ana(this, ini)
10362 ALLOCATE(this%volanab(SIZE(this%ana), SIZE(this%anavar%b), SIZE(this%network)))
10363 IF (linivol) this%volanab(:,:,:) = ibmiss
10364ENDIF
10365
10366IF (ASSOCIATED(this%anavar%c) .AND. .NOT.ASSOCIATED(this%volanac)) THEN
10367 CALL vol7d_force_alloc_ana(this, ini)
10368 ALLOCATE(this%volanac(SIZE(this%ana), SIZE(this%anavar%c), SIZE(this%network)))
10369 IF (linivol) this%volanac(:,:,:) = cmiss
10370ENDIF
10371
10372! Attributi dell'anagrafica
10373IF (ASSOCIATED(this%anaattr%r) .AND. ASSOCIATED(this%anavarattr%r) .AND. &
10374 .NOT.ASSOCIATED(this%volanaattrr)) THEN
10375 CALL vol7d_force_alloc_ana(this, ini)
10376 ALLOCATE(this%volanaattrr(SIZE(this%ana), SIZE(this%anavarattr%r), &
10377 SIZE(this%network), SIZE(this%anaattr%r)))
10378 IF (linivol) this%volanaattrr(:,:,:,:) = rmiss
10379ENDIF
10380
10381IF (ASSOCIATED(this%anaattr%d) .AND. ASSOCIATED(this%anavarattr%d) .AND. &
10382 .NOT.ASSOCIATED(this%volanaattrd)) THEN
10383 CALL vol7d_force_alloc_ana(this, ini)
10384 ALLOCATE(this%volanaattrd(SIZE(this%ana), SIZE(this%anavarattr%d), &
10385 SIZE(this%network), SIZE(this%anaattr%d)))
10386 IF (linivol) this%volanaattrd(:,:,:,:) = rdmiss
10387ENDIF
10388
10389IF (ASSOCIATED(this%anaattr%i) .AND. ASSOCIATED(this%anavarattr%i) .AND. &
10390 .NOT.ASSOCIATED(this%volanaattri)) THEN
10391 CALL vol7d_force_alloc_ana(this, ini)
10392 ALLOCATE(this%volanaattri(SIZE(this%ana), SIZE(this%anavarattr%i), &
10393 SIZE(this%network), SIZE(this%anaattr%i)))
10394 IF (linivol) this%volanaattri(:,:,:,:) = imiss
10395ENDIF
10396
10397IF (ASSOCIATED(this%anaattr%b) .AND. ASSOCIATED(this%anavarattr%b) .AND. &
10398 .NOT.ASSOCIATED(this%volanaattrb)) THEN
10399 CALL vol7d_force_alloc_ana(this, ini)
10400 ALLOCATE(this%volanaattrb(SIZE(this%ana), SIZE(this%anavarattr%b), &
10401 SIZE(this%network), SIZE(this%anaattr%b)))
10402 IF (linivol) this%volanaattrb(:,:,:,:) = ibmiss
10403ENDIF
10404
10405IF (ASSOCIATED(this%anaattr%c) .AND. ASSOCIATED(this%anavarattr%c) .AND. &
10406 .NOT.ASSOCIATED(this%volanaattrc)) THEN
10407 CALL vol7d_force_alloc_ana(this, ini)
10408 ALLOCATE(this%volanaattrc(SIZE(this%ana), SIZE(this%anavarattr%c), &
10409 SIZE(this%network), SIZE(this%anaattr%c)))
10410 IF (linivol) this%volanaattrc(:,:,:,:) = cmiss
10411ENDIF
10412
10413! Dati
10414IF (ASSOCIATED(this%dativar%r) .AND. .NOT.ASSOCIATED(this%voldatir)) THEN
10415 CALL vol7d_force_alloc_dati(this, ini)
10416 ALLOCATE(this%voldatir(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
10417 SIZE(this%timerange), SIZE(this%dativar%r), SIZE(this%network)))
10418 IF (linivol) this%voldatir(:,:,:,:,:,:) = rmiss
10419ENDIF
10420
10421IF (ASSOCIATED(this%dativar%d) .AND. .NOT.ASSOCIATED(this%voldatid)) THEN
10422 CALL vol7d_force_alloc_dati(this, ini)
10423 ALLOCATE(this%voldatid(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
10424 SIZE(this%timerange), SIZE(this%dativar%d), SIZE(this%network)))
10425 IF (linivol) this%voldatid(:,:,:,:,:,:) = rdmiss
10426ENDIF
10427
10428IF (ASSOCIATED(this%dativar%i) .AND. .NOT.ASSOCIATED(this%voldatii)) THEN
10429 CALL vol7d_force_alloc_dati(this, ini)
10430 ALLOCATE(this%voldatii(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
10431 SIZE(this%timerange), SIZE(this%dativar%i), SIZE(this%network)))
10432 IF (linivol) this%voldatii(:,:,:,:,:,:) = imiss
10433ENDIF
10434
10435IF (ASSOCIATED(this%dativar%b) .AND. .NOT.ASSOCIATED(this%voldatib)) THEN
10436 CALL vol7d_force_alloc_dati(this, ini)
10437 ALLOCATE(this%voldatib(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
10438 SIZE(this%timerange), SIZE(this%dativar%b), SIZE(this%network)))
10439 IF (linivol) this%voldatib(:,:,:,:,:,:) = ibmiss
10440ENDIF
10441
10442IF (ASSOCIATED(this%dativar%c) .AND. .NOT.ASSOCIATED(this%voldatic)) THEN
10443 CALL vol7d_force_alloc_dati(this, ini)
10444 ALLOCATE(this%voldatic(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
10445 SIZE(this%timerange), SIZE(this%dativar%c), SIZE(this%network)))
10446 IF (linivol) this%voldatic(:,:,:,:,:,:) = cmiss
10447ENDIF
10448
10449! Attributi dei dati
10450IF (ASSOCIATED(this%datiattr%r) .AND. ASSOCIATED(this%dativarattr%r) .AND. &
10451 .NOT.ASSOCIATED(this%voldatiattrr)) THEN
10452 CALL vol7d_force_alloc_dati(this, ini)
10453 ALLOCATE(this%voldatiattrr(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
10454 SIZE(this%timerange), SIZE(this%dativarattr%r), SIZE(this%network), &
10455 SIZE(this%datiattr%r)))
10456 IF (linivol) this%voldatiattrr(:,:,:,:,:,:,:) = rmiss
10457ENDIF
10458
10459IF (ASSOCIATED(this%datiattr%d) .AND. ASSOCIATED(this%dativarattr%d) .AND. &
10460 .NOT.ASSOCIATED(this%voldatiattrd)) THEN
10461 CALL vol7d_force_alloc_dati(this, ini)
10462 ALLOCATE(this%voldatiattrd(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
10463 SIZE(this%timerange), SIZE(this%dativarattr%d), SIZE(this%network), &
10464 SIZE(this%datiattr%d)))
10465 IF (linivol) this%voldatiattrd(:,:,:,:,:,:,:) = rdmiss
10466ENDIF
10467
10468IF (ASSOCIATED(this%datiattr%i) .AND. ASSOCIATED(this%dativarattr%i) .AND. &
10469 .NOT.ASSOCIATED(this%voldatiattri)) THEN
10470 CALL vol7d_force_alloc_dati(this, ini)
10471 ALLOCATE(this%voldatiattri(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
10472 SIZE(this%timerange), SIZE(this%dativarattr%i), SIZE(this%network), &
10473 SIZE(this%datiattr%i)))
10474 IF (linivol) this%voldatiattri(:,:,:,:,:,:,:) = imiss
10475ENDIF
10476
10477IF (ASSOCIATED(this%datiattr%b) .AND. ASSOCIATED(this%dativarattr%b) .AND. &
10478 .NOT.ASSOCIATED(this%voldatiattrb)) THEN
10479 CALL vol7d_force_alloc_dati(this, ini)
10480 ALLOCATE(this%voldatiattrb(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
10481 SIZE(this%timerange), SIZE(this%dativarattr%b), SIZE(this%network), &
10482 SIZE(this%datiattr%b)))
10483 IF (linivol) this%voldatiattrb(:,:,:,:,:,:,:) = ibmiss
10484ENDIF
10485
10486IF (ASSOCIATED(this%datiattr%c) .AND. ASSOCIATED(this%dativarattr%c) .AND. &
10487 .NOT.ASSOCIATED(this%voldatiattrc)) THEN
10488 CALL vol7d_force_alloc_dati(this, ini)
10489 ALLOCATE(this%voldatiattrc(SIZE(this%ana), SIZE(this%time), SIZE(this%level), &
10490 SIZE(this%timerange), SIZE(this%dativarattr%c), SIZE(this%network), &
10491 SIZE(this%datiattr%c)))
10492 IF (linivol) this%voldatiattrc(:,:,:,:,:,:,:) = cmiss
10493ENDIF
10494
10495! Catch-all method
10496CALL vol7d_force_alloc(this)
10497
10498! Creo gli indici var-attr
10499
10500#ifdef DEBUG
10501CALL l4f_log(l4f_debug,"calling: vol7d_set_attr_ind")
10502#endif
10503
10504CALL vol7d_set_attr_ind(this)
10505
10506
10507
10508END SUBROUTINE vol7d_alloc_vol
10509
10510
10511!> Metodo per creare gli indici che associano le variabili aventi attributo
10512!! alle variabili nei relativi descrittori.
10513!! Ha senso chiamare questo metodo solo dopo che i descrittori delle variabili
10514!! e degli attributi desiderati sono stati allocati ed è stato assegnato un
10515!! valore ai relativi membri btable (vedi vol7d_var_class::vol7d_var), se
10516!! i descrittori non sono stati allocati o assegnati, il metodo non fa niente.
10517SUBROUTINE vol7d_set_attr_ind(this)
10518TYPE(vol7d),INTENT(inout) :: this !< oggetto in cui creare gli indici
10519
10520INTEGER :: i
10521
10522! real
10523IF (ASSOCIATED(this%dativar%r)) THEN
10524 IF (ASSOCIATED(this%dativarattr%r)) THEN
10525 DO i = 1, SIZE(this%dativar%r)
10526 this%dativar%r(i)%r = &
10527 firsttrue(this%dativar%r(i)%btable == this%dativarattr%r(:)%btable)
10528 ENDDO
10529 ENDIF
10530
10531 IF (ASSOCIATED(this%dativarattr%d)) THEN
10532 DO i = 1, SIZE(this%dativar%r)
10533 this%dativar%r(i)%d = &
10534 firsttrue(this%dativar%r(i)%btable == this%dativarattr%d(:)%btable)
10535 ENDDO
10536 ENDIF
10537
10538 IF (ASSOCIATED(this%dativarattr%i)) THEN
10539 DO i = 1, SIZE(this%dativar%r)
10540 this%dativar%r(i)%i = &
10541 firsttrue(this%dativar%r(i)%btable == this%dativarattr%i(:)%btable)
10542 ENDDO
10543 ENDIF
10544
10545 IF (ASSOCIATED(this%dativarattr%b)) THEN
10546 DO i = 1, SIZE(this%dativar%r)
10547 this%dativar%r(i)%b = &
10548 firsttrue(this%dativar%r(i)%btable == this%dativarattr%b(:)%btable)
10549 ENDDO
10550 ENDIF
10551
10552 IF (ASSOCIATED(this%dativarattr%c)) THEN
10553 DO i = 1, SIZE(this%dativar%r)
10554 this%dativar%r(i)%c = &
10555 firsttrue(this%dativar%r(i)%btable == this%dativarattr%c(:)%btable)
10556 ENDDO
10557 ENDIF
10558ENDIF
10559! double
10560IF (ASSOCIATED(this%dativar%d)) THEN
10561 IF (ASSOCIATED(this%dativarattr%r)) THEN
10562 DO i = 1, SIZE(this%dativar%d)
10563 this%dativar%d(i)%r = &
10564 firsttrue(this%dativar%d(i)%btable == this%dativarattr%r(:)%btable)
10565 ENDDO
10566 ENDIF
10567
10568 IF (ASSOCIATED(this%dativarattr%d)) THEN
10569 DO i = 1, SIZE(this%dativar%d)
10570 this%dativar%d(i)%d = &
10571 firsttrue(this%dativar%d(i)%btable == this%dativarattr%d(:)%btable)
10572 ENDDO
10573 ENDIF
10574
10575 IF (ASSOCIATED(this%dativarattr%i)) THEN
10576 DO i = 1, SIZE(this%dativar%d)
10577 this%dativar%d(i)%i = &
10578 firsttrue(this%dativar%d(i)%btable == this%dativarattr%i(:)%btable)
10579 ENDDO
10580 ENDIF
10581
10582 IF (ASSOCIATED(this%dativarattr%b)) THEN
10583 DO i = 1, SIZE(this%dativar%d)
10584 this%dativar%d(i)%b = &
10585 firsttrue(this%dativar%d(i)%btable == this%dativarattr%b(:)%btable)
10586 ENDDO
10587 ENDIF
10588
10589 IF (ASSOCIATED(this%dativarattr%c)) THEN
10590 DO i = 1, SIZE(this%dativar%d)
10591 this%dativar%d(i)%c = &
10592 firsttrue(this%dativar%d(i)%btable == this%dativarattr%c(:)%btable)
10593 ENDDO
10594 ENDIF
10595ENDIF
10596! integer
10597IF (ASSOCIATED(this%dativar%i)) THEN
10598 IF (ASSOCIATED(this%dativarattr%r)) THEN
10599 DO i = 1, SIZE(this%dativar%i)
10600 this%dativar%i(i)%r = &
10601 firsttrue(this%dativar%i(i)%btable == this%dativarattr%r(:)%btable)
10602 ENDDO
10603 ENDIF
10604
10605 IF (ASSOCIATED(this%dativarattr%d)) THEN
10606 DO i = 1, SIZE(this%dativar%i)
10607 this%dativar%i(i)%d = &
10608 firsttrue(this%dativar%i(i)%btable == this%dativarattr%d(:)%btable)
10609 ENDDO
10610 ENDIF
10611
10612 IF (ASSOCIATED(this%dativarattr%i)) THEN
10613 DO i = 1, SIZE(this%dativar%i)
10614 this%dativar%i(i)%i = &
10615 firsttrue(this%dativar%i(i)%btable == this%dativarattr%i(:)%btable)
10616 ENDDO
10617 ENDIF
10618
10619 IF (ASSOCIATED(this%dativarattr%b)) THEN
10620 DO i = 1, SIZE(this%dativar%i)
10621 this%dativar%i(i)%b = &
10622 firsttrue(this%dativar%i(i)%btable == this%dativarattr%b(:)%btable)
10623 ENDDO
10624 ENDIF
10625
10626 IF (ASSOCIATED(this%dativarattr%c)) THEN
10627 DO i = 1, SIZE(this%dativar%i)
10628 this%dativar%i(i)%c = &
10629 firsttrue(this%dativar%i(i)%btable == this%dativarattr%c(:)%btable)
10630 ENDDO
10631 ENDIF
10632ENDIF
10633! byte
10634IF (ASSOCIATED(this%dativar%b)) THEN
10635 IF (ASSOCIATED(this%dativarattr%r)) THEN
10636 DO i = 1, SIZE(this%dativar%b)
10637 this%dativar%b(i)%r = &
10638 firsttrue(this%dativar%b(i)%btable == this%dativarattr%r(:)%btable)
10639 ENDDO
10640 ENDIF
10641
10642 IF (ASSOCIATED(this%dativarattr%d)) THEN
10643 DO i = 1, SIZE(this%dativar%b)
10644 this%dativar%b(i)%d = &
10645 firsttrue(this%dativar%b(i)%btable == this%dativarattr%d(:)%btable)
10646 ENDDO
10647 ENDIF
10648
10649 IF (ASSOCIATED(this%dativarattr%i)) THEN
10650 DO i = 1, SIZE(this%dativar%b)
10651 this%dativar%b(i)%i = &
10652 firsttrue(this%dativar%b(i)%btable == this%dativarattr%i(:)%btable)
10653 ENDDO
10654 ENDIF
10655
10656 IF (ASSOCIATED(this%dativarattr%b)) THEN
10657 DO i = 1, SIZE(this%dativar%b)
10658 this%dativar%b(i)%b = &
10659 firsttrue(this%dativar%b(i)%btable == this%dativarattr%b(:)%btable)
10660 ENDDO
10661 ENDIF
10662
10663 IF (ASSOCIATED(this%dativarattr%c)) THEN
10664 DO i = 1, SIZE(this%dativar%b)
10665 this%dativar%b(i)%c = &
10666 firsttrue(this%dativar%b(i)%btable == this%dativarattr%c(:)%btable)
10667 ENDDO
10668 ENDIF
10669ENDIF
10670! character
10671IF (ASSOCIATED(this%dativar%c)) THEN
10672 IF (ASSOCIATED(this%dativarattr%r)) THEN
10673 DO i = 1, SIZE(this%dativar%c)
10674 this%dativar%c(i)%r = &
10675 firsttrue(this%dativar%c(i)%btable == this%dativarattr%r(:)%btable)
10676 ENDDO
10677 ENDIF
10678
10679 IF (ASSOCIATED(this%dativarattr%d)) THEN
10680 DO i = 1, SIZE(this%dativar%c)
10681 this%dativar%c(i)%d = &
10682 firsttrue(this%dativar%c(i)%btable == this%dativarattr%d(:)%btable)
10683 ENDDO
10684 ENDIF
10685
10686 IF (ASSOCIATED(this%dativarattr%i)) THEN
10687 DO i = 1, SIZE(this%dativar%c)
10688 this%dativar%c(i)%i = &
10689 firsttrue(this%dativar%c(i)%btable == this%dativarattr%i(:)%btable)
10690 ENDDO
10691 ENDIF
10692
10693 IF (ASSOCIATED(this%dativarattr%b)) THEN
10694 DO i = 1, SIZE(this%dativar%c)
10695 this%dativar%c(i)%b = &
10696 firsttrue(this%dativar%c(i)%btable == this%dativarattr%b(:)%btable)
10697 ENDDO
10698 ENDIF
10699
10700 IF (ASSOCIATED(this%dativarattr%c)) THEN
10701 DO i = 1, SIZE(this%dativar%c)
10702 this%dativar%c(i)%c = &
10703 firsttrue(this%dativar%c(i)%btable == this%dativarattr%c(:)%btable)
10704 ENDDO
10705 ENDIF
10706ENDIF
10707
10708END SUBROUTINE vol7d_set_attr_ind
10709
10710
10711!> Metodo per fondere 2 oggetti vol7d.
10712!! Il secondo volume viene accodato al primo e poi distrutto, si veda
10713!! quindi la descrizione di ::vol7d_append. Se uno degli oggetti \a
10714!! this o \a that sono vuoti non perde tempo inutile,
10715SUBROUTINE vol7d_merge(this, that, sort, bestdata, &
10716 ltimesimple, ltimerangesimple, llevelsimple, lanasimple)
10717TYPE(vol7d),INTENT(INOUT) :: this !< primo oggetto in ingresso, alla fine conterrà il risultato della fusione
10718TYPE(vol7d),INTENT(INOUT) :: that !< secondo oggetto in ingresso, alla fine sarà distrutto
10719LOGICAL,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
10720LOGICAL,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
10721LOGICAL,INTENT(IN),OPTIONAL :: ltimesimple, ltimerangesimple, llevelsimple, lanasimple ! experimental, please do not use outside the library now
10722
10723TYPE(vol7d) :: v7d_clean
10724
10725
10726IF (.NOT.c_e(this)) THEN ! speedup
10727 this = that
10728 CALL init(v7d_clean)
10729 that = v7d_clean ! destroy that without deallocating
10730ELSE ! Append that to this and destroy that
10731 CALL vol7d_append(this, that, sort, bestdata, &
10732 ltimesimple, ltimerangesimple, llevelsimple, lanasimple)
10733 CALL delete(that)
10734ENDIF
10735
10736END SUBROUTINE vol7d_merge
10737
10738
10739!> Metodo per accodare un oggetto vol7d ad un altro.
10740!! Si tratta di un metodo molto potente e versatile;
10741!! i descrittori delle dimensioni del volume finale conterranno i valori
10742!! dei corrispondenti descrittori del primo e del secondo volume
10743!! e i volumi di anagrafica e dati conterranno i valori dei due volumi
10744!! ai posti giusti, e valori mancanti per le nuove combinazioni che
10745!! eventualmente si verranno a creare.
10746!! Se i volumi multidimensionali di anagrafica e/o dati dei 2 oggetti
10747!! hanno un'intersezione non nulla, negli elementi comuni il volume finale
10748!! conterrà il corrispondente elemento del \b secondo volume.
10749!! Attenzione che, durante l'esecuzione del metodo, la memoria richiesta è
10750!! pari alla memoria complessiva occupata dai 2 volumi iniziali più
10751!! la memoria complessiva del volume finale, per cui, nel caso di volumi grandi,
10752!! ci potrebbero essere problemi di esaurimento della memoria centrale.
10753!! Se l'oggetto \a that è vuoto non perde tempo inutile,
10754!!
10755!! \todo nel caso di elementi comuni inserire la possibiità (opzionale per
10756!! non penalizzare le prestazioni quando ciò non serve) di effettuare una scelta
10757!! più ragionata dell'elemento da tenere, almeno controllando i dati mancanti
10758!! se non le flag di qualità
10759!!
10760!! \todo "rateizzare" l'allocazione dei volumi per ridurre l'occupazione di
10761!! memoria nel caso siano allocati contemporaneamente volumi di variabili e
10762!! di attributi o più volumi di tipi diversi
10763!!
10764!! \todo il parametro \a that è dichiarato \a INOUT perché la vol7d_alloc_vol
10765!! può modificarlo, bisognerebbe implementare una vol7d_check_vol che restituisca
10766!! errore anziché usare la vol7d_alloc_vol.
10767SUBROUTINE vol7d_append(this, that, sort, bestdata, &
10768 ltimesimple, ltimerangesimple, llevelsimple, lanasimple, lnetworksimple)
10769TYPE(vol7d),INTENT(INOUT) :: this !< primo oggetto in ingresso, a cui sarà accodato il secondo
10770TYPE(vol7d),INTENT(IN) :: that !< secondo oggetto in ingresso, non viene modificato dal metodo
10771LOGICAL,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
10772! experimental, please do not use outside the library now, they force the use
10773! of a simplified mapping algorithm which is valid only whene the dimension
10774! content is the same in both volumes , or when one of them is empty
10775LOGICAL,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
10776LOGICAL,INTENT(IN),OPTIONAL :: ltimesimple, ltimerangesimple, llevelsimple, lanasimple, lnetworksimple
10777
10778
10779TYPE(vol7d) :: v7dtmp
10780LOGICAL :: lsort, lbestdata
10781INTEGER,POINTER :: remapt1(:), remapt2(:), remaptr1(:), remaptr2(:), &
10782 remapl1(:), remapl2(:), remapa1(:), remapa2(:), remapn1(:), remapn2(:)
10783
10784IF (.NOT.c_e(that)) RETURN ! speedup, nothing to do
10785IF (.NOT.vol7d_check_vol(that)) RETURN ! be safe
10786IF (.NOT.c_e(this)) THEN ! this case is like a vol7d_copy, more efficient to copy?
10787 CALL vol7d_copy(that, this, sort=sort)
10788 RETURN
10789ENDIF
10790
10791IF (this%time_definition /= that%time_definition) THEN
10792 CALL l4f_log(l4f_fatal, &
10793 'in vol7d_append, cannot append volumes with different &
10794 &time definition')
10795 CALL raise_fatal_error()
10796ENDIF
10797
10798! Completo l'allocazione per avere volumi a norma
10799CALL vol7d_alloc_vol(this)
10800
10801CALL init(v7dtmp, time_definition=this%time_definition)
10802CALL optio(sort, lsort)
10803CALL optio(bestdata, lbestdata)
10804
10805! Calcolo le mappature tra volumi vecchi e volume nuovo
10806! I puntatori remap* vengono tutti o allocati o nullificati
10807IF (optio_log(ltimesimple)) THEN
10808 CALL vol7d_remap2simple_datetime(this%time, that%time, v7dtmp%time, &
10809 lsort, remapt1, remapt2)
10810ELSE
10811 CALL vol7d_remap2_datetime(this%time, that%time, v7dtmp%time, &
10812 lsort, remapt1, remapt2)
10813ENDIF
10814IF (optio_log(ltimerangesimple)) THEN
10815 CALL vol7d_remap2simple_vol7d_timerange(this%timerange, that%timerange, &
10816 v7dtmp%timerange, lsort, remaptr1, remaptr2)
10817ELSE
10818 CALL vol7d_remap2_vol7d_timerange(this%timerange, that%timerange, &
10819 v7dtmp%timerange, lsort, remaptr1, remaptr2)
10820ENDIF
10821IF (optio_log(llevelsimple)) THEN
10822 CALL vol7d_remap2simple_vol7d_level(this%level, that%level, v7dtmp%level, &
10823 lsort, remapl1, remapl2)
10824ELSE
10825 CALL vol7d_remap2_vol7d_level(this%level, that%level, v7dtmp%level, &
10826 lsort, remapl1, remapl2)
10827ENDIF
10828IF (optio_log(lanasimple)) THEN
10829 CALL vol7d_remap2simple_vol7d_ana(this%ana, that%ana, v7dtmp%ana, &
10830 .false., remapa1, remapa2)
10831ELSE
10832 CALL vol7d_remap2_vol7d_ana(this%ana, that%ana, v7dtmp%ana, &
10833 .false., remapa1, remapa2)
10834ENDIF
10835IF (optio_log(lnetworksimple)) THEN
10836 CALL vol7d_remap2simple_vol7d_network(this%network, that%network, v7dtmp%network, &
10837 .false., remapn1, remapn2)
10838ELSE
10839 CALL vol7d_remap2_vol7d_network(this%network, that%network, v7dtmp%network, &
10840 .false., remapn1, remapn2)
10841ENDIF
10842
10843! Faccio la fusione fisica dei volumi
10844CALL vol7d_merge_finalr(this, that, v7dtmp, &
10845 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
10846 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
10847CALL vol7d_merge_finald(this, that, v7dtmp, &
10848 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
10849 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
10850CALL vol7d_merge_finali(this, that, v7dtmp, &
10851 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
10852 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
10853CALL vol7d_merge_finalb(this, that, v7dtmp, &
10854 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
10855 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
10856CALL vol7d_merge_finalc(this, that, v7dtmp, &
10857 remapa1, remapa2, remapt1, remapt2, remapl1, remapl2, &
10858 remaptr1, remaptr2, remapn1, remapn2, lbestdata)
10859
10860! Dealloco i vettori di rimappatura
10861IF (ASSOCIATED(remapt1)) DEALLOCATE(remapt1)
10862IF (ASSOCIATED(remapt2)) DEALLOCATE(remapt2)
10863IF (ASSOCIATED(remaptr1)) DEALLOCATE(remaptr1)
10864IF (ASSOCIATED(remaptr2)) DEALLOCATE(remaptr2)
10865IF (ASSOCIATED(remapl1)) DEALLOCATE(remapl1)
10866IF (ASSOCIATED(remapl2)) DEALLOCATE(remapl2)
10867IF (ASSOCIATED(remapa1)) DEALLOCATE(remapa1)
10868IF (ASSOCIATED(remapa2)) DEALLOCATE(remapa2)
10869IF (ASSOCIATED(remapn1)) DEALLOCATE(remapn1)
10870IF (ASSOCIATED(remapn2)) DEALLOCATE(remapn2)
10871
10872! Distruggo il vecchio volume e assegno il nuovo a this
10873CALL delete(this)
10874this = v7dtmp
10875! Ricreo gli indici var-attr
10876CALL vol7d_set_attr_ind(this)
10877
10878END SUBROUTINE vol7d_append
10879
10880
10881!> Metodo per creare una copia completa e indipendente di un oggetto vol7d.
10882!! Questo metodo crea un duplicato di tutti i membri di un oggetto vol7d,
10883!! con la possibilità di rielaborarlo durante la copia. Se l'oggetto da copiare
10884!! è vuoto non perde tempo inutile.
10885!! Attenzione, il codice:
10886!! \code
10887!! USE vol7d_class
10888!! TYPE(vol7d) :: vol1, vol2
10889!! CALL init(vol1)
10890!! CALL init(vol2)
10891!! ... ! riempio vol1
10892!! vol2 = vol1
10893!! \endcode
10894!! fa una cosa diversa rispetto a:
10895!! \code
10896!! USE vol7d_class
10897!! TYPE(vol7d) :: vol1, vol2
10898!! CALL init(vol1)
10899!! CALL init(vol2)
10900!! ... ! riempio vol1
10901!! CALL vol7d_copy(vol1, vol2)
10902!! \endcode
10903!! nel primo caso, infatti, l'operatore di assegnazione copia solo i componenti
10904!! statici di \a vol1 nei corrispondenti elementi di \a vol2, mentre i componenti che
10905!! sono allocati dinamicamente (cioè quelli che in ::vol7d hanno l'attributo
10906!! \c POINTER, in pratica quasi tutti) non vengono duplicati, ma per essi vol2
10907!! conterrà un puntatore al corrispondente elemento a cui già punta vol1, e quindi
10908!! eventuali cambiamenti al contenuto di uno dei due oggetti influenzerà il
10909!! contenuto dell'altro; nel secondo caso, invece, vol1 e vol2 sono, dopo la
10910!! vol7d_copy, 2 istanze
10911!! completamente indipendenti, ma uguali tra loro per contenuto, della classe
10912!! vol7d, e quindi hanno vita indipendente.
10913SUBROUTINE vol7d_copy(this, that, sort, unique, miss, &
10914 lsort_time, lsort_timerange, lsort_level, &
10915 ltime, ltimerange, llevel, lana, lnetwork, &
10916 lanavarr, lanavard, lanavari, lanavarb, lanavarc, &
10917 lanaattrr, lanaattrd, lanaattri, lanaattrb, lanaattrc, &
10918 lanavarattrr, lanavarattrd, lanavarattri, lanavarattrb, lanavarattrc, &
10919 ldativarr, ldativard, ldativari, ldativarb, ldativarc, &
10920 ldatiattrr, ldatiattrd, ldatiattri, ldatiattrb, ldatiattrc, &
10921 ldativarattrr, ldativarattrd, ldativarattri, ldativarattrb, ldativarattrc)
10922TYPE(vol7d),INTENT(IN) :: this !< oggetto origine
10923TYPE(vol7d),INTENT(INOUT) :: that !< oggetto destinazione
10924LOGICAL,INTENT(IN),OPTIONAL :: sort !< if present and \a .TRUE., sort all the sortable dimensions
10925LOGICAL,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)
10926LOGICAL,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
10927LOGICAL,INTENT(IN),OPTIONAL :: lsort_time !< if present and \a .TRUE., sort only time dimension (alternative to \a sort )
10928LOGICAL,INTENT(IN),OPTIONAL :: lsort_timerange !< if present and \a .TRUE., sort only timerange dimension (alternative to \a sort )
10929LOGICAL,INTENT(IN),OPTIONAL :: lsort_level !< if present and \a .TRUE., sort only level dimension (alternative to \a sort )
10930!> se fornito, deve essere un vettore logico della stessa lunghezza di
10931!! this%time indicante quali elementi della dimensione \a time
10932!! mantenere (valori \c .TRUE.) e quali scartare (valori \c .FALSE.)
10933!! nel volume copiato; in alternativa può essere un vettore di
10934!! lunghezza 1, in tal caso, se \c .FALSE. , equivale a scartare tutti
10935!! gli elementi (utile principalmente per le variabili); è compatibile
10936!! col parametro \a miss
10937LOGICAL,INTENT(IN),OPTIONAL :: ltime(:)
10938!> come il precedente per la dimensione \a timerange
10939LOGICAL,INTENT(IN),OPTIONAL :: ltimerange(:)
10940!> come il precedente per la dimensione \a level
10941LOGICAL,INTENT(IN),OPTIONAL :: llevel(:)
10942!> come il precedente per la dimensione \a ana
10943LOGICAL,INTENT(IN),OPTIONAL :: lana(:)
10944!> come il precedente per la dimensione \a network
10945LOGICAL,INTENT(IN),OPTIONAL :: lnetwork(:)
10946!> come il precedente per tutte le possibili dimensioni variabile
10947LOGICAL,INTENT(in),OPTIONAL :: &
10948 lanavarr(:), lanavard(:), lanavari(:), lanavarb(:), lanavarc(:), &
10949 lanaattrr(:), lanaattrd(:), lanaattri(:), lanaattrb(:), lanaattrc(:), &
10950 lanavarattrr(:), lanavarattrd(:), lanavarattri(:), lanavarattrb(:), lanavarattrc(:), &
10951 ldativarr(:), ldativard(:), ldativari(:), ldativarb(:), ldativarc(:), &
10952 ldatiattrr(:), ldatiattrd(:), ldatiattri(:), ldatiattrb(:), ldatiattrc(:), &
10953 ldativarattrr(:), ldativarattrd(:), ldativarattri(:), ldativarattrb(:), ldativarattrc(:)
10954
10955LOGICAL :: lsort, lunique, lmiss
10956INTEGER,POINTER :: remapt(:), remaptr(:), remapl(:), remapa(:), remapn(:)
10957
10958CALL init(that)
10959IF (.NOT.c_e(this)) RETURN ! speedup, nothing to do
10960IF (.NOT.vol7d_check_vol(this)) RETURN ! be safe
10961
10962CALL optio(sort, lsort)
10963CALL optio(unique, lunique)
10964CALL optio(miss, lmiss)
10965
10966! Calcolo le mappature tra volume vecchio e volume nuovo
10967! I puntatori remap* vengono tutti o allocati o nullificati
10968CALL vol7d_remap1_datetime(this%time, that%time, &
10969 lsort.OR.optio_log(lsort_time), lunique, lmiss, remapt, ltime)
10970CALL vol7d_remap1_vol7d_timerange(this%timerange, that%timerange, &
10971 lsort.OR.optio_log(lsort_timerange), lunique, lmiss, remaptr, ltimerange)
10972CALL vol7d_remap1_vol7d_level(this%level, that%level, &
10973 lsort.OR.optio_log(lsort_level), lunique, lmiss, remapl, llevel)
10974CALL vol7d_remap1_vol7d_ana(this%ana, that%ana, &
10975 lsort, lunique, lmiss, remapa, lana)
10976CALL vol7d_remap1_vol7d_network(this%network, that%network, &
10977 lsort, lunique, lmiss, remapn, lnetwork)
10978
10979! lanavari, lanavarb, lanavarc, &
10980! lanaattri, lanaattrb, lanaattrc, &
10981! lanavarattri, lanavarattrb, lanavarattrc, &
10982! ldativari, ldativarb, ldativarc, &
10983! ldatiattri, ldatiattrb, ldatiattrc, &
10984! ldativarattri, ldativarattrb, ldativarattrc
10985! Faccio la riforma fisica dei volumi
10986CALL vol7d_reform_finalr(this, that, &
10987 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
10988 lanavarr, lanaattrr, lanavarattrr, ldativarr, ldatiattrr, ldativarattrr)
10989CALL vol7d_reform_finald(this, that, &
10990 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
10991 lanavard, lanaattrd, lanavarattrd, ldativard, ldatiattrd, ldativarattrd)
10992CALL vol7d_reform_finali(this, that, &
10993 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
10994 lanavari, lanaattri, lanavarattri, ldativari, ldatiattri, ldativarattri)
10995CALL vol7d_reform_finalb(this, that, &
10996 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
10997 lanavarb, lanaattrb, lanavarattrb, ldativarb, ldatiattrb, ldativarattrb)
10998CALL vol7d_reform_finalc(this, that, &
10999 remapa, remapt, remapl, remaptr, remapn, lsort, lunique, lmiss, &
11000 lanavarc, lanaattrc, lanavarattrc, ldativarc, ldatiattrc, ldativarattrc)
11001
11002! Dealloco i vettori di rimappatura
11003IF (ASSOCIATED(remapt)) DEALLOCATE(remapt)
11004IF (ASSOCIATED(remaptr)) DEALLOCATE(remaptr)
11005IF (ASSOCIATED(remapl)) DEALLOCATE(remapl)
11006IF (ASSOCIATED(remapa)) DEALLOCATE(remapa)
11007IF (ASSOCIATED(remapn)) DEALLOCATE(remapn)
11008
11009! Ricreo gli indici var-attr
11010CALL vol7d_set_attr_ind(that)
11011that%time_definition = this%time_definition
11012
11013END SUBROUTINE vol7d_copy
11014
11015
11016!> Metodo per riformare in varie maniere un oggetto vol7d.
11017!! Equivale ad una copia (vedi ::vol7d_copy)
11018!! seguita dalla distruzione del volume iniziale e alla
11019!! sua riassegnazione al volume copiato. Ha senso se almeno uno dei parametri
11020!! \a sort, \a uniq o \a miss è fornito uguale a \c .TRUE., altrimenti
11021!! è solo una perdita di tempo.
11022!! Può essere utile, ad esempio, per eliminare stazioni
11023!! o istanti temporali indesiderati, basta assegnare il loro corrispondente
11024!! elemento del descrittore a valore mancante e chiamare vol7d_reform
11025!! con miss=.TRUE. .
11026SUBROUTINE vol7d_reform(this, sort, unique, miss, &
11027 lsort_time, lsort_timerange, lsort_level, &
11028 ltime, ltimerange, llevel, lana, lnetwork, &
11029 lanavarr, lanavard, lanavari, lanavarb, lanavarc, &
11030 lanaattrr, lanaattrd, lanaattri, lanaattrb, lanaattrc, &
11031 lanavarattrr, lanavarattrd, lanavarattri, lanavarattrb, lanavarattrc, &
11032 ldativarr, ldativard, ldativari, ldativarb, ldativarc, &
11033 ldatiattrr, ldatiattrd, ldatiattri, ldatiattrb, ldatiattrc, &
11034 ldativarattrr, ldativarattrd, ldativarattri, ldativarattrb, ldativarattrc&
11035 ,purgeana)
11036TYPE(vol7d),INTENT(INOUT) :: this !< oggetto da riformare
11037LOGICAL,INTENT(IN),OPTIONAL :: sort !< if present and \a .TRUE., sort all the sortable dimensions
11038LOGICAL,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)
11039LOGICAL,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
11040LOGICAL,INTENT(IN),OPTIONAL :: lsort_time !< if present and \a .TRUE., sort only time dimension (alternative to \a sort )
11041LOGICAL,INTENT(IN),OPTIONAL :: lsort_timerange !< if present and \a .TRUE., sort only timerange dimension (alternative to \a sort )
11042LOGICAL,INTENT(IN),OPTIONAL :: lsort_level !< if present and \a .TRUE., sort only level dimension (alternative to \a sort )
11043!> se fornito, deve essere un vettore logico della stessa lunghezza di
11044!! this%time indicante quali elementi della dimensione \a time
11045!! mantenere (valori \c .TRUE.) e quali scartare (valori \c .FALSE.)
11046!! nel volume copiato; in alternativa può essere un vettore di
11047!! lunghezza 1, in tal caso, se \c .FALSE. , equivale a scartare tutti
11048!! gli elementi (utile principalmente per le variabili); è compatibile
11049!! col parametro \a miss
11050LOGICAL,INTENT(IN),OPTIONAL :: ltime(:)
11051LOGICAL,INTENT(IN),OPTIONAL :: ltimerange(:) !< come il precedente per la dimensione \a timerange
11052LOGICAL,INTENT(IN),OPTIONAL :: llevel(:) !< come il precedente per la dimensione \a level
11053LOGICAL,INTENT(IN),OPTIONAL :: lana(:) !< come il precedente per la dimensione \a ana
11054LOGICAL,INTENT(IN),OPTIONAL :: lnetwork(:) !< come il precedente per la dimensione \a network
11055!> come il precedente per tutte le possibili dimensioni variabile
11056LOGICAL,INTENT(in),OPTIONAL :: &
11057 lanavarr(:), lanavard(:), lanavari(:), lanavarb(:), lanavarc(:), &
11058 lanaattrr(:), lanaattrd(:), lanaattri(:), lanaattrb(:), lanaattrc(:), &
11059 lanavarattrr(:), lanavarattrd(:), lanavarattri(:), lanavarattrb(:), lanavarattrc(:), &
11060 ldativarr(:), ldativard(:), ldativari(:), ldativarb(:), ldativarc(:), &
11061 ldatiattrr(:), ldatiattrd(:), ldatiattri(:), ldatiattrb(:), ldatiattrc(:), &
11062 ldativarattrr(:), ldativarattrd(:), ldativarattri(:), ldativarattrb(:), ldativarattrc(:)
11063LOGICAL,INTENT(IN),OPTIONAL :: purgeana !< if true remove ana with all data missing
11064
11065TYPE(vol7d) :: v7dtmp
11066logical,allocatable :: llana(:)
11067integer :: i
11068
11069CALL vol7d_copy(this, v7dtmp, sort, unique, miss, &
11070 lsort_time, lsort_timerange, lsort_level, &
11071 ltime, ltimerange, llevel, lana, lnetwork, &
11072 lanavarr, lanavard, lanavari, lanavarb, lanavarc, &
11073 lanaattrr, lanaattrd, lanaattri, lanaattrb, lanaattrc, &
11074 lanavarattrr, lanavarattrd, lanavarattri, lanavarattrb, lanavarattrc, &
11075 ldativarr, ldativard, ldativari, ldativarb, ldativarc, &
11076 ldatiattrr, ldatiattrd, ldatiattri, ldatiattrb, ldatiattrc, &
11077 ldativarattrr, ldativarattrd, ldativarattri, ldativarattrb, ldativarattrc)
11078
11079! destroy old volume
11080CALL delete(this)
11081
11082if (optio_log(purgeana)) then
11083 allocate(llana(size(v7dtmp%ana)))
11084 llana =.false.
11085 do i =1,size(v7dtmp%ana)
11086 if (associated(v7dtmp%voldatii)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatii(i,:,:,:,:,:)))
11087 if (associated(v7dtmp%voldatir)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatir(i,:,:,:,:,:)))
11088 if (associated(v7dtmp%voldatid)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatid(i,:,:,:,:,:)))
11089 if (associated(v7dtmp%voldatib)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatib(i,:,:,:,:,:)))
11090 if (associated(v7dtmp%voldatic)) llana(i)= llana(i) .or. any(c_e(v7dtmp%voldatic(i,:,:,:,:,:)))
11091 end do
11092 CALL vol7d_copy(v7dtmp, this,lana=llana)
11093 CALL delete(v7dtmp)
11094 deallocate(llana)
11095else
11096 this=v7dtmp
11097end if
11098
11099END SUBROUTINE vol7d_reform
11100
11101
11102!> Sorts the sortable dimensions in the volume \a this only when necessary.
11103!! Most of the times, the time, timerange and level dimensions in a
11104!! vol7d object are correctly sorted; on the other side many methods
11105!! strictly rely on this fact in order to work correctly. This method
11106!! performs a quick check and sorts the required dimensions only if
11107!! they are not sorted in ascending order yet, improving safety
11108!! without impairing much performance.
11109SUBROUTINE vol7d_smart_sort(this, lsort_time, lsort_timerange, lsort_level)
11110TYPE(vol7d),INTENT(INOUT) :: this !< object to be sorted
11111LOGICAL,OPTIONAL,INTENT(in) :: lsort_time !< if present and \a .TRUE., sort time dimension if it is not sorted in ascending order
11112LOGICAL,OPTIONAL,INTENT(in) :: lsort_timerange !< if present and \a .TRUE., sort timerange dimension if it is not sorted in ascending order
11113LOGICAL,OPTIONAL,INTENT(in) :: lsort_level !< if present and \a .TRUE., sort vertical level dimension if it is not sorted in ascending order
11114
11115INTEGER :: i
11116LOGICAL :: to_be_sorted
11117
11118to_be_sorted = .false.
11119CALL vol7d_alloc_vol(this) ! usual safety check
11120
11121IF (optio_log(lsort_time)) THEN
11122 DO i = 2, SIZE(this%time)
11123 IF (this%time(i) < this%time(i-1)) THEN
11124 to_be_sorted = .true.
11125 EXIT
11126 ENDIF
11127 ENDDO
11128ENDIF
11129IF (optio_log(lsort_timerange)) THEN
11130 DO i = 2, SIZE(this%timerange)
11131 IF (this%timerange(i) < this%timerange(i-1)) THEN
11132 to_be_sorted = .true.
11133 EXIT
11134 ENDIF
11135 ENDDO
11136ENDIF
11137IF (optio_log(lsort_level)) THEN
11138 DO i = 2, SIZE(this%level)
11139 IF (this%level(i) < this%level(i-1)) THEN
11140 to_be_sorted = .true.
11141 EXIT
11142 ENDIF
11143 ENDDO
11144ENDIF
11145
11146IF (to_be_sorted) CALL vol7d_reform(this, &
11147 lsort_time=lsort_time, lsort_timerange=lsort_timerange, lsort_level=lsort_level )
11148
11149END SUBROUTINE vol7d_smart_sort
11150
11151!> Filter the contents of a volume keeping only desired data.
11152!! This subroutine filters a vol7d object by keeping only a subset of
11153!! the data contained. It can keep only times within a specified
11154!! interval, only station networks contained in a list and only
11155!! specified station or data variables. If a filter parameter is not
11156!! provided, no filtering will take place according to that criterion.
11157!! The volume is reallocated keeping only the desired data.
11158SUBROUTINE vol7d_filter(this, avl, vl, nl, s_d, e_d)
11159TYPE(vol7d),INTENT(inout) :: this !< volume to be filtered
11160CHARACTER(len=*),INTENT(in),OPTIONAL :: avl(:) !< list of station variables to be kept, if not provided or of zero length, all variables are kept
11161CHARACTER(len=*),INTENT(in),OPTIONAL :: vl(:) !< list of data variables to be kept, if not provided or of zero length, all variables are kept
11162TYPE(vol7d_network),OPTIONAL :: nl(:) !< list of station networks to be kept, if not provided or of zero length, all networks are kept
11163TYPE(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
11164TYPE(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
11165
11166INTEGER :: i
11167
11168IF (PRESENT(avl)) THEN
11169 IF (SIZE(avl) > 0) THEN
11170
11171 IF (ASSOCIATED(this%anavar%r)) THEN
11172 DO i = 1, SIZE(this%anavar%r)
11173 IF (all(this%anavar%r(i)%btable /= avl)) this%anavar%r(i) = vol7d_var_miss
11174 ENDDO
11175 ENDIF
11176
11177 IF (ASSOCIATED(this%anavar%i)) THEN
11178 DO i = 1, SIZE(this%anavar%i)
11179 IF (all(this%anavar%i(i)%btable /= avl)) this%anavar%i(i) = vol7d_var_miss
11180 ENDDO
11181 ENDIF
11182
11183 IF (ASSOCIATED(this%anavar%b)) THEN
11184 DO i = 1, SIZE(this%anavar%b)
11185 IF (all(this%anavar%b(i)%btable /= avl)) this%anavar%b(i) = vol7d_var_miss
11186 ENDDO
11187 ENDIF
11188
11189 IF (ASSOCIATED(this%anavar%d)) THEN
11190 DO i = 1, SIZE(this%anavar%d)
11191 IF (all(this%anavar%d(i)%btable /= avl)) this%anavar%d(i) = vol7d_var_miss
11192 ENDDO
11193 ENDIF
11194
11195 IF (ASSOCIATED(this%anavar%c)) THEN
11196 DO i = 1, SIZE(this%anavar%c)
11197 IF (all(this%anavar%c(i)%btable /= avl)) this%anavar%c(i) = vol7d_var_miss
11198 ENDDO
11199 ENDIF
11200
11201 ENDIF
11202ENDIF
11203
11204
11205IF (PRESENT(vl)) THEN
11206 IF (size(vl) > 0) THEN
11207 IF (ASSOCIATED(this%dativar%r)) THEN
11208 DO i = 1, SIZE(this%dativar%r)
11209 IF (all(this%dativar%r(i)%btable /= vl)) this%dativar%r(i) = vol7d_var_miss
11210 ENDDO
11211 ENDIF
11212
11213 IF (ASSOCIATED(this%dativar%i)) THEN
11214 DO i = 1, SIZE(this%dativar%i)
11215 IF (all(this%dativar%i(i)%btable /= vl)) this%dativar%i(i) = vol7d_var_miss
11216 ENDDO
11217 ENDIF
11218
11219 IF (ASSOCIATED(this%dativar%b)) THEN
11220 DO i = 1, SIZE(this%dativar%b)
11221 IF (all(this%dativar%b(i)%btable /= vl)) this%dativar%b(i) = vol7d_var_miss
11222 ENDDO
11223 ENDIF
11224
11225 IF (ASSOCIATED(this%dativar%d)) THEN
11226 DO i = 1, SIZE(this%dativar%d)
11227 IF (all(this%dativar%d(i)%btable /= vl)) this%dativar%d(i) = vol7d_var_miss
11228 ENDDO
11229 ENDIF
11230
11231 IF (ASSOCIATED(this%dativar%c)) THEN
11232 DO i = 1, SIZE(this%dativar%c)
11233 IF (all(this%dativar%c(i)%btable /= vl)) this%dativar%c(i) = vol7d_var_miss
11234 ENDDO
11235 ENDIF
11236
11237 IF (ASSOCIATED(this%dativar%c)) THEN
11238 DO i = 1, SIZE(this%dativar%c)
11239 IF (all(this%dativar%c(i)%btable /= vl)) this%dativar%c(i) = vol7d_var_miss
11240 ENDDO
11241 ENDIF
11242
11243 ENDIF
11244ENDIF
11245
11246IF (PRESENT(nl)) THEN
11247 IF (SIZE(nl) > 0) THEN
11248 DO i = 1, SIZE(this%network)
11249 IF (all(this%network(i) /= nl)) this%network(i) = vol7d_network_miss
11250 ENDDO
11251 ENDIF
11252ENDIF
11253
11254IF (PRESENT(s_d)) THEN
11255 IF (c_e(s_d)) THEN
11256 WHERE (this%time < s_d)
11257 this%time = datetime_miss
11258 END WHERE
11259 ENDIF
11260ENDIF
11261
11262IF (PRESENT(e_d)) THEN
11263 IF (c_e(e_d)) THEN
11264 WHERE (this%time > e_d)
11265 this%time = datetime_miss
11266 END WHERE
11267 ENDIF
11268ENDIF
11269
11270CALL vol7d_reform(this, miss=.true.)
11271
11272END SUBROUTINE vol7d_filter
11273
11274
11275!> Metodo per convertire i volumi di dati di un oggetto vol7d in dati
11276!! reali dove possibile. L'oggetto convertito è una copia completa
11277!! dell'originale che può essere quindi distrutto dopo la chiamata.
11278!! Per i dati di anagrafica, al momento sono convertiti solo
11279!! i dati CHARACTER se è passato \a anaconv=.TRUE.
11280!! Gli attributi non sono toccati.
11281SUBROUTINE vol7d_convr(this, that, anaconv)
11282TYPE(vol7d),INTENT(IN) :: this !< oggetto origine
11283TYPE(vol7d),INTENT(INOUT) :: that !< oggetto convertito
11284LOGICAL,OPTIONAL,INTENT(in) :: anaconv !< converti anche anagrafica
11285INTEGER :: i
11286LOGICAL :: fv(1)=(/.false./), tv(1)=(/.true./), acp(1), acn(1)
11287TYPE(vol7d) :: v7d_tmp
11288
11289IF (optio_log(anaconv)) THEN
11290 acp=fv
11291 acn=tv
11292ELSE
11293 acp=tv
11294 acn=fv
11295ENDIF
11296
11297! Volume con solo i dati reali e tutti gli attributi
11298! l'anagrafica e` copiata interamente se necessario
11299CALL vol7d_copy(this, that, &
11300 lanavarr=tv, lanavard=acp, lanavari=acp, lanavarb=acp, lanavarc=acp, &
11301 ldativarr=tv, ldativard=fv, ldativari=fv, ldativarb=fv, ldativarc=fv)
11302
11303! Volume solo di dati double
11304CALL vol7d_copy(this, v7d_tmp, &
11305 lanavarr=fv, lanavard=acn, lanavari=fv, lanavarb=fv, lanavarc=fv, &
11306 lanaattrr=fv, lanaattrd=fv, lanaattri=fv, lanaattrb=fv, lanaattrc=fv, &
11307 lanavarattrr=fv, lanavarattrd=fv, lanavarattri=fv, lanavarattrb=fv, lanavarattrc=fv, &
11308 ldativarr=fv, ldativard=tv, ldativari=fv, ldativarb=fv, ldativarc=fv, &
11309 ldatiattrr=fv, ldatiattrd=fv, ldatiattri=fv, ldatiattrb=fv, ldatiattrc=fv, &
11310 ldativarattrr=fv, ldativarattrd=fv, ldativarattri=fv, ldativarattrb=fv, ldativarattrc=fv)
11311
11312! converto a dati reali
11313IF (ASSOCIATED(v7d_tmp%anavar%d) .OR. ASSOCIATED(v7d_tmp%dativar%d)) THEN
11314
11315 IF (ASSOCIATED(v7d_tmp%anavar%d)) THEN
11316! alloco i dati reali e vi trasferisco i double
11317 ALLOCATE(v7d_tmp%volanar(SIZE(v7d_tmp%volanad, 1), SIZE(v7d_tmp%volanad, 2), &
11318 SIZE(v7d_tmp%volanad, 3)))
11319 DO i = 1, SIZE(v7d_tmp%anavar%d)
11320 v7d_tmp%volanar(:,i,:) = &
11321 realdat(v7d_tmp%volanad(:,i,:), v7d_tmp%anavar%d(i))
11322 ENDDO
11323 DEALLOCATE(v7d_tmp%volanad)
11324! trasferisco le variabili
11325 v7d_tmp%anavar%r => v7d_tmp%anavar%d
11326 NULLIFY(v7d_tmp%anavar%d)
11327 ENDIF
11328
11329 IF (ASSOCIATED(v7d_tmp%dativar%d)) THEN
11330! alloco i dati reali e vi trasferisco i double
11331 ALLOCATE(v7d_tmp%voldatir(SIZE(v7d_tmp%voldatid, 1), SIZE(v7d_tmp%voldatid, 2), &
11332 SIZE(v7d_tmp%voldatid, 3), SIZE(v7d_tmp%voldatid, 4), SIZE(v7d_tmp%voldatid, 5), &
11333 SIZE(v7d_tmp%voldatid, 6)))
11334 DO i = 1, SIZE(v7d_tmp%dativar%d)
11335 v7d_tmp%voldatir(:,:,:,:,i,:) = &
11336 realdat(v7d_tmp%voldatid(:,:,:,:,i,:), v7d_tmp%dativar%d(i))
11337 ENDDO
11338 DEALLOCATE(v7d_tmp%voldatid)
11339! trasferisco le variabili
11340 v7d_tmp%dativar%r => v7d_tmp%dativar%d
11341 NULLIFY(v7d_tmp%dativar%d)
11342 ENDIF
11343
11344! fondo con il volume definitivo
11345 CALL vol7d_merge(that, v7d_tmp)
11346ELSE
11347 CALL delete(v7d_tmp)
11348ENDIF
11349
11350
11351! Volume solo di dati interi
11352CALL vol7d_copy(this, v7d_tmp, &
11353 lanavarr=fv, lanavard=fv, lanavari=acn, lanavarb=fv, lanavarc=fv, &
11354 lanaattrr=fv, lanaattrd=fv, lanaattri=fv, lanaattrb=fv, lanaattrc=fv, &
11355 lanavarattrr=fv, lanavarattrd=fv, lanavarattri=fv, lanavarattrb=fv, lanavarattrc=fv, &
11356 ldativarr=fv, ldativard=fv, ldativari=tv, ldativarb=fv, ldativarc=fv, &
11357 ldatiattrr=fv, ldatiattrd=fv, ldatiattri=fv, ldatiattrb=fv, ldatiattrc=fv, &
11358 ldativarattrr=fv, ldativarattrd=fv, ldativarattri=fv, ldativarattrb=fv, ldativarattrc=fv)
11359
11360! converto a dati reali
11361IF (ASSOCIATED(v7d_tmp%anavar%i) .OR. ASSOCIATED(v7d_tmp%dativar%i)) THEN
11362
11363 IF (ASSOCIATED(v7d_tmp%anavar%i)) THEN
11364! alloco i dati reali e vi trasferisco gli interi
11365 ALLOCATE(v7d_tmp%volanar(SIZE(v7d_tmp%volanai, 1), SIZE(v7d_tmp%volanai, 2), &
11366 SIZE(v7d_tmp%volanai, 3)))
11367 DO i = 1, SIZE(v7d_tmp%anavar%i)
11368 v7d_tmp%volanar(:,i,:) = &
11369 realdat(v7d_tmp%volanai(:,i,:), v7d_tmp%anavar%i(i))
11370 ENDDO
11371 DEALLOCATE(v7d_tmp%volanai)
11372! trasferisco le variabili
11373 v7d_tmp%anavar%r => v7d_tmp%anavar%i
11374 NULLIFY(v7d_tmp%anavar%i)
11375 ENDIF
11376
11377 IF (ASSOCIATED(v7d_tmp%dativar%i)) THEN
11378! alloco i dati reali e vi trasferisco gli interi
11379 ALLOCATE(v7d_tmp%voldatir(SIZE(v7d_tmp%voldatii, 1), SIZE(v7d_tmp%voldatii, 2), &
11380 SIZE(v7d_tmp%voldatii, 3), SIZE(v7d_tmp%voldatii, 4), SIZE(v7d_tmp%voldatii, 5), &
11381 SIZE(v7d_tmp%voldatii, 6)))
11382 DO i = 1, SIZE(v7d_tmp%dativar%i)
11383 v7d_tmp%voldatir(:,:,:,:,i,:) = &
11384 realdat(v7d_tmp%voldatii(:,:,:,:,i,:), v7d_tmp%dativar%i(i))
11385 ENDDO
11386 DEALLOCATE(v7d_tmp%voldatii)
11387! trasferisco le variabili
11388 v7d_tmp%dativar%r => v7d_tmp%dativar%i
11389 NULLIFY(v7d_tmp%dativar%i)
11390 ENDIF
11391
11392! fondo con il volume definitivo
11393 CALL vol7d_merge(that, v7d_tmp)
11394ELSE
11395 CALL delete(v7d_tmp)
11396ENDIF
11397
11398
11399! Volume solo di dati byte
11400CALL vol7d_copy(this, v7d_tmp, &
11401 lanavarr=fv, lanavard=fv, lanavari=fv, lanavarb=acn, lanavarc=fv, &
11402 lanaattrr=fv, lanaattrd=fv, lanaattri=fv, lanaattrb=fv, lanaattrc=fv, &
11403 lanavarattrr=fv, lanavarattrd=fv, lanavarattri=fv, lanavarattrb=fv, lanavarattrc=fv, &
11404 ldativarr=fv, ldativard=fv, ldativari=fv, ldativarb=tv, ldativarc=fv, &
11405 ldatiattrr=fv, ldatiattrd=fv, ldatiattri=fv, ldatiattrb=fv, ldatiattrc=fv, &
11406 ldativarattrr=fv, ldativarattrd=fv, ldativarattri=fv, ldativarattrb=fv, ldativarattrc=fv)
11407
11408! converto a dati reali
11409IF (ASSOCIATED(v7d_tmp%anavar%b) .OR. ASSOCIATED(v7d_tmp%dativar%b)) THEN
11410
11411 IF (ASSOCIATED(v7d_tmp%anavar%b)) THEN
11412! alloco i dati reali e vi trasferisco i byte
11413 ALLOCATE(v7d_tmp%volanar(SIZE(v7d_tmp%volanab, 1), SIZE(v7d_tmp%volanab, 2), &
11414 SIZE(v7d_tmp%volanab, 3)))
11415 DO i = 1, SIZE(v7d_tmp%anavar%b)
11416 v7d_tmp%volanar(:,i,:) = &
11417 realdat(v7d_tmp%volanab(:,i,:), v7d_tmp%anavar%b(i))
11418 ENDDO
11419 DEALLOCATE(v7d_tmp%volanab)
11420! trasferisco le variabili
11421 v7d_tmp%anavar%r => v7d_tmp%anavar%b
11422 NULLIFY(v7d_tmp%anavar%b)
11423 ENDIF
11424
11425 IF (ASSOCIATED(v7d_tmp%dativar%b)) THEN
11426! alloco i dati reali e vi trasferisco i byte
11427 ALLOCATE(v7d_tmp%voldatir(SIZE(v7d_tmp%voldatib, 1), SIZE(v7d_tmp%voldatib, 2), &
11428 SIZE(v7d_tmp%voldatib, 3), SIZE(v7d_tmp%voldatib, 4), SIZE(v7d_tmp%voldatib, 5), &
11429 SIZE(v7d_tmp%voldatib, 6)))
11430 DO i = 1, SIZE(v7d_tmp%dativar%b)
11431 v7d_tmp%voldatir(:,:,:,:,i,:) = &
11432 realdat(v7d_tmp%voldatib(:,:,:,:,i,:), v7d_tmp%dativar%b(i))
11433 ENDDO
11434 DEALLOCATE(v7d_tmp%voldatib)
11435! trasferisco le variabili
11436 v7d_tmp%dativar%r => v7d_tmp%dativar%b
11437 NULLIFY(v7d_tmp%dativar%b)
11438 ENDIF
11439
11440! fondo con il volume definitivo
11441 CALL vol7d_merge(that, v7d_tmp)
11442ELSE
11443 CALL delete(v7d_tmp)
11444ENDIF
11445
11446
11447! Volume solo di dati character
11448CALL vol7d_copy(this, v7d_tmp, &
11449 lanavarr=fv, lanavard=fv, lanavari=fv, lanavarb=fv, lanavarc=acn, &
11450 lanaattrr=fv, lanaattrd=fv, lanaattri=fv, lanaattrb=fv, lanaattrc=fv, &
11451 lanavarattrr=fv, lanavarattrd=fv, lanavarattri=fv, lanavarattrb=fv, lanavarattrc=fv, &
11452 ldativarr=fv, ldativard=fv, ldativari=fv, ldativarb=fv, ldativarc=tv, &
11453 ldatiattrr=fv, ldatiattrd=fv, ldatiattri=fv, ldatiattrb=fv, ldatiattrc=fv, &
11454 ldativarattrr=fv, ldativarattrd=fv, ldativarattri=fv, ldativarattrb=fv, ldativarattrc=fv)
11455
11456! converto a dati reali
11457IF (ASSOCIATED(v7d_tmp%anavar%c) .OR. ASSOCIATED(v7d_tmp%dativar%c)) THEN
11458
11459 IF (ASSOCIATED(v7d_tmp%anavar%c)) THEN
11460! alloco i dati reali e vi trasferisco i character
11461 ALLOCATE(v7d_tmp%volanar(SIZE(v7d_tmp%volanac, 1), SIZE(v7d_tmp%volanac, 2), &
11462 SIZE(v7d_tmp%volanac, 3)))
11463 DO i = 1, SIZE(v7d_tmp%anavar%c)
11464 v7d_tmp%volanar(:,i,:) = &
11465 realdat(v7d_tmp%volanac(:,i,:), v7d_tmp%anavar%c(i))
11466 ENDDO
11467 DEALLOCATE(v7d_tmp%volanac)
11468! trasferisco le variabili
11469 v7d_tmp%anavar%r => v7d_tmp%anavar%c
11470 NULLIFY(v7d_tmp%anavar%c)
11471 ENDIF
11472
11473 IF (ASSOCIATED(v7d_tmp%dativar%c)) THEN
11474! alloco i dati reali e vi trasferisco i character
11475 ALLOCATE(v7d_tmp%voldatir(SIZE(v7d_tmp%voldatic, 1), SIZE(v7d_tmp%voldatic, 2), &
11476 SIZE(v7d_tmp%voldatic, 3), SIZE(v7d_tmp%voldatic, 4), SIZE(v7d_tmp%voldatic, 5), &
11477 SIZE(v7d_tmp%voldatic, 6)))
11478 DO i = 1, SIZE(v7d_tmp%dativar%c)
11479 v7d_tmp%voldatir(:,:,:,:,i,:) = &
11480 realdat(v7d_tmp%voldatic(:,:,:,:,i,:), v7d_tmp%dativar%c(i))
11481 ENDDO
11482 DEALLOCATE(v7d_tmp%voldatic)
11483! trasferisco le variabili
11484 v7d_tmp%dativar%r => v7d_tmp%dativar%c
11485 NULLIFY(v7d_tmp%dativar%c)
11486 ENDIF
11487
11488! fondo con il volume definitivo
11489 CALL vol7d_merge(that, v7d_tmp)
11490ELSE
11491 CALL delete(v7d_tmp)
11492ENDIF
11493
11494END SUBROUTINE vol7d_convr
11495
11496
11497!> Metodo per ottenere solo le differenze tra due oggetti vol7d.
11498!! Il primo volume viene confrontato col secondo; nel secondo volume ovunque
11499!! i dati confrontati siano coincidenti viene impostato valore mancante.
11500SUBROUTINE vol7d_diff_only (this, that, data_only,ana)
11501TYPE(vol7d),INTENT(IN) :: this !< primo volume da confrontare
11502TYPE(vol7d),INTENT(OUT) :: that !< secondo volume da confrontare in cui eliminare i dati coincidenti
11503logical , optional, intent(in) :: data_only !< attiva l'elaborazione dei soli dati e non dell'anagrafica (default: .false.)
11504logical , optional, intent(in) :: ana !< attiva l'elaborazione dell'anagrafica (coordinate e ident) (default: .false.)
11505logical :: ldata_only,lana
11506
11507IF (PRESENT(data_only)) THEN
11508 ldata_only = data_only
11509ELSE
11510 ldata_only = .false.
11511ENDIF
11512
11513IF (PRESENT(ana)) THEN
11514 lana = ana
11515ELSE
11516 lana = .false.
11517ENDIF
11518
11519
11520#undef VOL7D_POLY_ARRAY
11521#define VOL7D_POLY_ARRAY voldati
11522#include "vol7d_class_diff.F90"
11523#undef VOL7D_POLY_ARRAY
11524#define VOL7D_POLY_ARRAY voldatiattr
11525#include "vol7d_class_diff.F90"
11526#undef VOL7D_POLY_ARRAY
11527
11528if ( .not. ldata_only) then
11529
11530#define VOL7D_POLY_ARRAY volana
11531#include "vol7d_class_diff.F90"
11532#undef VOL7D_POLY_ARRAY
11533#define VOL7D_POLY_ARRAY volanaattr
11534#include "vol7d_class_diff.F90"
11535#undef VOL7D_POLY_ARRAY
11536
11537 if(lana)then
11538 where ( this%ana == that%ana )
11539 that%ana = vol7d_ana_miss
11540 end where
11541 end if
11542
11543end if
11544
11545
11546
11547END SUBROUTINE vol7d_diff_only
11548
11549
11550
11551! Creo le routine da ripetere per i vari tipi di dati di v7d
11552! tramite un template e il preprocessore
11553#undef VOL7D_POLY_TYPE
11554#undef VOL7D_POLY_TYPES
11555#define VOL7D_POLY_TYPE REAL
11556#define VOL7D_POLY_TYPES r
11557#include "vol7d_class_type_templ.F90"
11558#undef VOL7D_POLY_TYPE
11559#undef VOL7D_POLY_TYPES
11560#define VOL7D_POLY_TYPE DOUBLE PRECISION
11561#define VOL7D_POLY_TYPES d
11562#include "vol7d_class_type_templ.F90"
11563#undef VOL7D_POLY_TYPE
11564#undef VOL7D_POLY_TYPES
11565#define VOL7D_POLY_TYPE INTEGER
11566#define VOL7D_POLY_TYPES i
11567#include "vol7d_class_type_templ.F90"
11568#undef VOL7D_POLY_TYPE
11569#undef VOL7D_POLY_TYPES
11570#define VOL7D_POLY_TYPE INTEGER(kind=int_b)
11571#define VOL7D_POLY_TYPES b
11572#include "vol7d_class_type_templ.F90"
11573#undef VOL7D_POLY_TYPE
11574#undef VOL7D_POLY_TYPES
11575#define VOL7D_POLY_TYPE CHARACTER(len=vol7d_cdatalen)
11576#define VOL7D_POLY_TYPES c
11577#include "vol7d_class_type_templ.F90"
11578
11579! Creo le routine da ripetere per i vari descrittori di dimensioni di v7d
11580! tramite un template e il preprocessore
11581#define VOL7D_SORT
11582#undef VOL7D_NO_ZERO_ALLOC
11583#undef VOL7D_POLY_TYPE
11584#define VOL7D_POLY_TYPE datetime
11585#include "vol7d_class_desc_templ.F90"
11586#undef VOL7D_POLY_TYPE
11587#define VOL7D_POLY_TYPE vol7d_timerange
11588#include "vol7d_class_desc_templ.F90"
11589#undef VOL7D_POLY_TYPE
11590#define VOL7D_POLY_TYPE vol7d_level
11591#include "vol7d_class_desc_templ.F90"
11592#undef VOL7D_SORT
11593#undef VOL7D_POLY_TYPE
11594#define VOL7D_POLY_TYPE vol7d_network
11595#include "vol7d_class_desc_templ.F90"
11596#undef VOL7D_POLY_TYPE
11597#define VOL7D_POLY_TYPE vol7d_ana
11598#include "vol7d_class_desc_templ.F90"
11599#define VOL7D_NO_ZERO_ALLOC
11600#undef VOL7D_POLY_TYPE
11601#define VOL7D_POLY_TYPE vol7d_var
11602#include "vol7d_class_desc_templ.F90"
11603
11604!>\brief Scrittura su file di un volume Vol7d.
11605!! Scrittura su file unformatted di un intero volume Vol7d.
11606!! Il volume viene serializzato e scritto su file.
11607!! Il file puo' essere aperto opzionalmente dall'utente. Si possono passare
11608!! opzionalmente unità e nome del file altrimenti assegnati internamente a dei default; se assegnati internamente
11609!! tali parametri saranno in output.
11610!! Se non viene fornito il nome file viene utilizzato un file di default con nome pari al nome del programma in
11611!! esecuzione con postfisso ".v7d".
11612!! Come parametro opzionale c'è la description che insieme alla data corrente viene inserita nell'header del file.
11613subroutine vol7d_write_on_file (this,unit,description,filename,filename_auto)
11614
11615TYPE(vol7d),INTENT(IN) :: this !< volume vol7d da scrivere
11616integer,optional,intent(inout) :: unit !< unità su cui scrivere; se passata =0 ritorna il valore rielaborato (default =rielaborato internamente con getlun )
11617character(len=*),intent(in),optional :: filename !< nome del file su cui scrivere
11618character(len=*),intent(out),optional :: filename_auto !< nome del file generato se "filename" è omesso
11619character(len=*),INTENT(IN),optional :: description !< descrizione del volume
11620
11621integer :: lunit
11622character(len=254) :: ldescription,arg,lfilename
11623integer :: nana, ntime, ntimerange, nlevel, nnetwork, &
11624 ndativarr, ndativari, ndativarb, ndativard, ndativarc,&
11625 ndatiattrr, ndatiattri, ndatiattrb, ndatiattrd, ndatiattrc,&
11626 ndativarattrr, ndativarattri, ndativarattrb, ndativarattrd, ndativarattrc,&
11627 nanavarr, nanavari, nanavarb, nanavard, nanavarc,&
11628 nanaattrr, nanaattri, nanaattrb, nanaattrd, nanaattrc,&
11629 nanavarattrr, nanavarattri, nanavarattrb, nanavarattrd, nanavarattrc
11630!integer :: im,id,iy
11631integer :: tarray(8)
11632logical :: opened,exist
11633
11634 nana=0
11635 ntime=0
11636 ntimerange=0
11637 nlevel=0
11638 nnetwork=0
11639 ndativarr=0
11640 ndativari=0
11641 ndativarb=0
11642 ndativard=0
11643 ndativarc=0
11644 ndatiattrr=0
11645 ndatiattri=0
11646 ndatiattrb=0
11647 ndatiattrd=0
11648 ndatiattrc=0
11649 ndativarattrr=0
11650 ndativarattri=0
11651 ndativarattrb=0
11652 ndativarattrd=0
11653 ndativarattrc=0
11654 nanavarr=0
11655 nanavari=0
11656 nanavarb=0
11657 nanavard=0
11658 nanavarc=0
11659 nanaattrr=0
11660 nanaattri=0
11661 nanaattrb=0
11662 nanaattrd=0
11663 nanaattrc=0
11664 nanavarattrr=0
11665 nanavarattri=0
11666 nanavarattrb=0
11667 nanavarattrd=0
11668 nanavarattrc=0
11669
11670
11671!call idate(im,id,iy)
11672call date_and_time(values=tarray)
11673call getarg(0,arg)
11674
11675if (present(description))then
11676 ldescription=description
11677else
11678 ldescription="Vol7d generated by: "//trim(arg)
11679end if
11680
11681if (.not. present(unit))then
11682 lunit=getunit()
11683else
11684 if (unit==0)then
11685 lunit=getunit()
11686 unit=lunit
11687 else
11688 lunit=unit
11689 end if
11690end if
11691
11692lfilename=trim(arg)//".v7d"
11693if (index(arg,'/',back=.true.) > 0) lfilename=lfilename(index(arg,'/',back=.true.)+1 : )
11694
11695if (present(filename))then
11696 if (filename /= "")then
11697 lfilename=filename
11698 end if
11699end if
11700
11701if (present(filename_auto))filename_auto=lfilename
11702
11703
11704inquire(unit=lunit,opened=opened)
11705if (.not. opened) then
11706! inquire(file=lfilename, EXIST=exist)
11707! IF (exist) THEN
11708! CALL l4f_log(L4F_FATAL, &
11709! 'in vol7d_write_on_file, file exists, cannot open file '//TRIM(lfilename))
11710! CALL raise_fatal_error()
11711! ENDIF
11712 OPEN(unit=lunit, file=lfilename, form='UNFORMATTED', access='STREAM')
11713 CALL l4f_log(l4f_info, 'opened: '//trim(lfilename))
11714end if
11715
11716if (associated(this%ana)) nana=size(this%ana)
11717if (associated(this%time)) ntime=size(this%time)
11718if (associated(this%timerange)) ntimerange=size(this%timerange)
11719if (associated(this%level)) nlevel=size(this%level)
11720if (associated(this%network)) nnetwork=size(this%network)
11721
11722if (associated(this%dativar%r)) ndativarr=size(this%dativar%r)
11723if (associated(this%dativar%i)) ndativari=size(this%dativar%i)
11724if (associated(this%dativar%b)) ndativarb=size(this%dativar%b)
11725if (associated(this%dativar%d)) ndativard=size(this%dativar%d)
11726if (associated(this%dativar%c)) ndativarc=size(this%dativar%c)
11727
11728if (associated(this%datiattr%r)) ndatiattrr=size(this%datiattr%r)
11729if (associated(this%datiattr%i)) ndatiattri=size(this%datiattr%i)
11730if (associated(this%datiattr%b)) ndatiattrb=size(this%datiattr%b)
11731if (associated(this%datiattr%d)) ndatiattrd=size(this%datiattr%d)
11732if (associated(this%datiattr%c)) ndatiattrc=size(this%datiattr%c)
11733
11734if (associated(this%dativarattr%r)) ndativarattrr=size(this%dativarattr%r)
11735if (associated(this%dativarattr%i)) ndativarattri=size(this%dativarattr%i)
11736if (associated(this%dativarattr%b)) ndativarattrb=size(this%dativarattr%b)
11737if (associated(this%dativarattr%d)) ndativarattrd=size(this%dativarattr%d)
11738if (associated(this%dativarattr%c)) ndativarattrc=size(this%dativarattr%c)
11739
11740if (associated(this%anavar%r)) nanavarr=size(this%anavar%r)
11741if (associated(this%anavar%i)) nanavari=size(this%anavar%i)
11742if (associated(this%anavar%b)) nanavarb=size(this%anavar%b)
11743if (associated(this%anavar%d)) nanavard=size(this%anavar%d)
11744if (associated(this%anavar%c)) nanavarc=size(this%anavar%c)
11745
11746if (associated(this%anaattr%r)) nanaattrr=size(this%anaattr%r)
11747if (associated(this%anaattr%i)) nanaattri=size(this%anaattr%i)
11748if (associated(this%anaattr%b)) nanaattrb=size(this%anaattr%b)
11749if (associated(this%anaattr%d)) nanaattrd=size(this%anaattr%d)
11750if (associated(this%anaattr%c)) nanaattrc=size(this%anaattr%c)
11751
11752if (associated(this%anavarattr%r)) nanavarattrr=size(this%anavarattr%r)
11753if (associated(this%anavarattr%i)) nanavarattri=size(this%anavarattr%i)
11754if (associated(this%anavarattr%b)) nanavarattrb=size(this%anavarattr%b)
11755if (associated(this%anavarattr%d)) nanavarattrd=size(this%anavarattr%d)
11756if (associated(this%anavarattr%c)) nanavarattrc=size(this%anavarattr%c)
11757
11758write(unit=lunit)ldescription
11759write(unit=lunit)tarray
11760
11761write(unit=lunit)&
11762 nana, ntime, ntimerange, nlevel, nnetwork, &
11763 ndativarr, ndativari, ndativarb, ndativard, ndativarc,&
11764 ndatiattrr, ndatiattri, ndatiattrb, ndatiattrd, ndatiattrc,&
11765 ndativarattrr, ndativarattri, ndativarattrb, ndativarattrd, ndativarattrc,&
11766 nanavarr, nanavari, nanavarb, nanavard, nanavarc,&
11767 nanaattrr, nanaattri, nanaattrb, nanaattrd, nanaattrc,&
11768 nanavarattrr, nanavarattri, nanavarattrb, nanavarattrd, nanavarattrc, &
11769 this%time_definition
11770
11771
11772!write(unit=lunit)this
11773
11774
11775!! prime 5 dimensioni
11776if (associated(this%ana)) call write_unit(this%ana, lunit)
11777if (associated(this%time)) call write_unit(this%time, lunit)
11778if (associated(this%level)) write(unit=lunit)this%level
11779if (associated(this%timerange)) write(unit=lunit)this%timerange
11780if (associated(this%network)) write(unit=lunit)this%network
11781
11782 !! 6a dimensione: variabile dell'anagrafica e dei dati
11783 !! con relativi attributi e in 5 tipi diversi
11784
11785if (associated(this%anavar%r)) write(unit=lunit)this%anavar%r
11786if (associated(this%anavar%i)) write(unit=lunit)this%anavar%i
11787if (associated(this%anavar%b)) write(unit=lunit)this%anavar%b
11788if (associated(this%anavar%d)) write(unit=lunit)this%anavar%d
11789if (associated(this%anavar%c)) write(unit=lunit)this%anavar%c
11790
11791if (associated(this%anaattr%r)) write(unit=lunit)this%anaattr%r
11792if (associated(this%anaattr%i)) write(unit=lunit)this%anaattr%i
11793if (associated(this%anaattr%b)) write(unit=lunit)this%anaattr%b
11794if (associated(this%anaattr%d)) write(unit=lunit)this%anaattr%d
11795if (associated(this%anaattr%c)) write(unit=lunit)this%anaattr%c
11796
11797if (associated(this%anavarattr%r)) write(unit=lunit)this%anavarattr%r
11798if (associated(this%anavarattr%i)) write(unit=lunit)this%anavarattr%i
11799if (associated(this%anavarattr%b)) write(unit=lunit)this%anavarattr%b
11800if (associated(this%anavarattr%d)) write(unit=lunit)this%anavarattr%d
11801if (associated(this%anavarattr%c)) write(unit=lunit)this%anavarattr%c
11802
11803if (associated(this%dativar%r)) write(unit=lunit)this%dativar%r
11804if (associated(this%dativar%i)) write(unit=lunit)this%dativar%i
11805if (associated(this%dativar%b)) write(unit=lunit)this%dativar%b
11806if (associated(this%dativar%d)) write(unit=lunit)this%dativar%d
11807if (associated(this%dativar%c)) write(unit=lunit)this%dativar%c
11808
11809if (associated(this%datiattr%r)) write(unit=lunit)this%datiattr%r
11810if (associated(this%datiattr%i)) write(unit=lunit)this%datiattr%i
11811if (associated(this%datiattr%b)) write(unit=lunit)this%datiattr%b
11812if (associated(this%datiattr%d)) write(unit=lunit)this%datiattr%d
11813if (associated(this%datiattr%c)) write(unit=lunit)this%datiattr%c
11814
11815if (associated(this%dativarattr%r)) write(unit=lunit)this%dativarattr%r
11816if (associated(this%dativarattr%i)) write(unit=lunit)this%dativarattr%i
11817if (associated(this%dativarattr%b)) write(unit=lunit)this%dativarattr%b
11818if (associated(this%dativarattr%d)) write(unit=lunit)this%dativarattr%d
11819if (associated(this%dativarattr%c)) write(unit=lunit)this%dativarattr%c
11820
11821!! Volumi di valori e attributi per anagrafica e dati
11822
11823if (associated(this%volanar)) write(unit=lunit)this%volanar
11824if (associated(this%volanaattrr)) write(unit=lunit)this%volanaattrr
11825if (associated(this%voldatir)) write(unit=lunit)this%voldatir
11826if (associated(this%voldatiattrr)) write(unit=lunit)this%voldatiattrr
11827
11828if (associated(this%volanai)) write(unit=lunit)this%volanai
11829if (associated(this%volanaattri)) write(unit=lunit)this%volanaattri
11830if (associated(this%voldatii)) write(unit=lunit)this%voldatii
11831if (associated(this%voldatiattri)) write(unit=lunit)this%voldatiattri
11832
11833if (associated(this%volanab)) write(unit=lunit)this%volanab
11834if (associated(this%volanaattrb)) write(unit=lunit)this%volanaattrb
11835if (associated(this%voldatib)) write(unit=lunit)this%voldatib
11836if (associated(this%voldatiattrb)) write(unit=lunit)this%voldatiattrb
11837
11838if (associated(this%volanad)) write(unit=lunit)this%volanad
11839if (associated(this%volanaattrd)) write(unit=lunit)this%volanaattrd
11840if (associated(this%voldatid)) write(unit=lunit)this%voldatid
11841if (associated(this%voldatiattrd)) write(unit=lunit)this%voldatiattrd
11842
11843if (associated(this%volanac)) write(unit=lunit)this%volanac
11844if (associated(this%volanaattrc)) write(unit=lunit)this%volanaattrc
11845if (associated(this%voldatic)) write(unit=lunit)this%voldatic
11846if (associated(this%voldatiattrc)) write(unit=lunit)this%voldatiattrc
11847
11848if (.not. present(unit)) close(unit=lunit)
11849
11850end subroutine vol7d_write_on_file
11851
11852
11853!>\brief Lettura da file di un volume Vol7d.
11854!! Lettura da file unformatted di un intero volume Vol7d.
11855!! Questa subroutine comprende vol7d_alloc e vol7d_alloc_vol.
11856!! Il file puo' essere aperto opzionalmente dall'utente. Si possono passare
11857!! opzionalmente unità e nome del file altrimenti assegnati internamente a dei default; se assegnati internamente
11858!! tali parametri saranno in output.
11859
11860
11861subroutine vol7d_read_from_file (this,unit,filename,description,tarray,filename_auto)
11862
11863TYPE(vol7d),INTENT(OUT) :: this !< Volume vol7d da leggere
11864integer,intent(inout),optional :: unit !< unità su cui è stato aperto un file; se =0 rielaborato internamente (default = elaborato internamente con getunit)
11865character(len=*),INTENT(in),optional :: filename !< nome del file eventualmente da aprire (default = (nome dell'eseguibile)//.v7d )
11866character(len=*),intent(out),optional :: filename_auto !< nome del file generato se "filename" è omesso
11867character(len=*),INTENT(out),optional :: description !< descrizione del volume letto
11868integer,intent(out),optional :: tarray(8) !< vettore come definito da "date_and_time" della data di scrittura del volume
11869
11870
11871integer :: nana, ntime, ntimerange, nlevel, nnetwork, &
11872 ndativarr, ndativari, ndativarb, ndativard, ndativarc,&
11873 ndatiattrr, ndatiattri, ndatiattrb, ndatiattrd, ndatiattrc,&
11874 ndativarattrr, ndativarattri, ndativarattrb, ndativarattrd, ndativarattrc,&
11875 nanavarr, nanavari, nanavarb, nanavard, nanavarc,&
11876 nanaattrr, nanaattri, nanaattrb, nanaattrd, nanaattrc,&
11877 nanavarattrr, nanavarattri, nanavarattrb, nanavarattrd, nanavarattrc
11878
11879character(len=254) :: ldescription,lfilename,arg
11880integer :: ltarray(8),lunit,ios
11881logical :: opened,exist
11882
11883
11884call getarg(0,arg)
11885
11886if (.not. present(unit))then
11887 lunit=getunit()
11888else
11889 if (unit==0)then
11890 lunit=getunit()
11891 unit=lunit
11892 else
11893 lunit=unit
11894 end if
11895end if
11896
11897lfilename=trim(arg)//".v7d"
11898if (index(arg,'/',back=.true.) > 0) lfilename=lfilename(index(arg,'/',back=.true.)+1 : )
11899
11900if (present(filename))then
11901 if (filename /= "")then
11902 lfilename=filename
11903 end if
11904end if
11905
11906if (present(filename_auto))filename_auto=lfilename
11907
11908
11909inquire(unit=lunit,opened=opened)
11910IF (.NOT. opened) THEN
11911 inquire(file=lfilename,exist=exist)
11912 IF (.NOT.exist) THEN
11913 CALL l4f_log(l4f_fatal, &
11914 'in vol7d_read_from_file, file does not exists, cannot open')
11915 CALL raise_fatal_error()
11916 ENDIF
11917 OPEN(unit=lunit, file=lfilename, form='UNFORMATTED', access='STREAM', &
11918 status='OLD', action='READ')
11919 CALL l4f_log(l4f_info, 'opened: '//trim(lfilename))
11920end if
11921
11922
11923call init(this)
11924read(unit=lunit,iostat=ios)ldescription
11925
11926if (ios < 0) then ! A negative value indicates that the End of File or End of Record
11927 call vol7d_alloc (this)
11928 call vol7d_alloc_vol (this)
11929 if (present(description))description=ldescription
11930 if (present(tarray))tarray=ltarray
11931 if (.not. present(unit)) close(unit=lunit)
11932end if
11933
11934read(unit=lunit)ltarray
11935
11936CALL l4f_log(l4f_info, 'Reading vol7d from file')
11937CALL l4f_log(l4f_info, 'description: '//trim(ldescription))
11938CALL l4f_log(l4f_info, 'written on '//trim(to_char(ltarray(1)))//' '// &
11939 trim(to_char(ltarray(2)))//' '//trim(to_char(ltarray(3))))
11940
11941if (present(description))description=ldescription
11942if (present(tarray))tarray=ltarray
11943
11944read(unit=lunit)&
11945 nana, ntime, ntimerange, nlevel, nnetwork, &
11946 ndativarr, ndativari, ndativarb, ndativard, ndativarc,&
11947 ndatiattrr, ndatiattri, ndatiattrb, ndatiattrd, ndatiattrc,&
11948 ndativarattrr, ndativarattri, ndativarattrb, ndativarattrd, ndativarattrc,&
11949 nanavarr, nanavari, nanavarb, nanavard, nanavarc,&
11950 nanaattrr, nanaattri, nanaattrb, nanaattrd, nanaattrc,&
11951 nanavarattrr, nanavarattri, nanavarattrb, nanavarattrd, nanavarattrc, &
11952 this%time_definition
11953
11954call vol7d_alloc (this, &
11955 nana=nana, ntime=ntime, ntimerange=ntimerange, nlevel=nlevel, nnetwork=nnetwork,&
11956 ndativarr=ndativarr, ndativari=ndativari, ndativarb=ndativarb,&
11957 ndativard=ndativard, ndativarc=ndativarc,&
11958 ndatiattrr=ndatiattrr, ndatiattri=ndatiattri, ndatiattrb=ndatiattrb,&
11959 ndatiattrd=ndatiattrd, ndatiattrc=ndatiattrc,&
11960 ndativarattrr=ndativarattrr, ndativarattri=ndativarattri, ndativarattrb=ndativarattrb, &
11961 ndativarattrd=ndativarattrd, ndativarattrc=ndativarattrc,&
11962 nanavarr=nanavarr, nanavari=nanavari, nanavarb=nanavarb, &
11963 nanavard=nanavard, nanavarc=nanavarc,&
11964 nanaattrr=nanaattrr, nanaattri=nanaattri, nanaattrb=nanaattrb,&
11965 nanaattrd=nanaattrd, nanaattrc=nanaattrc,&
11966 nanavarattrr=nanavarattrr, nanavarattri=nanavarattri, nanavarattrb=nanavarattrb, &
11967 nanavarattrd=nanavarattrd, nanavarattrc=nanavarattrc)
11968
11969
11970if (associated(this%ana)) call read_unit(this%ana, lunit)
11971if (associated(this%time)) call read_unit(this%time, lunit)
11972if (associated(this%level)) read(unit=lunit)this%level
11973if (associated(this%timerange)) read(unit=lunit)this%timerange
11974if (associated(this%network)) read(unit=lunit)this%network
11975
11976if (associated(this%anavar%r)) read(unit=lunit)this%anavar%r
11977if (associated(this%anavar%i)) read(unit=lunit)this%anavar%i
11978if (associated(this%anavar%b)) read(unit=lunit)this%anavar%b
11979if (associated(this%anavar%d)) read(unit=lunit)this%anavar%d
11980if (associated(this%anavar%c)) read(unit=lunit)this%anavar%c
11981
11982if (associated(this%anaattr%r)) read(unit=lunit)this%anaattr%r
11983if (associated(this%anaattr%i)) read(unit=lunit)this%anaattr%i
11984if (associated(this%anaattr%b)) read(unit=lunit)this%anaattr%b
11985if (associated(this%anaattr%d)) read(unit=lunit)this%anaattr%d
11986if (associated(this%anaattr%c)) read(unit=lunit)this%anaattr%c
11987
11988if (associated(this%anavarattr%r)) read(unit=lunit)this%anavarattr%r
11989if (associated(this%anavarattr%i)) read(unit=lunit)this%anavarattr%i
11990if (associated(this%anavarattr%b)) read(unit=lunit)this%anavarattr%b
11991if (associated(this%anavarattr%d)) read(unit=lunit)this%anavarattr%d
11992if (associated(this%anavarattr%c)) read(unit=lunit)this%anavarattr%c
11993
11994if (associated(this%dativar%r)) read(unit=lunit)this%dativar%r
11995if (associated(this%dativar%i)) read(unit=lunit)this%dativar%i
11996if (associated(this%dativar%b)) read(unit=lunit)this%dativar%b
11997if (associated(this%dativar%d)) read(unit=lunit)this%dativar%d
11998if (associated(this%dativar%c)) read(unit=lunit)this%dativar%c
11999
12000if (associated(this%datiattr%r)) read(unit=lunit)this%datiattr%r
12001if (associated(this%datiattr%i)) read(unit=lunit)this%datiattr%i
12002if (associated(this%datiattr%b)) read(unit=lunit)this%datiattr%b
12003if (associated(this%datiattr%d)) read(unit=lunit)this%datiattr%d
12004if (associated(this%datiattr%c)) read(unit=lunit)this%datiattr%c
12005
12006if (associated(this%dativarattr%r)) read(unit=lunit)this%dativarattr%r
12007if (associated(this%dativarattr%i)) read(unit=lunit)this%dativarattr%i
12008if (associated(this%dativarattr%b)) read(unit=lunit)this%dativarattr%b
12009if (associated(this%dativarattr%d)) read(unit=lunit)this%dativarattr%d
12010if (associated(this%dativarattr%c)) read(unit=lunit)this%dativarattr%c
12011
12012call vol7d_alloc_vol (this)
12013
12014!! Volumi di valori e attributi per anagrafica e dati
12015
12016if (associated(this%volanar)) read(unit=lunit)this%volanar
12017if (associated(this%volanaattrr)) read(unit=lunit)this%volanaattrr
12018if (associated(this%voldatir)) read(unit=lunit)this%voldatir
12019if (associated(this%voldatiattrr)) read(unit=lunit)this%voldatiattrr
12020
12021if (associated(this%volanai)) read(unit=lunit)this%volanai
12022if (associated(this%volanaattri)) read(unit=lunit)this%volanaattri
12023if (associated(this%voldatii)) read(unit=lunit)this%voldatii
12024if (associated(this%voldatiattri)) read(unit=lunit)this%voldatiattri
12025
12026if (associated(this%volanab)) read(unit=lunit)this%volanab
12027if (associated(this%volanaattrb)) read(unit=lunit)this%volanaattrb
12028if (associated(this%voldatib)) read(unit=lunit)this%voldatib
12029if (associated(this%voldatiattrb)) read(unit=lunit)this%voldatiattrb
12030
12031if (associated(this%volanad)) read(unit=lunit)this%volanad
12032if (associated(this%volanaattrd)) read(unit=lunit)this%volanaattrd
12033if (associated(this%voldatid)) read(unit=lunit)this%voldatid
12034if (associated(this%voldatiattrd)) read(unit=lunit)this%voldatiattrd
12035
12036if (associated(this%volanac)) read(unit=lunit)this%volanac
12037if (associated(this%volanaattrc)) read(unit=lunit)this%volanaattrc
12038if (associated(this%voldatic)) read(unit=lunit)this%voldatic
12039if (associated(this%voldatiattrc)) read(unit=lunit)this%voldatiattrc
12040
12041if (.not. present(unit)) close(unit=lunit)
12042
12043end subroutine vol7d_read_from_file
12044
12045
12046! to double precision
12047elemental doubleprecision function doubledatd(voldat,var)
12048doubleprecision,intent(in) :: voldat
12049type(vol7d_var),intent(in) :: var
12050
12051doubledatd=voldat
12052
12053end function doubledatd
12054
12055
12056elemental doubleprecision function doubledatr(voldat,var)
12057real,intent(in) :: voldat
12058type(vol7d_var),intent(in) :: var
12059
12060if (c_e(voldat))then
12061 doubledatr=dble(voldat)
12062else
12063 doubledatr=dmiss
12064end if
12065
12066end function doubledatr
12067
12068
12069elemental doubleprecision function doubledati(voldat,var)
12070integer,intent(in) :: voldat
12071type(vol7d_var),intent(in) :: var
12072
12073if (c_e(voldat)) then
12074 if (c_e(var%scalefactor))then
12075 doubledati=dble(voldat)/10.d0**var%scalefactor
12076 else
12077 doubledati=dble(voldat)
12078 endif
12079else
12080 doubledati=dmiss
12081end if
12082
12083end function doubledati
12084
12085
12086elemental doubleprecision function doubledatb(voldat,var)
12087integer(kind=int_b),intent(in) :: voldat
12088type(vol7d_var),intent(in) :: var
12089
12090if (c_e(voldat)) then
12091 if (c_e(var%scalefactor))then
12092 doubledatb=dble(voldat)/10.d0**var%scalefactor
12093 else
12094 doubledatb=dble(voldat)
12095 endif
12096else
12097 doubledatb=dmiss
12098end if
12099
12100end function doubledatb
12101
12102
12103elemental doubleprecision function doubledatc(voldat,var)
12104CHARACTER(len=vol7d_cdatalen),intent(in) :: voldat
12105type(vol7d_var),intent(in) :: var
12106
12107doubledatc = c2d(voldat)
12108if (c_e(doubledatc) .and. c_e(var%scalefactor))then
12109 doubledatc=doubledatc/10.d0**var%scalefactor
12110end if
12111
12112end function doubledatc
12113
12114
12115! to integer
12116elemental integer function integerdatd(voldat,var)
12117doubleprecision,intent(in) :: voldat
12118type(vol7d_var),intent(in) :: var
12119
12120if (c_e(voldat))then
12121 if (c_e(var%scalefactor)) then
12122 integerdatd=nint(voldat*10d0**var%scalefactor)
12123 else
12124 integerdatd=nint(voldat)
12125 endif
12126else
12127 integerdatd=imiss
12128end if
12129
12130end function integerdatd
12131
12132
12133elemental integer function integerdatr(voldat,var)
12134real,intent(in) :: voldat
12135type(vol7d_var),intent(in) :: var
12136
12137if (c_e(voldat))then
12138 if (c_e(var%scalefactor)) then
12139 integerdatr=nint(voldat*10d0**var%scalefactor)
12140 else
12141 integerdatr=nint(voldat)
12142 endif
12143else
12144 integerdatr=imiss
12145end if
12146
12147end function integerdatr
12148
12149
12150elemental integer function integerdati(voldat,var)
12151integer,intent(in) :: voldat
12152type(vol7d_var),intent(in) :: var
12153
12154integerdati=voldat
12155
12156end function integerdati
12157
12158
12159elemental integer function integerdatb(voldat,var)
12160integer(kind=int_b),intent(in) :: voldat
12161type(vol7d_var),intent(in) :: var
12162
12163if (c_e(voldat))then
12164 integerdatb=voldat
12165else
12166 integerdatb=imiss
12167end if
12168
12169end function integerdatb
12170
12171
12172elemental integer function integerdatc(voldat,var)
12173CHARACTER(len=vol7d_cdatalen),intent(in) :: voldat
12174type(vol7d_var),intent(in) :: var
12175
12176integerdatc=c2i(voldat)
12177
12178end function integerdatc
12179
12180
12181! to real
12182elemental real function realdatd(voldat,var)
12183doubleprecision,intent(in) :: voldat
12184type(vol7d_var),intent(in) :: var
12185
12186if (c_e(voldat))then
12187 realdatd=real(voldat)
12188else
12189 realdatd=rmiss
12190end if
12191
12192end function realdatd
12193
12194
12195elemental real function realdatr(voldat,var)
12196real,intent(in) :: voldat
12197type(vol7d_var),intent(in) :: var
12198
12199realdatr=voldat
12200
12201end function realdatr
12202
12203
12204elemental real function realdati(voldat,var)
12205integer,intent(in) :: voldat
12206type(vol7d_var),intent(in) :: var
12207
12208if (c_e(voldat)) then
12209 if (c_e(var%scalefactor))then
12210 realdati=float(voldat)/10.**var%scalefactor
12211 else
12212 realdati=float(voldat)
12213 endif
12214else
12215 realdati=rmiss
12216end if
12217
12218end function realdati
12219
12220
12221elemental real function realdatb(voldat,var)
12222integer(kind=int_b),intent(in) :: voldat
12223type(vol7d_var),intent(in) :: var
12224
12225if (c_e(voldat)) then
12226 if (c_e(var%scalefactor))then
12227 realdatb=float(voldat)/10**var%scalefactor
12228 else
12229 realdatb=float(voldat)
12230 endif
12231else
12232 realdatb=rmiss
12233end if
12234
12235end function realdatb
12236
12237
12238elemental real function realdatc(voldat,var)
12239CHARACTER(len=vol7d_cdatalen),intent(in) :: voldat
12240type(vol7d_var),intent(in) :: var
12241
12242realdatc=c2r(voldat)
12243if (c_e(realdatc) .and. c_e(var%scalefactor))then
12244 realdatc=realdatc/10.**var%scalefactor
12245end if
12246
12247end function realdatc
12248
12249
12250!> Return an ana volume of a requested variable as real data.
12251!! It returns a 2-d array of the proper shape (ana x network) for the
12252!! ana variable requested, converted to real type. If the conversion
12253!! fails or if the variable is not contained in the ana volume,
12254!! missing data are returned.
12255FUNCTION realanavol(this, var) RESULT(vol)
12256TYPE(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
12257TYPE(vol7d_var),INTENT(in) :: var !< the ana variable to be returned
12258REAL :: vol(SIZE(this%ana),size(this%network))
12259
12260CHARACTER(len=1) :: dtype
12261INTEGER :: indvar
12262
12263dtype = cmiss
12264indvar = index(this%anavar, var, type=dtype)
12265
12266IF (indvar > 0) THEN
12267 SELECT CASE (dtype)
12268 CASE("d")
12269 vol = realdat(this%volanad(:,indvar,:), var)
12270 CASE("r")
12271 vol = this%volanar(:,indvar,:)
12272 CASE("i")
12273 vol = realdat(this%volanai(:,indvar,:), var)
12274 CASE("b")
12275 vol = realdat(this%volanab(:,indvar,:), var)
12276 CASE("c")
12277 vol = realdat(this%volanac(:,indvar,:), var)
12278 CASE default
12279 vol = rmiss
12280 END SELECT
12281ELSE
12282 vol = rmiss
12283ENDIF
12284
12285END FUNCTION realanavol
12286
12287
12288!> Return an ana volume of a requested variable as integer data.
12289!! It returns a 2-d array of the proper shape (ana x network) for the
12290!! ana variable requested, converted to integer type. If the conversion
12291!! fails or if the variable is not contained in the ana volume,
12292!! missing data are returned.
12293FUNCTION integeranavol(this, var) RESULT(vol)
12294TYPE(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
12295TYPE(vol7d_var),INTENT(in) :: var !< the ana variable to be returned
12296INTEGER :: vol(SIZE(this%ana),size(this%network))
12297
12298CHARACTER(len=1) :: dtype
12299INTEGER :: indvar
12300
12301dtype = cmiss
12302indvar = index(this%anavar, var, type=dtype)
12303
12304IF (indvar > 0) THEN
12305 SELECT CASE (dtype)
12306 CASE("d")
12307 vol = integerdat(this%volanad(:,indvar,:), var)
12308 CASE("r")
12309 vol = integerdat(this%volanar(:,indvar,:), var)
12310 CASE("i")
12311 vol = this%volanai(:,indvar,:)
12312 CASE("b")
12313 vol = integerdat(this%volanab(:,indvar,:), var)
12314 CASE("c")
12315 vol = integerdat(this%volanac(:,indvar,:), var)
12316 CASE default
12317 vol = imiss
12318 END SELECT
12319ELSE
12320 vol = imiss
12321ENDIF
12322
12323END FUNCTION integeranavol
12324
12325
12326!> Move data for all variables from one coordinate in the character volume to other.
12327!! Only not missing data will be copyed and all attributes will be moved together.
12328!! Usefull to colapse data spread in more indices (level or time or ....).
12329!! After the move is possible to set to missing some descriptor and make a copy with miss=.true.
12330!! to obtain a new vol7d with less data shape.
12331subroutine move_datac (v7d,&
12332 indana,indtime,indlevel,indtimerange,indnetwork,&
12333 indananew,indtimenew,indlevelnew,indtimerangenew,indnetworknew)
12334
12335TYPE(vol7d),intent(inout) :: v7d !< data in form of character in this object will be moved
12336
12337integer,intent(in) :: indana,indtime,indlevel,indtimerange,indnetwork !< source coordinate of the data
12338integer,intent(in) :: indananew,indtimenew,indlevelnew,indtimerangenew,indnetworknew !< destination coordinate of data
12339integer :: inddativar,inddativarattr
12340
12341
12342do inddativar=1,size(v7d%dativar%c)
12343
12344 if (c_e(v7d%voldatic(indana,indtime,indlevel,indtimerange,inddativar,indnetwork)) .and. &
12345 .not. c_e(v7d%voldatic(indananew,indtimenew,indlevelnew,indtimerangenew,inddativar,indnetworknew))&
12346 ) then
12347
12348 ! dati
12349 v7d%voldatic &
12350 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativar,indnetworknew) = &
12351 v7d%voldatic &
12352 (indana,indtime,indlevel,indtimerange,inddativar,indnetwork)
12353
12354
12355 ! attributi
12356 if (associated (v7d%dativarattr%i)) then
12357 inddativarattr = index(v7d%dativarattr%i,v7d%dativar%c(inddativar))
12358 if (inddativarattr > 0 ) then
12359 v7d%voldatiattri &
12360 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
12361 v7d%voldatiattri &
12362 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
12363 end if
12364 end if
12365
12366 if (associated (v7d%dativarattr%r)) then
12367 inddativarattr = index(v7d%dativarattr%r,v7d%dativar%c(inddativar))
12368 if (inddativarattr > 0 ) then
12369 v7d%voldatiattrr &
12370 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
12371 v7d%voldatiattrr &
12372 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
12373 end if
12374 end if
12375
12376 if (associated (v7d%dativarattr%d)) then
12377 inddativarattr = index(v7d%dativarattr%d,v7d%dativar%c(inddativar))
12378 if (inddativarattr > 0 ) then
12379 v7d%voldatiattrd &
12380 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
12381 v7d%voldatiattrd &
12382 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
12383 end if
12384 end if
12385
12386 if (associated (v7d%dativarattr%b)) then
12387 inddativarattr = index(v7d%dativarattr%b,v7d%dativar%c(inddativar))
12388 if (inddativarattr > 0 ) then
12389 v7d%voldatiattrb &
12390 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
12391 v7d%voldatiattrb &
12392 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
12393 end if
12394 end if
12395
12396 if (associated (v7d%dativarattr%c)) then
12397 inddativarattr = index(v7d%dativarattr%c,v7d%dativar%c(inddativar))
12398 if (inddativarattr > 0 ) then
12399 v7d%voldatiattrc &
12400 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
12401 v7d%voldatiattrc &
12402 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
12403 end if
12404 end if
12405
12406 end if
12407
12408end do
12409
12410end subroutine move_datac
12411
12412!> Move data for all variables from one coordinate in the real volume to other.
12413!! Only not missing data will be copyed and all attributes will be moved together.
12414!! Usefull to colapse data spread in more indices (level or time or ....).
12415!! After the move is possible to set to missing some descriptor and make a copy with miss=.true.
12416!! to obtain a new vol7d with less data shape.
12417subroutine move_datar (v7d,&
12418 indana,indtime,indlevel,indtimerange,indnetwork,&
12419 indananew,indtimenew,indlevelnew,indtimerangenew,indnetworknew)
12420
12421TYPE(vol7d),intent(inout) :: v7d !< data in form of character in this object will be moved
12422
12423integer,intent(in) :: indana,indtime,indlevel,indtimerange,indnetwork !< source coordinate of the data
12424integer,intent(in) :: indananew,indtimenew,indlevelnew,indtimerangenew,indnetworknew !< destination coordinate of data
12425integer :: inddativar,inddativarattr
12426
12427
12428do inddativar=1,size(v7d%dativar%r)
12429
12430 if (c_e(v7d%voldatir(indana,indtime,indlevel,indtimerange,inddativar,indnetwork)) .and. &
12431 .not. c_e(v7d%voldatir(indananew,indtimenew,indlevelnew,indtimerangenew,inddativar,indnetworknew))&
12432 ) then
12433
12434 ! dati
12435 v7d%voldatir &
12436 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativar,indnetworknew) = &
12437 v7d%voldatir &
12438 (indana,indtime,indlevel,indtimerange,inddativar,indnetwork)
12439
12440
12441 ! attributi
12442 if (associated (v7d%dativarattr%i)) then
12443 inddativarattr = index(v7d%dativarattr%i,v7d%dativar%r(inddativar))
12444 if (inddativarattr > 0 ) then
12445 v7d%voldatiattri &
12446 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
12447 v7d%voldatiattri &
12448 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
12449 end if
12450 end if
12451
12452 if (associated (v7d%dativarattr%r)) then
12453 inddativarattr = index(v7d%dativarattr%r,v7d%dativar%r(inddativar))
12454 if (inddativarattr > 0 ) then
12455 v7d%voldatiattrr &
12456 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
12457 v7d%voldatiattrr &
12458 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
12459 end if
12460 end if
12461
12462 if (associated (v7d%dativarattr%d)) then
12463 inddativarattr = index(v7d%dativarattr%d,v7d%dativar%r(inddativar))
12464 if (inddativarattr > 0 ) then
12465 v7d%voldatiattrd &
12466 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
12467 v7d%voldatiattrd &
12468 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
12469 end if
12470 end if
12471
12472 if (associated (v7d%dativarattr%b)) then
12473 inddativarattr = index(v7d%dativarattr%b,v7d%dativar%r(inddativar))
12474 if (inddativarattr > 0 ) then
12475 v7d%voldatiattrb &
12476 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
12477 v7d%voldatiattrb &
12478 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
12479 end if
12480 end if
12481
12482 if (associated (v7d%dativarattr%c)) then
12483 inddativarattr = index(v7d%dativarattr%c,v7d%dativar%r(inddativar))
12484 if (inddativarattr > 0 ) then
12485 v7d%voldatiattrc &
12486 (indananew,indtimenew,indlevelnew,indtimerangenew,inddativarattr,indnetworknew,:) = &
12487 v7d%voldatiattrc &
12488 (indana,indtime,indlevel,indtimerange,inddativarattr,indnetwork,:)
12489 end if
12490 end if
12491
12492 end if
12493
12494end do
12495
12496end subroutine move_datar
12497
12498
12499!> Reduce some dimensions (level and timerage) for semplification (rounding).
12500!! You can use this for simplify and use variables in computation like alchimia
12501!! where fields have to be on the same coordinate
12502!! It return real or character data only: if input is charcter data only it return character otherwise il return
12503!! all the data converted to real.
12504!! examples:
12505!! means in time for short periods and istantaneous values
12506!! 2 meter and surface levels
12507!! If there are data on more then one almost equal levels or timeranges, the first var present (at least one point)
12508!! will be taken (order is by icreasing var index).
12509!! You can use predefined values for classic semplification
12510!! almost_equal_levels and almost_equal_timeranges
12511!! The level or timerange in output will be defined by the first element of level and timerange list
12512subroutine v7d_rounding(v7din,v7dout,level,timerange,nostatproc)
12513type(vol7d),intent(inout) :: v7din !< input volume
12514type(vol7d),intent(out) :: v7dout !> output volume
12515type(vol7d_level),intent(in),optional :: level(:) !< almost equal level list
12516type(vol7d_timerange),intent(in),optional :: timerange(:) !< almost equal timerange list
12517!logical,intent(in),optional :: merge !< if there are data on more then one almost equal levels or timeranges
12518!! will be merged POINT BY POINT with priority for the fird data found ordered by icreasing var index
12519logical,intent(in),optional :: nostatproc !< do not take in account statistical processing code in timerange and P2
12520
12521integer :: nana,nlevel,ntime,ntimerange,nnetwork,nbin
12522integer :: iana,ilevel,itimerange,indl,indt,itime,inetwork
12523type(vol7d_level) :: roundlevel(size(v7din%level))
12524type(vol7d_timerange) :: roundtimerange(size(v7din%timerange))
12525type(vol7d) :: v7d_tmp
12526
12527
12528nbin=0
12529
12530if (associated(v7din%dativar%r)) nbin = nbin + size(v7din%dativar%r)
12531if (associated(v7din%dativar%i)) nbin = nbin + size(v7din%dativar%i)
12532if (associated(v7din%dativar%d)) nbin = nbin + size(v7din%dativar%d)
12533if (associated(v7din%dativar%b)) nbin = nbin + size(v7din%dativar%b)
12534
12535call init(v7d_tmp)
12536
12537roundlevel=v7din%level
12538
12539if (present(level))then
12540 do ilevel = 1, size(v7din%level)
12541 if ((any(v7din%level(ilevel) .almosteq. level))) then
12542 roundlevel(ilevel)=level(1)
12543 end if
12544 end do
12545end if
12546
12547roundtimerange=v7din%timerange
12548
12549if (present(timerange))then
12550 do itimerange = 1, size(v7din%timerange)
12551 if ((any(v7din%timerange(itimerange) .almosteq. timerange))) then
12552 roundtimerange(itimerange)=timerange(1)
12553 end if
12554 end do
12555end if
12556
12557!set istantaneous values everywere
12558!preserve p1 for forecast time
12559if (optio_log(nostatproc)) then
12560 roundtimerange(:)%timerange=254
12561 roundtimerange(:)%p2=0
12562end if
12563
12564
12565nana=size(v7din%ana)
12566nlevel=count_distinct(roundlevel,back=.true.)
12567ntime=size(v7din%time)
12568ntimerange=count_distinct(roundtimerange,back=.true.)
12569nnetwork=size(v7din%network)
12570
12571call init(v7d_tmp)
12572
12573if (nbin == 0) then
12574 call copy(v7din,v7d_tmp)
12575else
12576 call vol7d_convr(v7din,v7d_tmp)
12577end if
12578
12579v7d_tmp%level=roundlevel
12580v7d_tmp%timerange=roundtimerange
12581
12582do ilevel=1, size(v7d_tmp%level)
12583 indl=index(v7d_tmp%level,roundlevel(ilevel))
12584 do itimerange=1,size(v7d_tmp%timerange)
12585 indt=index(v7d_tmp%timerange,roundtimerange(itimerange))
12586
12587 if (indl /= ilevel .or. indt /= itimerange) then
12588
12589 do iana=1, nana
12590 do itime=1,ntime
12591 do inetwork=1,nnetwork
12592
12593 if (nbin > 0) then
12594 call move_datar (v7d_tmp,&
12595 iana,itime,ilevel,itimerange,inetwork,&
12596 iana,itime,indl,indt,inetwork)
12597 else
12598 call move_datac (v7d_tmp,&
12599 iana,itime,ilevel,itimerange,inetwork,&
12600 iana,itime,indl,indt,inetwork)
12601 end if
12602
12603 end do
12604 end do
12605 end do
12606
12607 end if
12608
12609 end do
12610end do
12611
12612! set to missing level and time > nlevel
12613do ilevel=nlevel+1,size(v7d_tmp%level)
12614 call init (v7d_tmp%level(ilevel))
12615end do
12616
12617do itimerange=ntimerange+1,size(v7d_tmp%timerange)
12618 call init (v7d_tmp%timerange(itimerange))
12619end do
12620
12621!copy with remove
12622CALL copy(v7d_tmp,v7dout,miss=.true.,lsort_timerange=.true.,lsort_level=.true.)
12623CALL delete(v7d_tmp)
12624
12625!call display(v7dout)
12626
12627end subroutine v7d_rounding
12628
12629
12630END MODULE vol7d_class
12631
12632!>\example esempio_qc_convert.f90
12633!!\brief Programma esempio semplice per la scrittura su file di un volume vol7d
12634!!
12635!!Programma che scrive su file un volume vol7d letto da una serie di file ASCII.
12636!!Questo programma scrive i dati del clima che poi verranno letti da modqccli
12637
12638
12639!>\example esempio_v7ddballe_move_and_collapse.f90
12640!!\brief ! Example program to reduce to one the dimensions of levels and time without loss of data
Set of functions that return a trimmed CHARACTER representation of the input variable.
Legge un oggetto datetime/timedelta o un vettore di oggetti datetime/timedelta da un file FORMATTED o...
Scrive un oggetto datetime/timedelta o un vettore di oggetti datetime/timedelta su un file FORMATTED ...
Index method.
Generic subroutine for checking OPTIONAL parameters.
Test for a missing volume.
Check for problems return 0 if all check passed print diagnostics with log4f.
Distruttore per la classe vol7d.
doubleprecision data conversion
Scrittura su file.
Costruttore per la classe vol7d.
integer data conversion
real data conversion
Reduce some dimensions (level and timerage) for semplification (rounding).
Represent data in a pretty string.
This module defines usefull general purpose function and subroutine.
Utilities for CHARACTER variables.
Classi per la gestione delle coordinate temporali.
Gestione degli errori.
Definition of constants to be used for declaring variables of a desired type.
Definition kinds.F90:245
classe per la gestione del logging
Module for quickly interpreting the OPTIONAL parameters passed to a subprogram.
Classe per la gestione dell'anagrafica di stazioni meteo e affini.
Classe per la gestione di un volume completo di dati osservati.
Classe per la gestione dei livelli verticali in osservazioni meteo e affini.
Classe per la gestione delle reti di stazioni per osservazioni meteo e affini.
Classe per la gestione degli intervalli temporali di osservazioni meteo e affini.
Classe per gestire un vettore di oggetti di tipo vol7d_var_class::vol7d_var.
Definisce un oggetto contenente i volumi anagrafica e dati e tutti i descrittori delle loro dimension...

Generated with Doxygen.