×
INTELLIGENT WORK FORUMS
FOR COMPUTER PROFESSIONALS

Contact US

Log In

Come Join Us!

Are you a
Computer / IT professional?
Join Tek-Tips Forums!
  • Talk With Other Members
  • Be Notified Of Responses
    To Your Posts
  • Keyword Search
  • One-Click Access To Your
    Favorite Forums
  • Automated Signatures
    On Your Posts
  • Best Of All, It's Free!

*Tek-Tips's functionality depends on members receiving e-mail. By joining you are opting in to receive e-mail.

Posting Guidelines

Promoting, selling, recruiting, coursework and thesis posting is forbidden.

Students Click Here

Fortran code to average hourly data into daily values

Fortran code to average hourly data into daily values

Fortran code to average hourly data into daily values

(OP)
Hello All,

I am new to using Fortan and doing research work with hourly observation data and computing 24 hour times periods down to daily averaged vaule. I have did a search online and found a Fortran script similar to what my needs are for data computation. The script runs as far as line 101 then crashes. Not sure what the issues is with the script. Does anyone have any suggustions? Also how would I output the two columns of date and data to a new file say one named datatest.txt? I have file format and the script being used to below.....

Thank you

20101002 15:00 0.4
20101002 16:00 0.4
20101002 17:00 0.4
20101002 18:00 0.7
20101002 19:00 0.8
20101002 20:00 0.8
20101002 21:00 0.6
20101002 22:00 0.4

program control_break
! Single-Level Control Break Processing

implicit none

integer :: stat, nr_records
real :: dummy
! global variables
integer :: date, date_save, col02, nr_col03, tnr_col03
real :: col03, sum_col03, tsum_col03
common date, date_save, col02, col03, &
nr_col03, sum_col03, &
tnr_col03, tsum_col03

! open file
open (1, file="C:\\Users\\Jason\\Desktop\\GEOS-CHEM-Data\\County005-CO-0133.txt", status='old', iostat=stat)
if (stat .ne. 0) then
write(*,*) 'File cannot be opened !'
go to 99
end if

write(*, '(80A)') '*******************************************************'
! process file
nr_records = 0
date_save = 0

do while (.true.)
! read record
read(1, *, end=99) dummy, col02, col03
nr_records = nr_records + 1
call process_record
call save_keys
enddo

99 continue
! at end print totals
call print_daily_summary
call print_total_summary
write(*, 10) nr_records
write(*, '(80A)') '*******************************************************'
! close file
close(1)

10 format('Processing of',1X, I0, 1X, 'lines finished.')
end program control_break

subroutine process_record
implicit none
! global variables
integer :: date, date_save, col02, nr_col03, tnr_col03
real :: col03, sum_col03, tsum_col03
common date, date_save, col02, col03, &
nr_col03, sum_col03, &
tnr_col03, tsum_col03

! compute date
date = col02

! if not on first record
if (date_save .ne. 0) then
! process control break
call process_control_break
end if

! print line
write(*, 10) col02, col03

! compute sum of col03
if (col03 .ne. -999.0) then
nr_col03 = nr_col03 + 1
sum_col03 = sum_col03 + col03
tnr_col03 = tnr_col03 + 1
tsum_col03 = tsum_col03 + col03
end if

10 format(5X, I10, 1X, f8.2, 1X, f8.2)
end subroutine process_record

subroutine process_control_break
implicit none
! global variables
integer :: date, date_save, col02, nr_col03, tnr_col03
real :: col03, col07, sum_col03, tsum_col03
common date, date_save, col02, col03, &
nr_col03, sum_col03, &
tnr_col03, tsum_col03

if (date .ne. date_save) then
call print_daily_summary
end if
end subroutine process_control_break

subroutine print_daily_summary
implicit none
! global variables
integer :: date, date_save, col02, nr_col03, tnr_col03
real :: col03, sum_col03, tsum_col03
common date, date_save, col02, col03 &
nr_col03, sum_col03, &
tnr_col03, tsum_col03

write(*, *)
write(*, 10) date_save
write(*, 20) sum_col03
write(*, 30) nr_col03
write(*, 40) sum_col03/nr_col03
write(*, *)

10 format('* Summary for date',1x,I8,':')
20 format('* sum:',9x, f8.2, 1x, f8.2)
30 format('* count:',7x,I8,1x,I8)
40 format('* average:',5x, f8.2, 1x, f8.2)

