Hey, I wrote this (fortran) with the aim of finding the minimum spanning tree of a bunch of point开发者_JS百科s (syscount of them). I know for a fact that this approach works, since i wrote it in javascript earlier today. js is slow though, and i wanted to see how much faster fortran would be!! only problem is it's not working, i'm getting an annoying error;
prims.f95:72.43:
if((check == 1) .and. (path(nodesin(j))(k) < minpath)) then
1
Error: Expected a right parenthesis in expression at (1)
What the hell is that about?! the 43rd character on the line is the "h" of "path"
nodesin(1) = 1
do i = 1,syscount-1
pathstart = -1
pathend = -1
minpath = 2000
do j = 1,i
do k = 1, syscount
check = 1
do l = 1, i
if(nodesin(l) == k) then
check = 0
end if
end do
if((check == 1) .and. (path(nodesin(j))(k) < minpath)) then
minpath = path(nodesin(j))(k)
pathstart = nodesin(j)
pathend = k
end if
end do
end do
nodesin(i+1) = pathend
minpaths(i)(1) = pathstart
minpaths(i)(2) = pathend
end do
Also, i'm fairly new to fortran, so i have a few other questions;
can i use && instead of .and. ?
is there a versions of the for(object in list){} loop found in many other languages?
is there a verion of the php function in_array ? i.e. bool in_array(needle,haystack), and if there is, is there a better way of doing it than:
check = false
Asize = size(array)
do i = 1, Asize
if(array(i) == needle) then
check = true
end if
end do
then to using the check variable to see if it's there?
(I haven't posted anything on stackoverflow before. please don't get angry if i've broken loads of etiquette things!)
It looks like you have defined path
and minpaths
as two-dimensional arrays. Multi-dimensional arrays are accessed differently in Fortran when compared to C-like languages. In Fortran you separate the indices by commas within one set of parentheses.
I'm guessing by the use of these variables they are integer arrays. Here is how you access elements of those arrays (since you didn't share your variable declarations I am making up the shape of these arrays):
integer :: path(n1, n2)
integer :: minpaths(n3, 2)
your if statement should be:
if((check == 1) .and. (path(nodesin(j), k) < minpath)) then
your access to minpaths should be:
minpaths(i, 1) = pathstart
minpaths(i, 2) = pathend
Also, if you are not using IMPLICIT NONE
I recommend you consider it. Not using it is dangerous, and you are using variable names that are close to each other (minpath
and minpaths
). You could save hours of hair pulling debugging by using IMPLICIT NONE
.
While .EQ. can be replaced with ==, there is still only .AND.
For your code block to check whether a "variable is there", you can use "where" and have much shorter code!
In Fortran >= 90 statements and functions can operate on arrays so that explicit loops don't have to be used as frequently.
There is no for (object in list), but using the where statement can do something very similar.
Many of the intrinsic functions that act on arrays also take masks as optional arguments to selectively operate.
I suggest reading a book to learn about these features. I like the one by Metcalf, Reid and Cohen. In the meantime, the second Wikipedia article may help: http://en.wikipedia.org/wiki/Fortran_95_language_features
精彩评论