Is this cursed formatting?

One thing I miss a lot about Fortran compared to other languages I use is to declare variables at any point in time, and to have those variables automatically scoped to the block in which they’re declared (in an if, for example). This can be great for locality, descriptive names, etc., but in Fortran the only way to achieve this that I’m aware of is the block construct. The problem with that is that standard indentation would cause you to double indent the contents.

if (something) then
    block
        integer :: blah
        blah = foo( &
            bar, &
            baz, &
            whatever &
        )
        ! use blah
        ! ...
    end block
end if

I came up with this and I can’t decide if I hate it or love it. Thoughts?

if (something) then; block
    integer :: blah
    blah = foo( &
        bar, &
        baz, &
        whatever &
    )
    ! use blah
    ! ...
end block; end if
  • Cursed
  • Not cursed
0 voters

I voted not cursed. In general indentation is good, but multiple levels of indentation can lead to long lines or continuation lines, which reduce readability.

Also possible is

if (something) then
    block
    integer :: blah
    blah = foo( &
        bar, &
        baz, &
        whatever &
    )
    ! use blah
    ! ...
    end block
end if

ETA: I like the suggestion of @PierU below more.

Or the other way:

if (something) then
block
    integer :: blah
    blah = foo( &
        bar, &
        baz, &
        whatever &
    )
    ! use blah
    ! ...
end block
end if
3 Likes

Or using macros:

#define _IFB_(C) if (C) then ; block
#define _END_IFB_ end block ; end if


_IFB_ (something)
    integer :: blah
    blah = foo( &
        bar, &
        baz, &
        whatever &
    )
    ! use blah
    ! ...
_END_IFB_
1 Like

For simple cases like the one you describe you can achieve something similar with the associate construct.

And if you are not completely allergic to it you can create your preprocessor macro that adds the block for you (I was too slow :grin:)

#define iff(condition) if (condition) then; block
#define endiff end block; end if
1 Like

I like this. I already format select case constructs with de-indented case labels

select case (foo)
case (bar)
    ! code
case (baz)
    ! code
end select

I started doing this when I encountered it as the go fmt style, and now use it for all switch-like constructs.

I was trying to think of where this idea came from in my head. I think it’s an extension of cuddled braces from more Go style.

What would really be great is if one didn’t need explicit block/endblock at all inside block IFs, block DO loops and so on. But this has been debated ever since ALGOL-60 came out…

I actually think that it’s perfectly fine to NOT indent some constructs when it does not alter the readability (typically when they begin and end together). Similarly, I sometimes don’t indent perfectly nested loops:

do i = ...
do j = ...
do k = ...
   a(k,j,i) = ...
end do
end do
end do

But:

do i = ...
  x = some_function(i)
  do j = ...
  do k = ...
     a(k,j,i) = ...
  end do
  end do
end do

Indeed: Allow declaration statements anywhere · Issue #81 · j3-fortran/fortran_proposals · GitHub

But it seems that it could break some codes: Allow declaration statements anywhere · Issue #81 · j3-fortran/fortran_proposals · GitHub

This is a case where a deprecated feature (DATA statements anywhere in the code) prevents designing a new feature (implicit BLOCKs).

1 Like