! initialize gloabal variables
sum_col03 = 0
nr_col03 = 0
end subroutine print_daily_summary

subroutine print_total_summary
implicit none
! global variables
integer :: date, date_save, col02, nr_col03, tnr_col03
real :: col03, sum_col03, tsum_col03
common date, date_save, col02, col03, &
nr_col03, sum_col03, &
tnr_col03, tsum_col03

write(*, 10)
write(*, 20) tsum_col03
write(*, 30) tnr_col03
write(*, 40) tsum_col03/tnr_col03

10 format('** Summary for all dates:')
20 format('** sum:',9x, f8.2, 1x, f8.2)
30 format('** count:',7x,I8,1x,I8)
40 format('** average:',5x, f8.2, 1x, f8.2)
end subroutine print_total_summary

subroutine save_keys
implicit none
! global variables
integer :: date, date_save, col02, nr_col03, tnr_col03
real :: col03, sum_col03, tsum_col03
common date, date_save, col02, col03, &
nr_col03, sum_col03, &
tnr_col03, tsum_col03

date_save = date
end subroutine save_keys

RE: Fortran code to average hourly data into daily values

I adapted the program temperatures.f95 from https://www.tek-tips.com/viewthread.cfm?qid=165588...

Try this:

CODE

module glob_vars
  ! declaration of global variables
  implicit none
  integer :: nr_records
  ! file record fields
  integer :: date
  character(5) :: time
  real :: val
  ! save fields
  integer :: date_save
  character(5) :: time_save
  real :: val_save
  ! daily result fields
  integer :: nr_val
  real :: min_val, max_val, sum_val
  character(5) :: min_time, max_time
  ! total result fields
  integer :: tmin_date, tmax_date, tnr_val
  real :: tmin_val, tmax_val, tsum_val
  character(5) :: tmin_time, tmax_time  
end module glob_vars

program control_break2
  ! Single-Level Control Break Processing

  use glob_vars

  implicit none
  
  integer :: stat ! file status

  ! open file
  open (1, file='control_break2.dat', status='old', iostat=stat)
  if (stat .ne. 0) then
    write(*,*) 'File cannot be opened !'
    go to 99
  end if

  write(*, '(80A)') '*******************************************************'
  ! process file
  nr_records = 0
  date_save = 0

  do while (.true.)
    ! read record
    read(1, *, end=99) date, time, val
    nr_records = nr_records + 1
    call process_record
    call save_keys
  enddo

  99 continue
  ! at end print totals
  call print_daily_summary
  call print_total_summary
  write(*, 10) nr_records
  write(*, '(80A)') '*******************************************************'
  ! close file
  close(1)

  10 format('Processing of', 1X, I0, 1X, 'lines finished.')
end program control_break2

subroutine process_record
  use glob_vars
  implicit none

  ! on 1.record initialize min and max values
  if (nr_records .eq. 1) then
    ! daily values
    min_time = time
    min_val = val
    max_time = time
    max_val = val
    ! total values
    tmin_date = date
    tmin_time = time
    tmin_val = val
    tmax_date = date
    tmax_time = time
    tmax_val = val 
  end if

  ! if not on 1.record
  if (date_save .ne. 0) then
    ! process control break
    call process_control_break
  end if

  ! print line
  write(*, 10) nr_records, date, time, val

  ! compute minimum
  if (val .lt. min_val) then
    ! daily values
    min_time = time
    min_val = val
  end if
  if (val .lt. tmin_val) then
    ! total values
    tmin_date = date
    tmin_time = time
    tmin_val = val
  end if

  ! compute maximum
  if (val .gt. max_val) then 
    ! daily values
    max_time = time
    max_val = val 
  end if
  if (val .gt. tmax_val) then 
    ! total values
    tmax_date = date
    tmax_time = time
    tmax_val = val 
  end if

  nr_val = nr_val + 1
  sum_val = sum_val + val  
  tnr_val = tnr_val + 1
  tsum_val = tsum_val + val  
 
  10 format(5X, i3, 1x, i8, 1x, a, 1x, f3.1)  
end subroutine process_record

subroutine process_control_break
  use glob_vars
  implicit none
  !
  if (date .ne. date_save) then
     call print_daily_summary
  end if  
end subroutine process_control_break

