I'm doing an assignment for a class where we need to write a program using allocatable arrays to hold an arbitrary number of x and y data pairs, allocate the extent of the arrays accordingly, and then calculate the correlation coefficient of the line it produces. What I have so far is this:
!Calculate Correlation Coefficient
program array2
implicit none
!Variables Used:
! x = x array
! y = y array
! n = length of the file/# of x,y pairs
real, allocatable :: x(:)
real, allocatable :: y(:)
integer, parameter :: lun1=1
integer :: n=0
integer :: i,max_val
integer :: ierror=0
real :: sum_x,sum_y,sum_x2,sum_y2,sum_xy,x_mean,y_mean,m,b,R
! Open the file
open(unit=lun1,file='xyfile.dat',status='old',iostat=ierror)
if(ierror /= 0) then
write(*,*) "Could not read file"
stop 1
endif
! Get length of file (# of x,y pairs)
do while(ierror==0)
read(lun1,*,iostat=ierror) max_val
if(ierror==0) then
n=n+1
else
exit
endif
enddo
allocate (x(n)) !allocate space for x array
allocate (y(n)) !allocate space for y array
rewind(lun1)
do i=1,n,1
read(lun1,*) x(i)
enddo
do i=1,n,1
read(lun1,*) y(i)
enddo
close(unit=lun1) !close the file
! Precalculate sum(xy)
sum_xy=0
do i=1,n
sum_xy=sum_xy+(x(i)*y(i))
enddo
! Precalculate sum(x)
sum_x=0
do i=1,n
sum_x=sum_x+x(i)
enddo
! Precalculate sum(y)
sum_y=0
do i=1,n
sum_y=sum_y+y(i)
enddo
! Precalculate sum (x^2)
sum_x2=0
do i=1,n
sum_x2=sum_x2+(x(i)*x(i))
enddo
! Precalculate sum (y^2)
sum_y2=0
do i=1,n
sum_y2=sum_y2+(y(i)*y(i))
enddo
! Precalculate mean x and mean y
x_mean=sum_x/n
y_mean=sum_y/n
! Calculate slope
m=(sum_xy-(sum_x*y_mean))/(sum_x2-(sum_x*x_mean))
! Calculate intercept
b=y_mean-(m*x_mean)
! Calculate R
R=((n*(sum_xy))-(sum_x*sum_y))/sqrt((n*sum_x2)-(sum_x**2.0)*(n*sum_y2)-(sum_y**2.0))
write (*,*) "The correlation coefficient R =", R
deallocate (x)
deallocate (y)
stop 0
end program array2
It compiles fine (using fortran 90 and gfortran), and I created a test file called xyfile.dat to try it out, but I'm getting this error message:
At line 48 of file array2.f90 (unit = 1, file = 'xyfile.dat')
Fortran runtime error: End of file
Error termination. Backtrace:
#0 0x7f7aa5786f3a
#1 0x7f7aa5787a45
#2 0x7f7aa57881bc
#3 0x7f7aa584b3a3
#4 0x7f7aa5846109
#5 0x4012f5
#6 0x40181a
#7 0x7f7aa50bdf44
#8 0x400c48
#9 0xffffffffffffffff
What am I missing? My fake file has 20 lines of xy pairs, and an enter at the end (which I've seen as a suggestion), and it's a file that's worked with other code, so I'm not sure what's going on. Please keep in mind that I am extremely new to this, so obvious things might not be obvious to me. Any help is appreciated!
Also, somewhat unrelated, I'm not sure if I need to calculate the slope or intercept, but a friend of mine who was helping me said to put it in based on the assignment information, so let's just ignore that for now if it's not causing the error. :)
If I've understood you correctly the error might be here ...
do i=1,n,1
read(lun1,*) x(i)
enddo
do i=1,n,1
read(lun1,*) y(i)
enddo
The first loop reads each line in the file and gets an x
value from it. It ignores any value on the line after the first value. When the next loop starts the you've already read all the lines in the file, and there are no more to read the y
values from. You probably ought to write
do i=1,n,1
read(lun1,*) x(i), y(i)
enddo
and read both the x
and y
values from each line before reading the next.
Incidentally, if you plan to edit this question or to ask others, try to get into the habit of showing us which line the compiler barfs on, don't expect us to be able to count up to 48.