First of all, thank you @everythingfunctional for your efforts concerning varying strings. I realize this thread is some months old, but I see no reason not to “revive” it, so please let me add my two humble bits.
This is a topic I had in mind for years, but always postponed implementing a module for making varying-length strings less of a mess. And since allocatable strings do work as an elegant solution is normal cases, the real problem is arrays of varying-length strings, which is not a top priority (I don’t have to deal with them too often.) However in a recent project of mine I really needed such arrays, and I found this project to be a reliable solution. There are some limitations, but I didn’t expect a “magical” module that will let me use varying-length strings exactly as normal strings.
The first limitation is assignment. As others pointed out already, this won’t work (and in fact I didn’t expect it to work):
type(varying_string), dimension(3) :: str_vector
str_vector=["foo", "foofoo", "yet another foo"]
This works, of course:
type(varying_string), dimension(3) :: str
str_vector(1)="foo"; str_vector(2)="foofoo"; str_vector(3)="yet another foo"
It’s not very elegant, but I can think of ways that will automate this (maybe worth prototyping as an extension?)
Now, I’m not happy with the ISO (as I’m sure many others are.) I think it’s actually half-baked, and it could be much, much better. But I guess it is what it is, so let’s deal with it using extensions.
@everythingfunctional added extensions so that varying-length strings can be used in print
, read
or write
statements. This is a very welcomed addition. In version 4.0.0 print *,str_vector
actually works, but since that version is not recommended, I switched to 3.0.4 where print *,str_vector
doesn’t work. Using char
to convert a varying-length string to a “normal” one works, and it actually allows (a)
formats but for the vector str_vector
I used as an example above this won’t work:
print "(3a)",char(str_vector)
apparently because char
is not elemental. In version 4.0.0 gfortran accepts this but it prints nothing; in version 3.0.4 the compiler issues an error, which is better. So, to print a vector of varying_string
s one needs to do something like this
print "('Strings: ',2(a,', '),a)", char(str_vector(1)), char(str_vector(2)), char(str_vector(3))
which is not very elegant (and it actually reminds me the way you print arrays of “strings” in C.) Please correct me if there is another way to do this.
Again, I can think of ways that will automate this for any vector size, and maybe it is worth prototyping.
All the above are for vectors only. Arrays of such kind are obviously harder to prototype but vectors are probably the case most people will need (and there is always reshape
for arrays.)