subroutine print_daily_summary
  use glob_vars
  implicit none
  !
  write(*, *)
  write(*, 10) date_save
  write(*, 20) '*  min:', min_time, min_val
  write(*, 20) '*  max:', max_time, max_val
  write(*, 30) sum_val  
  write(*, 40) nr_val
  write(*, 50) sum_val / nr_val  
  write(*, *)

  10 format('*  Summary for date', 1x, i8,':')
  20 format(a7, 10x, a, 1x, f3.1)
  30 format('*  sum:', 9x, f8.2)  
  40 format('*  count:', 7x, I8)
  50 format('*  average:', 5x, f8.4)  

  ! initialize gloabal variables
  min_time = time
  min_val = val
  max_time = time
  max_val = val
  nr_val = 0
  sum_val = 0
end subroutine print_daily_summary

subroutine print_total_summary
  use glob_vars
  implicit none
  !
  write(*, *)
  write(*, 10)
  write(*, 20) '** min:', tmin_date, tmin_time, tmin_val 
  write(*, 20) '** max:', tmax_date, tmax_time, tmax_val  
  write(*, 30) tsum_val  
  write(*, 40) tnr_val
  write(*, 50) tsum_val / tnr_val
  write(*, *)

  10 format('** Summary for all dates:')
  20 format(a7, 2x, i8, 1x, a, 1x, f3.1)
  30 format('** sum:', 9x, f8.2)  
  40 format('** count:', 7x, I8)
  50 format('** average:', 5x, f8.4)
  
end subroutine print_total_summary

subroutine save_keys
  use glob_vars
  implicit none
  !
  date_save = date
end subroutine save_keys 

with this example data

CODE

20101002 15:00 0.4
20101002 16:00 0.4
20101002 17:00 0.4
20101002 18:00 0.7
20101002 19:00 0.8
20101002 20:00 0.8
20101002 21:00 0.6
20101002 22:00 0.4
20101003 15:00 0.1
20101003 16:00 0.2
20101003 17:00 0.3
20101004 18:00 0.9
20101004 19:00 0.8
20101005 20:00 0.8
20101005 21:00 0.6
20101005 22:00 0.4 

the output is:

CODE

$ gfortran control_break2.f95 -o control_break2
$ control_break2
*******************************************************
       1 20101002 15:00 0.4
       2 20101002 16:00 0.4
       3 20101002 17:00 0.4
       4 20101002 18:00 0.7
       5 20101002 19:00 0.8
       6 20101002 20:00 0.8
       7 20101002 21:00 0.6
       8 20101002 22:00 0.4

*  Summary for date 20101002:
*  min:          15:00 0.4
*  max:          19:00 0.8
*  sum:             4.50
*  count:              8
*  average:       0.5625

       9 20101003 15:00 0.1
      10 20101003 16:00 0.2
      11 20101003 17:00 0.3

*  Summary for date 20101003:
*  min:          15:00 0.1
*  max:          17:00 0.3
*  sum:             0.60
*  count:              3
*  average:       0.2000

      12 20101004 18:00 0.9
      13 20101004 19:00 0.8

*  Summary for date 20101004:
*  min:          19:00 0.8
*  max:          18:00 0.9
*  sum:             1.70
*  count:              2
*  average:       0.8500

      14 20101005 20:00 0.8
      15 20101005 21:00 0.6
      16 20101005 22:00 0.4

*  Summary for date 20101005:
*  min:          22:00 0.4
*  max:          20:00 0.8
*  sum:             1.80
*  count:              3
*  average:       0.6000


** Summary for all dates:
** min:  20101003 15:00 0.1
** max:  20101004 18:00 0.9
** sum:             8.60
** count:             16
** average:       0.5375

Processing of 16 lines finished.
******************************************************* 

RE: Fortran code to average hourly data into daily values

@ASRC8367,
Does it work or not?

Red Flag This Post

Please let us know here why this post is inappropriate. Reasons such as off-topic, duplicates, flames, illegal, vulgar, or students posting their homework.

Red Flag Submitted

Thank you for helping keep Tek-Tips Forums free from inappropriate posts.
The Tek-Tips staff will check this out and take appropriate action.

Reply To This Thread

Posting in the Tek-Tips forums is a member-only feature.

Click Here to join Tek-Tips and talk with other members! Already a Member? Login

Close Box

Join Tek-Tips® Today!

Join your peers on the Internet's largest technical computer professional community.
It's easy to join and it's free.

Here's Why Members Love Tek-Tips Forums:

Register now while it's still free!

Already a member? Close this window and log in.

Join Us             Close