UNPACK(3) - [ARRAY:CONSTRUCTION] Scatter the elements of a vector into an array using a mask
result = unpack(vector, mask, field)
type(TYPE(kind=KIND)) unpack(vector, mask, field)type(TYPE(kind=KIND)),intent(in) :: vector(:) logical,intent(in) :: mask(..) type(TYPE(kind=KIND)),intent(in) :: field(..)
o VECTOR is a rank-one array of any type o MASK is a logical array o FIELD is the same type and type parameters as VECTOR conformable with MASK. o The result is an array of the same type and type parameters as VECTOR and the same shape as MASK.
UNPACK(3) scatters the elements of VECTOR into a copy of an array FIELD of any rank using .true. values from MASK in array element order to specify placement of the VECTOR values.
So a copy of FIELD is generated with select elements replaced with values from VECTOR. This allows for complex replacement patterns that would be difficult when using array syntax or multiple assignment statements, particularly when the replacements are conditional.
o VECTOR : New values to place into specified locations in FIELD. It shall have at least as many elements as MASK has .true. values. o MASK : Shall be an array that specifies which values in FIELD are to be replaced with values from VECTOR. o FIELD : The input array to be altered.
The element of the result that corresponds to the ith true element of MASK, in array element order, has the value VECTOR(I) for i = 1, 2, . . [char46], t, where t is the number of true values in MASK. Each other element has a value equal to FIELD if FIELD is scalar or to the corresponding element of FIELD if it is an array.
The resulting array corresponds to FIELD with .true. elements of MASK replaced by values from VECTOR in array element order.
Particular values may be "scattered" to particular positions in an array by using
1 0 0
Sample program:
If M is the array 0 1 0 0 0 1 V is the array [1, 2, 3], [char46] T .
and Q is the logical mask T . . [char46] . T where "T" represents true and "." represents false, then the result of UNPACK (V, MASK = Q, FIELD = M) has the value 1 2 0 1 1 0 0 0 3
and the result of UNPACK (V, MASK = Q, FIELD = 0) has the value 0 2 0 1 0 0 0 0 3
program demo_unpack implicit none logical,parameter :: T=.true., F=.false.Results:integer :: vector(2) = [1,1]
! mask and field must conform integer,parameter :: r=2, c=2 logical :: mask(r,c) = reshape([ T,F,F,T ],[2,2]) integer :: field(r,c) = 0, unity(2,2)
! basic usage unity = unpack( vector, mask, field ) call print_matrix_int(unity=, unity)
! if FIELD is a scalar it is used to fill all the elements ! not assigned to by the vector and mask. call print_matrix_int(scalar field, & & unpack( & & vector=[ 1, 2, 3, 4 ], & & mask=reshape([ T,F,T,F,F,F,T,F,T ], [3,3]), & & field=0) )
contains
subroutine print_matrix_int(title,arr) ! convenience routine: ! just prints small integer arrays in row-column format implicit none character(len=*),intent(in) :: title integer,intent(in) :: arr(:,:) integer :: i character(len=:),allocatable :: biggest
write(*,*)trim(title) ! make buffer to write integer into biggest= ! find how many characters to use for integers write(biggest,(i0))ceiling(log10(max(1.0,real(maxval(abs(arr))))))+2 ! use this format to write a row biggest=(" [",*(i//trim(biggest)//:,",")) ! print one row of array at a time do i=1,size(arr,dim=1) write(*,fmt=biggest,advance=no)arr(i,:) write(*,(" ]")) enddo end subroutine print_matrix_int
end program demo_unpack
> unity= > [ 1, 0 ] > [ 0, 1 ] > scalar field > [ 1, 0, 3 ] > [ 0, 0, 0 ] > [ 2, 0, 4 ]
Fortran 95
MERGE(3), PACK(3), SPREAD(3)
Fortran intrinsic descriptions (license: MIT) @urbanjost
Nemo Release 3.1 | unpack (3fortran) | November 02, 2024 |