我试图从一个C文件(gpt2_1w.f
)调用一个Fortran子例程(main.c
)。问题是,在Fortran代码的一部分中,它需要打开并从名为gpt2_1wA.grd
的网格文件中读取一些值。 C程序可以毫无问题地调用一些基本级别的Fortran子例程,但是当涉及到Fortran的一些网格或Ascii文件时,它会给出_gfortran_at_open...etc
的未定义引用等错误。我同时使用了codeblocks和cygwin。也许我错过了一些库或者必须以某种方式在C代码中声明网格文件......我不确定。
这是我调用Fortran子例程的C代码:
的main.c
#include <stdio.h>
#include <math.h>
#define Pi 3.14159265358979
#define d2r (Pi/180.)
#define r2d (180./Pi)
//fortran sub//
void gpt2_1w_(double *dmjd, double *dlat,double *dlon, double *hell, double *nstat, double *it, double *p, double *T, double *dT, double *Tm, double *e, double *ah, double *aw, double *la, double *undu);
int main()
{
double dmjd = 55055;
double lat = 36.256;
double lon = 32.589;
double hell = 812.253;
double nstat = 1.0;
double it = 0.0;
double dlat=lat*d2r;
double dlon=lon*d2r;
double p, T, dT, Tm, e, ah, aw, la, undu;
//calling fortran sub//
gpt2_1w_(&dmjd, &dlat, &dlon, &hell, &nstat, &it, &p, &T, &dT, &Tm, &e, &ah, &aw, &la, &undu);
printf( "pressure = %15.8f\n", p );
printf( "Mean Temp = %15.8f\n", T );
return 0;
}
这里是整个Fortran代码:
subroutine gpt2_1w (dmjd,dlat,dlon,hell,nstat,it,
. p,T,dT,Tm,e,ah,aw,la,undu)
implicit double precision (a-h,o-z)
double precision lagrid(64800,5),la(64800),lal(4)
dimension vec(44)
dimension dlat(64800),dlon(64800),hell(64800)
dimension dT(64800),T(64800),p(64800),e(64800),
. ah(64800),aw(64800),undu(64800),Tm(64800)
dimension pgrid(64800,5),Tgrid(64800,5),Qgrid(64800,5),
. dTgrid(64800,5),u(64800),Hs(64800),ahgrid(64800,5),
. awgrid(64800,5),Tmgrid(64800,5)
dimension undul(4),Ql(4),dTl(4),Tl(4),pl(4),ahl(4),awl(4),Tml(4)
. ,el(4)
dimension indx(4)
character line*80
c% mean gravity in m/s**2
gm = 9.80665d0;
c% molar mass of dry air in kg/mol
dMtr = 28.965d-3
c% universal gas constant in J/K/mol
Rg = 8.3143d0
pi = 3.1415926535d0
c% change the reference epoch to January 1 2000
dmjd1 = dmjd-51544.5d0
c% factors for amplitudes
if (it.eq.1) then ! constant parameters
cosfy = 0.d0
coshy = 0.d0
sinfy = 0.d0
sinhy = 0.d0
else
cosfy = dcos(dmjd1/365.25d0*2.d0*pi)
coshy = dcos(dmjd1/365.25d0*4.d0*pi)
sinfy = dsin(dmjd1/365.25d0*2.d0*pi)
sinhy = dsin(dmjd1/365.25d0*4.d0*pi)
end if
c% read gridfile
open(11,file='gpt2_1wA.grd')
c% read first comment line
read (11,'(a80)') line
c% loop over grid points
do n = 1,64800
!% read data line
read (11,*) vec
pgrid(n,1:5) = vec(3:7) !% pressure in Pascal
Tgrid(n,1:5) = vec (8:12) !% temperature in Kelvin
Qgrid(n,1:5) = vec(13:17)/1000.d0 !% specific humidity in kg/kg
dTgrid(n,1:5) = vec(18:22)/1000.d0 !% temperature lapse rate in Kelvin/m
u(n) = vec(23) !% geoid undulation in m
Hs(n) = vec(24) !% orthometric grid height in m
ahgrid(n,1:5) = vec(25:29)/1000.d0 !% hydrostatic mapping function coefficient, dimensionless
awgrid(n,1:5) = vec(30:34)/1000.d0 !% wet mapping function coefficient, dimensionless
lagrid(n,1:5) = vec(35:39) !% water vapour decrease factor, dimensionless
Tmgrid(n,1:5) = vec(40:44) !% weighted mean temperature, Kelvin
end do
close (11)
c% loop over stations
do k = 1,nstat
!% only positive longitude in degrees
if (dlon(k).lt.0.d0) then
plon = (dlon(k) + 2.d0*pi)*180.d0/pi
else
plon = dlon(k)*180.d0/pi
end if
!% transform to polar distance in degrees
ppod = (-dlat(k) + pi/2.d0)*180.d0/pi
!% find the index (line in the grid file) of the nearest point
ipod = floor(ppod+1.d0)
ilon = floor(plon+1.d0)
!% normalized (to one) differences, can be positive or negative
diffpod = ppod - (ipod - 0.5d0)
difflon = plon - (ilon - 0.5d0)
!% added by HCY
if (ipod.eq.181) then
ipod = 180
end if
!% added by GP
if (ilon.eq.361) then
ilon = 1
end if
if (ilon.eq.0) then
ilon = 360
end if
!% get the number of the corresponding line
indx(1) = (ipod - 1)*360 + ilon
!% near the poles: nearest neighbour interpolation, otherwise: bilinear
!% with the 1 degree grid the limits are lower and upper (GP)
ibilinear = 0
if ((ppod.gt.(0.5d0)).and.(ppod.lt.(179.5d0))) then
ibilinear = 1
end if
!% case of nearest neighborhood
if (ibilinear.eq.0) then
ix = indx(1);
!% transforming ellipsoidal height to orthometric height
undu(k) = u(ix)
hgt = hell(k)-undu(k)
!% pressure, temperature at the height of the grid
T0 = Tgrid(ix,1) +
. Tgrid(ix,2)*cosfy + Tgrid(ix,3)*sinfy +
. Tgrid(ix,4)*coshy + Tgrid(ix,5)*sinhy
p0 = pgrid(ix,1) +
. pgrid(ix,2)*cosfy + pgrid(ix,3)*sinfy+
. pgrid(ix,4)*coshy + pgrid(ix,5)*sinhy
!% specific humidity
Q = Qgrid(ix,1) +
. Qgrid(ix,2)*cosfy + Qgrid(ix,3)*sinfy+
. Qgrid(ix,4)*coshy + Qgrid(ix,5)*sinhy
!% lapse rate of the temperature
dT(k) = dTgrid(ix,1) +
. dTgrid(ix,2)*cosfy + dTgrid(ix,3)*sinfy+
. dTgrid(ix,4)*coshy + dTgrid(ix,5)*sinhy
!% station height - grid height
redh = hgt - Hs(ix)
!% temperature at station height in Celsius
T(k) = T0 + dT(k)*redh - 273.15d0
!% temperature lapse rate in degrees / km
dT(k) = dT(k)*1000.d0
!% virtual temperature in Kelvin
Tv = T0*(1+0.6077d0*Q)
c = gm*dMtr/(Rg*Tv)
!% pressure in hPa
p(k) = (p0*exp(-c*redh))/100.d0
!% hydrostatic coefficient ah
ah(k) = ahgrid(ix,1) +
. ahgrid(ix,2)*cosfy + ahgrid(ix,3)*sinfy+
. ahgrid(ix,4)*coshy + ahgrid(ix,5)*sinhy
!% wet coefficient aw
aw(k) = awgrid(ix,1) +
. awgrid(ix,2)*cosfy + awgrid(ix,3)*sinfy +
. awgrid(ix,4)*coshy + awgrid(ix,5)*sinhy
!% water vapour decrease factor la - added by GP
la(k) = lagrid(ix,1) +
. lagrid(ix,2)*cosfy + lagrid(ix,3)*sinfy +
. lagrid(ix,4)*coshy + lagrid(ix,5)*sinhy
!% mean temperature of the water vapor Tm - added by GP
Tm(k) = Tmgrid(ix,1) +
. Tmgrid(ix,2)*cosfy + Tmgrid(ix,3)*sinfy +
. Tmgrid(ix,4)*coshy + Tmgrid(ix,5)*sinhy
!% water vapor pressure in hPa - changed by GP
e0 = Q*p0/(0.622d0+0.378d0*Q)/100.d0 !% on the grid
e(k) = e0*(100.d0*p(k)/p0)**(la(k)+1) ! % on the station height - (14) Askne and Nordius, 1987
else !% bilinear interpolation
ipod1 = ipod + int(sign(1.d0,diffpod))
ilon1 = ilon + int(sign(1.d0,difflon))
!% changed for the 1 degree grid (GP)
if (ilon1.eq.361) then
ilon1 = 1
end if
if (ilon1.eq.0) then
ilon1 = 360
end if
!% get the number of the line
indx(2) = (ipod1 - 1)*360 + ilon !% along same longitude
indx(3) = (ipod - 1)*360 + ilon1 !% along same polar distance
indx(4) = (ipod1 - 1)*360 + ilon1 !% diagonal
do l = 1,4
!% transforming ellipsoidal height to orthometric height:
!% Hortho = -N + Hell
undul(l) = u(indx(l))
hgt = hell(k)-undul(l)
!% pressure, temperature at the height of the grid
T0 = Tgrid(indx(l),1) +
. Tgrid(indx(l),2)*cosfy + Tgrid(indx(l),3)*sinfy +
. Tgrid(indx(l),4)*coshy + Tgrid(indx(l),5)*sinhy
p0 = pgrid(indx(l),1) +
. pgrid(indx(l),2)*cosfy + pgrid(indx(l),3)*sinfy +
. pgrid(indx(l),4)*coshy + pgrid(indx(l),5)*sinhy
!% humidity
Ql(l) = Qgrid(indx(l),1) +
. Qgrid(indx(l),2)*cosfy + Qgrid(indx(l),3)*sinfy +
. Qgrid(indx(l),4)*coshy + Qgrid(indx(l),5)*sinhy
!% reduction = stationheight - gridheight
Hs1 = Hs(indx(l))
redh = hgt - Hs1
!% lapse rate of the temperature in degree / m
dTl(l) = dTgrid(indx(l),1) +
. dTgrid(indx(l),2)*cosfy + dTgrid(indx(l),3)*sinfy +
. dTgrid(indx(l),4)*coshy + dTgrid(indx(l),5)*sinhy
!% temperature reduction to station height
Tl(l) = T0 + dTl(l)*redh - 273.15d0
!% virtual temperature
Tv = T0*(1+0.6077d0*Ql(l))
c = gm*dMtr/(Rg*Tv)
!% pressure in hPa
pl(l) = (p0*exp(-c*redh))/100.d0
!% hydrostatic coefficient ah
ahl(l) = ahgrid(indx(l),1) +
. ahgrid(indx(l),2)*cosfy + ahgrid(indx(l),3)*sinfy +
. ahgrid(indx(l),4)*coshy + ahgrid(indx(l),5)*sinhy
!% wet coefficient aw
awl(l) = awgrid(indx(l),1) +
. awgrid(indx(l),2)*cosfy + awgrid(indx(l),3)*sinfy +
. awgrid(indx(l),4)*coshy + awgrid(indx(l),5)*sinhy
!% water vapor decrease factor la - added by GP
lal(l) = lagrid(indx(l),1) +
. lagrid(indx(l),2)*cosfy + lagrid(indx(l),3)*sinfy +
. lagrid(indx(l),4)*coshy + lagrid(indx(l),5)*sinhy
!% mean temperature of the water vapor Tm - added by GP
Tml(l) = Tmgrid(indx(l),1) +
. Tmgrid(indx(l),2)*cosfy + Tmgrid(indx(l),3)*sinfy +
. Tmgrid(indx(l),4)*coshy + Tmgrid(indx(l),5)*sinhy
!% water vapor pressure in hPa - changed by GP
e0 = Ql(l)*p0/(0.622d0+0.378d0*Ql(l))/100.d0 !% on the grid
el(l) = e0*(100.d0*pl(l)/p0)**(lal(l)+1.d0) !% on the station height (14) Askne and Nordius, 1987
end do
dnpod1 = abs(diffpod) !% distance nearer point
dnpod2 = 1.d0 - dnpod1 !% distance to distant point
dnlon1 = abs(difflon)
dnlon2 = 1.d0 - dnlon1
!% pressure
R1 = dnpod2*pl(1)+dnpod1*pl(2)
R2 = dnpod2*pl(3)+dnpod1*pl(4)
p(k) = dnlon2*R1+dnlon1*R2
!% temperature
R1 = dnpod2*Tl(1)+dnpod1*Tl(2)
R2 = dnpod2*Tl(3)+dnpod1*Tl(4)
T(k) = dnlon2*R1+dnlon1*R2
!% temperature in degree per km
R1 = dnpod2*dTl(1)+dnpod1*dTl(2)
R2 = dnpod2*dTl(3)+dnpod1*dTl(4)
dT(k) = (dnlon2*R1+dnlon1*R2)*1000.d0
!% water vapor pressure in hPa - changed by GP
R1 = dnpod2*el(1)+dnpod1*el(2)
R2 = dnpod2*el(3)+dnpod1*el(4)
e(k) = dnlon2*R1+dnlon1*R2
!% hydrostatic
R1 = dnpod2*ahl(1)+dnpod1*ahl(2)
R2 = dnpod2*ahl(3)+dnpod1*ahl(4)
ah(k) = dnlon2*R1+dnlon1*R2
!% wet
R1 = dnpod2*awl(1)+dnpod1*awl(2)
R2 = dnpod2*awl(3)+dnpod1*awl(4)
aw(k) = dnlon2*R1+dnlon1*R2
!% undulation
R1 = dnpod2*undul(1)+dnpod1*undul(2)
R2 = dnpod2*undul(3)+dnpod1*undul(4)
undu(k) = dnlon2*R1+dnlon1*R2
!% water vapor decrease factor la - added by GP
R1 = dnpod2*lal(1)+dnpod1*lal(2)
R2 = dnpod2*lal(3)+dnpod1*lal(4)
la(k) = dnlon2*R1+dnlon1*R2
!% mean temperature of the water vapor Tm - added by GP
R1 = dnpod2*Tml(1)+dnpod1*Tml(2)
R2 = dnpod2*Tml(3)+dnpod1*Tml(4)
Tm(k) = dnlon2*R1+dnlon1*R2
end if
end do
end subroutine
这是我从Fortran读取并希望从C中读取的网格文件的结构:
% lat lon p:a0 A1 B1 A2 B2 T:a0 A1 B1 A2 B2 Q:a0 A1 B1 A2 B2 dT:a0 A1 B1 A2 B2 undu Hs h:a0 A1 B1 A2 B2 w:a0 A1 B1 A2 B2 lam:a0 A1 B1 A2 B2 Tm:a0 A1 B1 A2 B2
89.5 0.5 101472 114 431 -221 -128 259.2 -13.3 -6.1 2.4 0.3 1.64 -1.63 -0.68 0.51 0.35 1.3 7.0 3.1 -0.5 1.9 15.05 0.00 1.1870 -0.0351 -0.0128 0.0053 0.0034 0.5796 0.0084 0.0093 0.0005 0.0042 1.6682 -0.7893 -0.3329 0.0769 -0.1810 254.8 -9.8 -4.3 2.2 1.1
89.5 1.5 101471 114 431 -220 -128 259.2 -13.3 -6.1 2.4 0.3 1.64 -1.63 -0.68 0.51 0.35 1.3 7.0 3.1 -0.5 1.9 15.04 0.00 1.1870 -0.0351 -0.0128 0.0053 0.0034 0.5796 0.0084 0.0092 0.0005 0.0042 1.6682 -0.7894 -0.3321 0.0761 -0.1812 254.8 -9.8 -4.3 2.2 1.1
89.5 2.5 101471 114 431 -220 -128 259.2 -13.3 -6.1 2.4 0.3 1.64 -1.63 -0.68 0.51 0.35 1.3 7.0 3.1 -0.5 1.9 15.04 0.00 1.1870 -0.0351 -0.0128 0.0053 0.0034 0.5796 0.0084 0.0093 0.0005 0.0042 1.6690 -0.7890 -0.3318 0.0757 -0.1813 254.8 -9.8 -4.3 2.2 1.1
我从C:
中读取与网格文件相关的错误||=== Build: Debug in gpt2_1w (compiler: GNU GCC Compiler) ===|
obj\Debug\gpt2_1w.o||In function `gpt2_1w_':|
gpt2_1w.f|167|undefined reference to `_gfortran_st_open'|
gpt2_1w.f|170|undefined reference to `_gfortran_st_read'|
gpt2_1w.f|170|undefined reference to `_gfortran_transfer_character'|
gpt2_1w.f|170|undefined reference to `_gfortran_st_read_done'|
gpt2_1w.f|176|undefined reference to `_gfortran_st_read'|
gpt2_1w.f|176|undefined reference to `_gfortran_transfer_array'|
gpt2_1w.f|176|undefined reference to `_gfortran_st_read_done'|
gpt2_1w.f|189|undefined reference to `_gfortran_st_close'|
我希望得到任何帮助,并提前感谢。