EMPIRE DA  v1.9.1
Data assimilation codes using EMPIRE communication
 All Classes Files Functions Variables Pages
generate_pf.f90
Go to the documentation of this file.
1 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
2 !!! Time-stamp: <2016-10-18 15:37:32 pbrowne>
3 !!!
4 !!! Subroutine to generate Pf matrix given ensemble members on a communicator
5 !!! Copyright (C) 2014 Philip A. Browne
6 !!!
7 !!! This program is free software: you can redistribute it and/or modify
8 !!! it under the terms of the GNU General Public License as published by
9 !!! the Free Software Foundation, either version 3 of the License, or
10 !!! (at your option) any later version.
11 !!!
12 !!! This program is distributed in the hope that it will be useful,
13 !!! but WITHOUT ANY WARRANTY; without even the implied warranty of
14 !!! MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 !!! GNU General Public License for more details.
16 !!!
17 !!! You should have received a copy of the GNU General Public License
18 !!! along with this program. If not, see <http://www.gnu.org/licenses/>.
19 !!!
20 !!! Email: p.browne @ reading.ac.uk
21 !!! Mail: School of Mathematical and Physical Sciences,
22 !!! University of Reading,
23 !!! Reading, UK
24 !!! RG6 6BB
25 !!!
26 !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
27 
28 
31 subroutine generate_pf(stateDim,cnt,comm,x,pf)
32  use output_empire, only : emp_e
33  implicit none
34  include 'mpif.h'
35  integer, parameter :: rk = kind(1.0d0)
36  integer, intent(in) :: stateDim
37  integer, intent(in) :: cnt
39  integer, intent(in) :: comm
40  real(kind=rk), dimension(stateDim,cnt), intent(in) :: x
42  real(kind=rk), dimension(stateDim*(stateDim+1)/2), intent(out) :: Pf
46 
47 
48 
49  real(kind=rk), dimension(stateDim) :: mean
50  real(kind=rk), dimension(stateDim,cnt) :: xp
52 
53  integer :: m
54  integer :: i ! counter
55  integer :: mpi_err !error flag for mpi
56 
57  ! get the total number of ensemble members used:
58  call mpi_allreduce(cnt,m,1,mpi_integer,mpi_sum,comm,mpi_err)
59  if(mpi_err .ne. mpi_success) then
60  write(emp_e,*) 'ERROR in generate_pf: mpi_allreduce 1 failed with flag ',mpi_err
61  stop
62  end if
63 
64  !get the ensemble mean
65  xp(:,1) = sum(x,dim=2)
66  call mpi_allreduce(xp(:,1),mean,statedim,mpi_double_precision&
67  &,mpi_sum,comm,mpi_err)
68  if(mpi_err .ne. mpi_success) then
69  write(emp_e,*) 'ERROR in generate_pf: mpi_allreduce 2 failed with flag ',mpi_err
70  stop
71  end if
72  ! use BLAS to perform mean = mean/real(m,rk)
73  call dscal(statedim,1.0d0/real(m,rk),mean,1)
74 
75 
76  !compute the unscaled ensemble perturbation matrix on this process
77  do i = 1,cnt
78  xp(:,i) = x(:,i)-mean
79  end do
80 
81  !form pf with only ensemble members on this process
82  call dsfrk('N',& !TRANSR The normal form of RFP A is stored
83  'U',& !UPLO upper part of matrix formed
84  'N',& !TRANS no transposed done
85  statedim,& !N dim of output matrix [square]
86  cnt,& !K number of columns in input
87  1.0d0,& !ALPHA alpha scalar
88  xp,& !A input matrix
89  statedim,& !LDA leading dimension of A
90  0.0d0,& !BETA add to empty array
91  pf,& !C output matrix
92  statedim& !LDC dimension of output matrix
93  )
94 
95  ! get pf on all processors
96  call mpi_allreduce(mpi_in_place,pf,statedim*(statedim+1)/2,mpi_double_precision&
97  &,mpi_sum,comm,mpi_err)
98  if(mpi_err .ne. mpi_success) then
99  write(emp_e,*) 'ERROR in generate_pf: mpi_allreduce 3 failed with flag ',mpi_err
100  stop
101  end if
102 
103  !scale pf appropriately
104  ! use BLAS to perform pf = pf/(m-1)
105  call dscal(statedim*(statedim+1)/2,1.0d0/real(m-1,rk),pf,1)
106 
107 end subroutine generate_pf
Module that stores the information about the outputting from empire.
subroutine generate_pf(stateDim, cnt, comm, x, pf)
subroutine to generate Pf matrix given ensemble members on a communicator
Definition: generate_pf.f90:31