Any reason why one can't initialize a local variable using information
obtained from defered array?
-----------------------------
subroutine f(u)
implicit none
integer, dimension(:) :: u
integer :: N=lbound(u,1) ! error
!N=lbound(u,1) ! OK
end subroutine f
------------------------
-------------------------------
$gfortran -std=f2003 -c t3.f90
t3.f90:4.20:
integer :: N=lbound(u,1)
1
Error: Deferred array 'u' at (1) is not permitted in an initialization expression
----------------------------------------
I do not see why the compiler can't generate code to
initialize N at run-time (i.e. just the call to lbound at run-time).
I guess what I am asking is, why is the above initialization not allowed?
Technically speaking. 'N' above is not static variable, and it is not
a constant, so, what is the problem of waiting until run-time to
obtain its initial value?
Why does it have to be known at compile time?
thanks
--Nasser
> Error: Deferred array 'u' at (1) is not permitted in an initialization
> expression
Remark 1: I would call "u" not deferred but assumed-shape array.
> Technically speaking. 'N' above is not static variable,
Technically speaking it is a static variable as Fortran defines:
"Explicit initialization of a variable that is not in a common block
implies the SAVE attribute, which may be confirmed by explicit
specification." (F2008, "5.2.3 Initialization").
> Why does it have to be known at compile time?
Well, the variable has the SAVE attribute - thus must be known at
compile time. But one can also argue: That's because Fortran requires it:
R505 initialization is = constant-expr
or => null-init
or => initial-data-target
And a "7.1.12 Constant expression" has:
"[...]
(4) a specification inquiry where each designator or function argument
[...]
(b) a variable whose properties inquired about are not
(i) assumed,
(ii) deferred, or [...]"
And the bounds are "assumed" in your case, though deferred bounds would
not have been better.
Tobias
PS: Fortran standard available from
http://www.nag.co.uk/sc22wg5/links.html /
http://gcc.gnu.org/wiki/GFortranStandards
Tobias covered the technical aspects from the
standard.
If Richard had seen this, I think he remind you
that initialization is not assignment, even though
the syntax uses an equals sign.
Initialization must be "determinable" at
compile time. Since "u" is a dummy argument,
passed shape at that, its parameters
cannot possibly be determined at compile
time (which you don't argue).
Anything done at run time is *not*, by
definition, initialization. Therefore, you
need to use an assignment. It's really
that simple.
N.B.: Initialization is done once, at program
start-up. Some people mistakenly expect
initialization to be done on every entry to a
subprogram. It's not. Even if you could coerce
the initialization as you wrote it above, you'd
get wrong results on subsequent subroutine
entries because N wouldn't change with "u".
-Ken
-Ken
> I do not see why the compiler can't generate code to
> initialize N at run-time (i.e. just the call to lbound at run-time).
>
> I guess what I am asking is, why is the above initialization not allowed?
If the value changes at the beginning each time the subroutine is
executed, it makes sense to me to put that expression in a regular
executable statement. It would be confusing to put such an
expression in the declaration because it would not be clear what
value it has. Does it have the saved value from the previous
invocation of the subroutine, or does it have the current value
based on u(:).
In this particular case, the value is always 1, so that is not a
good argument. It is the difference between
integer, save :: N=lbound(u,1)
integer, save :: N=1
Both expressions give the same result, but one is allowed and the
other one isn't for the reason above. If you replace lbound() with
ubound(), then it should be clear why the first form is confusing,
right?
A similar kind of confusion would result if you did something like
integer, save :: N
N = ...nonconstant expression...
A programer would look at that and wonder what is the purpose of the
save attribute on a variable that is clearly changed each time it is
in scope.
But if you put the statement in a regular executable statement, then
there is no confusion about what value it has, it always has the
value that it is assigned. If there is no save attribute it is not
saved, and in this case there is no need to save the value, so that
part of the issue is also eliminated.
$.02 -Ron Shepard
> On Mar 29, 11:39 pm, "Nasser M. Abbasi" <n...@12000.org> wrote:
> > Any reason why one can't initialize a local variable using information
> > obtained from defered array?
..
> > I do not see why the compiler can't generate code to
> > initialize N at run-time (i.e. just the call to lbound at run-time).
Because initialization is not a run-time thing. The fact that the
compiler might be able to do something at run-time is thus completely
irrelevant. Yes, the compiler can do such compuations at run time.
That's what it would do if you put it in an assignment statement.
Assignment statements happen at run-time. Initialization doesn't.
> If Richard had seen this, I think he remind you
> that initialization is not assignment, even though
> the syntax uses an equals sign.
[and Ken adds more that indeed quite well sumarizes what I would say,
in simillar words even. I just thought I would add the one extra bit
above].
--
Richard Maine
email: last name at domain . net
domain: summer-triangle
(snip)
> Initialization must be "determinable" at
> compile time. Since "u" is a dummy argument,
> passed shape at that, its parameters
> cannot possibly be determined at compile
> time (which you don't argue).
Since other languages offer initialization for automatic
variable, some believe that Fortran could also do that.
K&R C allowed it only for scalar variables, which made some
sense to me. ANSI C allows it for arrays, too.
> Anything done at run time is *not*, by
> definition, initialization. Therefore, you
> need to use an assignment. It's really
> that simple.
-- glen
(snip)
> If the value changes at the beginning each time the subroutine is
> executed, it makes sense to me to put that expression in a regular
> executable statement. It would be confusing to put such an
> expression in the declaration because it would not be clear what
> value it has. Does it have the saved value from the previous
> invocation of the subroutine, or does it have the current value
> based on u(:).
It seems not confusing in those languages that allow it. Actually,
there are some confusing cases in Java relating to initialization
in constructors. Consider the case where user written functions
were allowed in initialization of automatic variables, and where
the function had access to those variables.
> In this particular case, the value is always 1, so that is not a
> good argument. It is the difference between
> integer, save :: N=lbound(u,1)
> integer, save :: N=1
> Both expressions give the same result, but one is allowed and the
> other one isn't for the reason above. If you replace lbound() with
> ubound(), then it should be clear why the first form is confusing,
> right?
This has been discussed here before, but in some other languages,
which I won't mention, assumed shape arrays assume both the lower
and upper bound from the caller. It does seem more consistent,
though sometimes less convenient for the programmer.
-- glen
Not only C, many other languages. Ada does it very easily.
Here is a small example, where a local variable of a
procedure is initialized to take in the upper bound of
an array (i.e. UBOUND in fortran speak). Same as
what I was trying to do in Fortran.
I guess may be because Fortran local variables have the
automatic SAVE attribute that can complicate this. Although
not sure why. The local variable can have SAVE attribute,
but be changed each time the function is called.
Any way, it would have been a nice feature to have, as it makes
the code much more compact to write. No need to declare
a variable one place, then in the code, somewhere else removed
from the declaration, assign it.
----------------------------------------
with ada.text_io; use ada.text_io;
procedure main is
type array_t is array(integer range<>) of integer;
x : constant array_t(0..2):=(1,2,3);
procedure sub(u : array_t) is
v : constant natural := u'last; -- init to upper index of u
begin
put(integer'image(v));
end;
begin
sub(x); -- call sub with array argument
end main;
--------------------------
When running the above program:
$ ./main.exe
2
--Nasser
No. It is NOT initialization. Please reread the previous
responses. As long as you fail to distinguish initialization
from run-time <anything>, including assignment, you
will keep chasing your tail (figuratively).
Any value that changes value from call to call cannot
reasonably be thought of as an initialization expression.
If you insist on using a personal definition for "initialization"
rather than that of the Fortran standard, you'll be confused
or otherwise dissatisfied.
> I guess may be because Fortran local variables have the
> automatic SAVE attribute that can complicate this. Although
> not sure why. The local variable can have SAVE attribute,
> but be changed each time the function is called.
Again, please reread what was written. As a *general*
statement, NO, local variables are not automatically
given the SAVE attribute. However, local *initialized*
variables are implicitly given the SAVE attribute. In
other words, a small subset of possible local variables
are given the SAVE attribute.
> Any way, it would have been a nice feature to have, as it makes
> the code much more compact to write. No need to declare
> a variable one place, then in the code, somewhere else removed
> from the declaration, assign it.
From a style point of view, and I believe that is the
substance of your complaint, I beg to differ. Having
declarations clearly separated from executable
statements is an aid in understanding the code.
If you needed to go back and sometimes look for
what are essentially run-time assignments in the
declarations of variables, I'd find that most confusing!
I recognize that some other languages allow block-
level declarations, which amounts to mixing
declarations with executable statements. I would
probably avoid that, personally, except in the
most trivial cases.
-Ken
(snip, someone wrote)
>> Not only C, many other languages. Ada does it very easily.
>> Here is a small example, where a local variable of a
>> procedure is initialized to take in the upper bound of
>> an array (i.e. UBOUND in fortran speak). Same as
>> what I was trying to do in Fortran.
> No. It is NOT initialization. Please reread the previous
> responses. As long as you fail to distinguish initialization
> from run-time <anything>, including assignment, you
> will keep chasing your tail (figuratively).
Since the example was Ada, and not Fortran, the Fortran
rules don't apply.
> Any value that changes value from call to call cannot
> reasonably be thought of as an initialization expression.
> If you insist on using a personal definition for "initialization"
> rather than that of the Fortran standard, you'll be confused
> or otherwise dissatisfied.
Again, it seems that in many other languages you can initialize
local (automatic) variables at procedure entry.
Nothing against the Fortran rule, but it does seem to be rare.
-- glen
> Ron Shepard <ron-s...@nospam.comcast.net> wrote:
>
> (snip)
> > If the value changes at the beginning each time the subroutine is
> > executed, it makes sense to me to put that expression in a regular
> > executable statement. It would be confusing to put such an
> > expression in the declaration because it would not be clear what
> > value it has. Does it have the saved value from the previous
> > invocation of the subroutine, or does it have the current value
> > based on u(:).
>
> It seems not confusing in those languages that allow it.
Those languages aren't Fortran.
That is a very serious comment - not just being facietious. You can't
just pul an isolated feature out of a language and evaluate whether it
is confusing independent of context.
Part of the context in Fortran would be that there already exists a
definition of initialization in Fortran. The existing definition does
not work that way, and changing it to work that way is a nonstarter
because it would break existing standard-conforming programs. It would
break *MANY* existing programs - not just some special cases. No way
that is going to happen just because someone happens to think that it
looks nicer.
(Oh, and it also is an important functionality that has no substitute.
By that I'm not talking about just not looking as nice by someone's
estimation. I'm talking about there being no other way to get the job
done. Sometimes you need to do things differently the first time a
subroutine is called; there is no other way to do that.)
So if you add initializations that work differently, but you also keep
the existing cases for compatibility with existing code, then people
will have to learn what distinguishes the two cases. That's guaranteed
to be confusing.... and probably very subtle. Just about the only way to
make it even half workable would be to make a different syntax.... by
which time yout might almost as well use the different syntax we already
have (aka assignment statement).
No, acting differently depending on whether the variable was automatic
or not would not work. That would be incredibly subtle, subject to
version change (change what is allowed in initialization expressions,
and you change that), and even self-contradictory unless you add some
extra exceptions. I.e. Confusing.
> Ron Shepard <ron-s...@nospam.comcast.net> wrote:
>
> (snip)
> > If the value changes at the beginning each time the subroutine is
> > executed, it makes sense to me to put that expression in a regular
> > executable statement. It would be confusing to put such an
> > expression in the declaration because it would not be clear what
> > value it has. Does it have the saved value from the previous
> > invocation of the subroutine, or does it have the current value
> > based on u(:).
>
> It seems not confusing in those languages that allow it.
Ok, is this confusing to you?
ShepardHome$ cat save_init.f90
module sub_mod
contains
subroutine sub()
integer, save :: i=1
i=1
write(*,*) i
i = i + 1
end subroutine sub
end module sub_mod
program save_init
use sub_mod
call sub
call sub
end program save_init
ShepardHome$ gfortran save_init.f90
ShepardHome$ a.out
1
1
Now, remove that i=1 executable statement and see what you get.
ShepardHome$ a.out
1
2
That is the difference between an initialization and an executable
statement.
So like I said above, if the value changes each time you run the
subroutine, it makes sense to me for that to happen in an executable
statement (i.e. at run time). If it needs to be initialized once,
and then keep its value between calls thereafter, then it should be
done in the initialization.
And if you assign the value in an initialization, and then
immediately change it at the beginning of the subroutine, you end up
scratching your head wondering why the value is saved and
initialized, just to have it thrown away immediately thereafter.
You get that WTF feeling.
$.02 -Ron Shepard
Can't simply then compiler then issue an error when there is an
initialization on a variable with SAVE attribute on it?
As you may be know, in C, one can declare a local variable as 'static'
also, which means the local variable value is saved after the call return
But in C, I can still write
static int sum = 0;
Any way, Fortran is different, nothing can be done about it now. End of story ;)
---Nasser
>
> Can't simply then compiler then issue an error when there is an
> initialization on a variable with SAVE attribute on it?
>
> As you may be know, in C, one can declare a local variable as 'static'
> also, which means the local variable value is saved after the call return
>
> But in C, I can still write
>
> static int sum = 0;
>
SOrry, I think the above example is different from Fortran 'SAVE'. I think
the initialization here in C must be known about compile time. So, can't
use to compare to Fortran's.
I'd like to request the above be withdrawn from further considerations.
--Nasser
Since that is not an error, no. Not only is it not an error, it is
recommended practice (at least by me, and I suspect by plenty of others
as well) to specify SAVE whenever you have initialization. As of f90,
any initialized variable is implicitly SAVEd anyway. I prefer to make
the SAVE explicit.
Fortran traditionally (from Fortran I through Fortran 77) used, or
at least allowed for, all variables to be static. Recursion was
not allowed, so usually you wouldn't notice the difference.
(The SAVE statement was added in Fortran 77.)
With Fortran 90 and the addition of recursion (with the required
RECURSIVE keyword) local variables must be automatic. Even so,
without RECURSIVE local variables may still be statically allocated.
The SAVE keyword pretty much guarantees static allocation, but
its absence, without RECURSIVE, doesn't guarantee automatic
allocation. (In the usual computer science meaning of the terms.)
It seems to me that with the addition of the AUTOMATIC keyword,
to override the implied SAVE (sounds better than DONTSAVE) one
could do it.
> But in C, I can still write
> static int sum = 0;
In C, the default is auto (there is a keyword, but rarely used).
If you allow recursion, and don't require a special attribute,
then local variables pretty much have to be automatic.
There is one other case where Fortran requires automatic allocation,
and that is for local arrays with bounds that are not initialization
expressions, or variables with a length parameter that isn't an
initialization expression.
> Any way, Fortran is different, nothing can be done about it now.
> End of story ;)
-- glen
> It seems to me that with the addition of the AUTOMATIC keyword,
> to override the implied SAVE (sounds better than DONTSAVE) one
> could do it.
That is precisely the kind of suggestion that I was thinking someone
would make when I said
>> No, acting differently depending on whether the variable was
>> automatic or not would not work. That would be incredibly subtle,
>> subject to version change (change what is allowed in initialization
>> expressions, and you change that), and even self-contradictory unless
>> you add some extra exceptions. I.e. Confusing.
I'll not try to concoct examples, but you just proposed (well, anyway
suggested that "one could do it") a feature whereby the functionality
substantially changed depending on whether or not a variable was
automatic. The distinction on whether a variable is automatic can depend
on whether or not an expression is an initialization expression. That
can be a *VERY* subtle distinction. The exact test has also changed with
every recent standard (anyway I think it changed again in f2008 - don't
feel like checking).
That's sure confusing in my book - *FAR* more confusing than what is a
trivially simple rule in f66/f77/f90/f95/f2003/f2008 - that
initialization happens only on the first call. That might not be the
rule that some people would like, but it is hard to imagine a simpler
rule than "that's the way it is - always."
--
Richard Maine | Good judgment comes from experience;
email: last name at domain . net | experience comes from bad judgment.
domain: summertriangle | -- Mark Twain
(after I wrote)
>> It seems to me that with the addition of the AUTOMATIC keyword,
>> to override the implied SAVE (sounds better than DONTSAVE) one
>> could do it.
> That is precisely the kind of suggestion that I was thinking
> someone would make when I said
>>> No, acting differently depending on whether the variable was
>>> automatic or not would not work. That would be incredibly subtle,
>>> subject to version change (change what is allowed in initialization
>>> expressions, and you change that), and even self-contradictory unless
>>> you add some extra exceptions. I.e. Confusing.
> I'll not try to concoct examples, but you just proposed (well, anyway
> suggested that "one could do it") a feature whereby the functionality
> substantially changed depending on whether or not a variable was
> automatic.
Well, actually I only said that it had the AUTOMATIC attribute,
which isn't exactly the same. I did check to see if there was
already one (in F2003), and did notice that there are automatic
variables, and that they are required not to have the SAVE
attribute, and not have initializers. It seems, though, that
they don't have the AUTOMATIC keyword (unless added in F2008).
> The distinction on whether a variable is automatic can depend
> on whether or not an expression is an initialization expression. That
> can be a *VERY* subtle distinction. The exact test has also changed with
> every recent standard (anyway I think it changed again in f2008 - don't
> feel like checking).
I didn't check the F2008 change, either.
> That's sure confusing in my book - *FAR* more confusing than what is a
> trivially simple rule in f66/f77/f90/f95/f2003/f2008 - that
> initialization happens only on the first call. That might not be the
> rule that some people would like, but it is hard to imagine a simpler
> rule than "that's the way it is - always."
Well, there are plenty of things that changed from the "way they
have always been," though that doesn't mean that another one
should be added.
-- glen
> Nasser M. Abbasi <n...@12000.org> wrote:
> >
> > Can't simply then compiler then issue an error when there is an
> > initialization on a variable with SAVE attribute on it?
>
> Since that is not an error, no. Not only is it not an error, it is
> recommended practice (at least by me, and I suspect by plenty of others
> as well) to specify SAVE whenever you have initialization. As of f90,
> any initialized variable is implicitly SAVEd anyway. I prefer to make
> the SAVE explicit.
The way I look at it, the SAVE is redundant to the compiler, but it
tells the human looking at the code that the variable is indeed
saved between calls.
I know it is too late now, but I would have preferred that the SAVE
was required and that the compiler is required to tell you when it
is missing. Especially when programmers use other languages with
different semantics, it looks odd to see
integer :: i=1
write(*,*) i
and have the program print something other than 1. Having that SAVE
there tells you why that happens.
$.02 -Ron Shepard
> I know it is too late now, but I would have preferred that the SAVE
> was required and that the compiler is required to tell you when it
> is missing. Especially when programmers use other languages with
> different semantics, it looks odd to see
>
> integer :: i=1
> write(*,*) i
>
> and have the program print something other than 1. Having that SAVE
> there tells you why that happens.
I don't like implicit SAVE either. It was actually done before I was
atending J3 meetings, but I have a pretty good idea of why.
Lots of f77 programs asumed that all variables were SAVEd. Those
programs were not standard conforming, but *LOTS* of them did it. It
turned out to work for enough f77 compilers (not all, but enough) that
people got into the habit.
WIth f90, static allocation of everything started becomming far less
common. The standard pretty much required (as usual, not in those terms)
that many things be allocated dynamically, and factors outside of the
standard were also decreasing the tendency of eveything to be allocated
statically.
In existing f77 codes it was an almost certain bet that an initialized
variables needed to be SAVEd to work as the author intended. I'm not
talking about new codes that someone might write based on the way they
might incorrectly think initialization worked. I'm talking about a very
large number of existing operational codes. And yes, that *IS* the way
things were. I am not speculating or suggesting that this would be the
case based on some guess about how people might think. I worked in that
era and saw the practices used; this one was extremely widespread. As
has come up before, practices in Europe might have been enough different
that my experience doesn't apply as much there, and there were no doubt
isolated groups in the US that had different practices, but the large
majority of US programmers assumed static storage for everything. Heck,
we still occasionally see people in this newsgroup incorrectly stating
that all storage was static in f77, because that's what they were used
to believing or they read somewhere.
F90's implied SAVE for initialized variables allowed those existing
programs to continue working correctly as static storage became less
ubiquitous. In fact, it basically changed those non-standard f77
programs into standard-conforming f90 ones (at least in that regard).
As I mentioned above, I didn't really favor this approach. But I'm quite
confident that's why it was done. Of course, by now things are worse in
a way in that chnaging it would invalidate what are now
standard-conforming programs (and many of them). Changes that invalidate
standard-conforming programs tend to be a hard sell.
<snip: initialization occurs once, at or before first call>
> <snip> The existing definition does
> not work that way, and changing it to work that way is a nonstarter
> because it would break existing standard-conforming programs. <snip>
> (Oh, and it also is an important functionality that has no substitute.
> By that I'm not talking about just not looking as nice by someone's
> estimation. I'm talking about there being no other way to get the job
> done. Sometimes you need to do things differently the first time a
> subroutine is called; there is no other way to do that.)
>
Did something happen to DATA when I wasn't watching?
I'd concede it can be ugly, but it has always worked for me.
>> (Oh, and it also is an important functionality that has no substitute.
>> By that I'm not talking about just not looking as nice by someone's
>> estimation. I'm talking about there being no other way to get the job
>> done. Sometimes you need to do things differently the first time a
>> subroutine is called; there is no other way to do that.)
> Did something happen to DATA when I wasn't watching?
> I'd concede it can be ugly, but it has always worked for me.
DATA implies SAVE, the variables will be initialized once.
Is that what "worked for me" meant?
-- glen
DATA is just another syntax for initialization - not a separate feature.
Perhaps it could have been made otherwise - that DATA retained its old
functionality, while the new syntax in a type declaration meant
something different, but its about 20 years too late for that one, which
would now have the problem of breaking existing standard-conforming
programs.
(I also find DATA ugly, inconsistent, and awkward most of the time. But
there are some cases where its inconsistency happens to facilitate
things.)
> (I also find DATA ugly, inconsistent, and awkward most of the time. But
> there are some cases where its inconsistency happens to facilitate
> things.)
In this particular case, it seems less confusing to see a separate
data statement than to see the initialization on the declaration
line. Maybe that is a good thing.
It might also have been a good idea to have used a slightly
different syntax. Maybe something like
integer :: i /999/
(which I think was a pretty common f77 extension) would have make it
clearer that the initialization is done only once, not each time the
subroutine is executed.
But, as you say, the current syntax has been standardized for 20
years, so it isn't going to change now.
$.02 -Ron Shepard
> It might also have been a good idea to have used a slightly
> different syntax. Maybe something like
>
> integer :: i /999/
>
> (which I think was a pretty common f77 extension) would have make it
> clearer that the initialization is done only once, not each time the
> subroutine is executed.
>
> But, as you say, the current syntax has been standardized for 20
> years, so it isn't going to change now.
That particular syntax has... issues. I think the common f77 extension
draws from the DATA statement. To my knowledge, all it does is paste the
DATA statement syntax onto the type declaration.
A big problem with the DATA statement is the inconsistency that I
briefly alluded to. You don't notice it in the trivially simple cases
like the above example, but the DATA statement values have their own
special syntax different from anything else in the language. Those
values are not expressions of any sort; they are their own special
syntax category. In addition to confusions of meaning (where else in the
language does 2*2 not equal 4?), that means that they don't
automatically extend with any extensions to the definition of
expressions.
Let's see; I forgot that structure constructors got added to the DATA
statement syntax; good thing I checked before mentioning that. In a way
thouh, they just add to the inconsistencies. Looks like you can have
initialization expressions for the elements of a structure constructor,
but you can't have them outside of such a constructor. I have visions of
people making derived types solely for the purpose of allowing
expressions. But trying to allow expressions at the top level might be
awkward because of the "/" delimitters, and would certainly have
problems with the meaning of * in DATA statements; that meaning goes
back a lot more than just 20 years.
When I first read this, the slashes weren't there (must be a
newsreader bug), but then I reply and see them.
Yes, that form was allowed by the OS/360 compilers, and adopted
by some other compilers as an extension. Note that DATA allows:
DATA i,j,k/1,2,3/
but you can't do:
INTEGER i,j,k/1,2,3/
> (which I think was a pretty common f77 extension) would have make it
> clearer that the initialization is done only once, not each time the
> subroutine is executed.
The PL/I form is INITIAL(999), or,
DCL I FIXED DECIMAL(31,0) INITIAL(999);
As with some other lanuages, done onece for STATIC, and each
time for AUTOMATIC.
-- glen
> In addition to confusions of meaning (where else in the
> language does 2*2 not equal 4?),
I'm not disagreeing with your post, but I do know the answer to this:
List directed I/O.
And like data statements, this is why it would be difficult to add
expression evaluation to list-directed I/O (the input part, at
least). If I had the choice in the language, I personally would
*much* rather have expression evaluation built into the language in
list-directed I/O than the ability to specify multiple entries with
the *. Expressions in I/O statements would be extremely useful for
all kinds of applications.
> that means that they don't
> automatically extend with any extensions to the definition of
> expressions.
$.02 -Ron Shepard
> In article <1jzclsc.m92298fioow0N%nos...@see.signature>,
> nos...@see.signature (Richard Maine) wrote:
>
> > In addition to confusions of meaning (where else in the
> > language does 2*2 not equal 4?),
>
> I'm not disagreeing with your post, but I do know the answer to this:
>
> List directed I/O.
Ah yes. I forgot about that one.
It could be done with the addition of a new keyword.
I have suggested this here before, in all probability in a thread wherein
Richard, Glen and Ron were contributing, as now. On that occaision my
arguments were trashed due to the name of the new keyword I proposed. So...
Suppose we refer to the new keyword as XXXXXX. Then the syntax might look
something like this:
Integer, XXXXXX :: i = 1
Which I propose would mean "I is a local variable, and is initialized to 1
every time the procedure is called".
Personally, I would find this extremely useful, because it allows such
assignments to be seen on the same statement as the declaration. When you
are looking at a long procedure with 50 or more local variables and
pointers, it helps *a lot* to have declaration and assignment on the same
line. It would also allow folk who are more familiar with how other
languages behave, to get the effect they want and expect in Fortran.
Yes I know its too late for F2003 and 2008. But, bloody hell, I'm only 58,
maybe I'll actually get to use an F201x compiler!
--
Qolin
Email: my qname at domain dot com
Domain: qomputing
(snip on initialized non-static data)
> It could be done with the addition of a new keyword.
> I have suggested this here before, in all probability in a thread wherein
> Richard, Glen and Ron were contributing, as now. On that occaision my
> arguments were trashed due to the name of the new keyword I proposed. So...
> Suppose we refer to the new keyword as XXXXXX. Then the syntax might look
> something like this:
> Integer, XXXXXX :: i = 1
> Which I propose would mean "I is a local variable, and is
> initialized to 1 every time the procedure is called".
> Personally, I would find this extremely useful, because it allows such
> assignments to be seen on the same statement as the declaration. When you
> are looking at a long procedure with 50 or more local variables and
> pointers, it helps *a lot* to have declaration and assignment on the same
> line. It would also allow folk who are more familiar with how other
> languages behave, to get the effect they want and expect in Fortran.
I suppose, but usually when you get to many variables, you use
an array or structure. In C, there is no array assignment, which
makes array initialization especially useful. Even so, in K&R
(pre-ANSI) C, only static arrays could be initialized.
Java also allows for initializing automatic (local) arrays,
but not for array assignment.
To initialize an automatic array, the compiler has to allocate
space to store the initial data, plus the space for the array.
On the other hand, Fortran can generate array constants to give
a value to an automatic array in an assignment statement.
That greatly reduces the need for automatic variable initialization.
I forget if you can make a structure constant to assign values
to a structure in one assignment.
> Yes I know its too late for F2003 and 2008. But, bloody hell,
> I'm only 58, maybe I'll actually get to use an F201x compiler!
I might even last to a F202x compiler.
-- glen
> List directed I/O.
> And like data statements, this is why it would be difficult to add
> expression evaluation to list-directed I/O (the input part, at
> least). If I had the choice in the language, I personally would
> *much* rather have expression evaluation built into the language in
> list-directed I/O than the ability to specify multiple entries with
> the *. Expressions in I/O statements would be extremely useful for
> all kinds of applications.
For the syntax of the READ statement, that would be fairly
straightforward: Use something that is a syntax error
right now, such as a Format string without parenthesis or
FMT=: .
The semantics would need some working, though. For example,
which precision would the expression take?