Code Comments
Programming Forum and web based access to our favorite programming groups.Hi, I have several hundred binary WRITE statements in the form WRITE(IUNIT)A,B,C,D. For debugging, I would like to write these in ASCII. I know I can do this with an IF statement: IF(doASCII) THEN WRITE(IUNIT,*)A,B,C,D ELSE WRITE(IUNIT)A,B,C,D ENDIF but this requires recoding every single WRITE statement. It seems that there should be a way to do something like this at the top of the file... IF(doASCII)THEN IO_CONTROL_STRING = "*" ELSE IO_CONTROL_STRING = " " ENDIF and then simply add the control string to the WRITE... WRITE(IUNIT,IO_CONTROL_STRING)A,B,C,D Unfortunately, the above does not work. Is there any way to incorporate a variable IO control string in a WRITE statement? Thanks, Ron
Post Follow-up to this message"Ron G." wrote: > > Hi, > > I have several hundred binary WRITE statements in the form > WRITE(IUNIT)A,B,C,D. For debugging, I would like to write these in > ASCII. I know I can do this with an IF statement: > > IF(doASCII) THEN > WRITE(IUNIT,*)A,B,C,D > ELSE > WRITE(IUNIT)A,B,C,D > ENDIF > > but this requires recoding every single WRITE statement. > > It seems that there should be a way to do something like this at the > top of the file... > > IF(doASCII)THEN > IO_CONTROL_STRING = "*" > ELSE > IO_CONTROL_STRING = " " > ENDIF > > and then simply add the control string to the WRITE... > WRITE(IUNIT,IO_CONTROL_STRING)A,B,C,D > > Unfortunately, the above does not work. Is there any way to > incorporate a variable IO control string in a WRITE statement? > > Thanks, > Ron As far as I know, there is none. The reason is, if I understand such matters correctly, that writing to a formatted file is a completely different process than writing to an unformatted file, even though the _textual_ change to your source code seems minimal. Because of these completely different processes a runtime switch like the one you are looking for is simply impossible. Regards, Arjen
Post Follow-up to this messagergiordano@petrotel.com (Ron G.) writes: > IF(doASCII) THEN > WRITE(IUNIT,*)A,B,C,D > ELSE > WRITE(IUNIT)A,B,C,D > ENDIF > > but this requires recoding every single WRITE statement. It also requires changing the OPEN statement... assuming that you are using an OPEN statement, which I strongly recommend. And if you were doing anything other than the most trivial, there could be all kinds of other repercussions. For example, you could end up with different numbers records because formatted writes sometimes write multiple records. This is a significant enough change, that I'd worry pretty seriously about it introducing Heisenbergs (looking for the bug makes its symptoms change or even disappear). All in all, I'd think this has a fair chance of introducing more bugs than it is likely to help you find. The bigger and more complicated the program gets, the more I'd worry about this introducing problems. Have you considered just something like a filedump utility to help you look at the unformatted file? Admitedly, such utilities can be a bit of a pain, but they don't require such surgery to the code youu are trying to debug. > It seems that there should be a way to do something like this at the > top of the file... > > IF(doASCII)THEN > IO_CONTROL_STRING = "*" > ELSE > IO_CONTROL_STRING = " " > ENDIF > > and then simply add the control string to the WRITE... > WRITE(IUNIT,IO_CONTROL_STRING)A,B,C,D > > Unfortunately, the above does not work. Among other things, the above write is *EXACTLY* the correct syntax for a write with an explicit format. The variable name IO_CONTROL_STRING is a little strange, but the standard doesn't require sensible names. And those 2 values aren't good explicit formats (something like '(4g20.10)' would fit better), but the compiler can't necessarily see the variable value at compile time. > Is there any way to > incorporate a variable IO control string in a WRITE statement? Sorry, no. You can have variable values for the various IO specifiers, but you can't use a variable to change what IO specifiers are in the statement. In this case, you are trying to change whether the statement has a FMT specifier or not. Changing the value of the FMT specifier to a blank string isn't the same as not having the specifier. There are some things you can specify with variables, but other more fundamental things need to be specified at compile time. Whether the I/O is formatted or unformatted is one of those pretty fundamental things. Formatted I/O tends to be pretty dramatically different from unformatted. I'm not saying that it couldn't be done with a variable; clearly it could. One could do all I/O with an interpreter. This just happens to be past the boundary of what the standard allows to be run-time changeable. I note as an aside, that run-time variability is one of the advantages of the f90 standard way of specifying access= with a variable value instead of using multiple specifiers (such as readonly) as done in some f77 extensions. With the multiple specifiers, one had to use IF constructs and multiple OPEN statements in order to write an OPEN that could be used both with and without readonly. Other than using a filedump utility, other possible approaches to your problem include: 1. You could use a macro pre-processor. This would be an absolutely trivial application of such a thing. It isn't part of the Fortran standard, but macro pre-processors are easy enough to find. Heck, it wouldn't take very long to write one from scratch in Fortran to do this one trivial case... but I wouldn't really suggest writing your own anyway. 2. Staying within Fortran, you could modularize the writes so that they were all done in a subroutine, or maybe a small set of them. Then you'd just have to change the one (or few) subroutine(s). This does have the problem that it rapidly grows in complexity if you have many different variants of I/O lists, because you'd need a different subroutine (or optional arguments) for every argument list that had a different number of items or different type, kind, or rank for an item. This could vary from one case for the whole program to one case for every write statement. -- Richard Maine | Good judgment comes from experience; email: my first.last at org.domain | experience comes from bad judgment. org: nasa, domain: gov | -- Mark Twain
Post Follow-up to this messageRon G. wrote: > I have several hundred binary WRITE statements in the form > WRITE(IUNIT)A,B,C,D. For debugging, I would like to write these in > ASCII. I know I can do this with an IF statement: > IF(doASCII) THEN > WRITE(IUNIT,*)A,B,C,D > ELSE > WRITE(IUNIT)A,B,C,D > ENDIF When I have had this problem I would write a simple program that reads the binary file and writes a text file. (It wasn't always ASCII though.) This also helps to verify that the binary file format is consistent, comes in handy when debugging after having written the binary file, and is a good start toward the program that will eventually read that file. For one I did, each record of the file could be read by: READ(1) I,L,A,B,C,D,(X(J),J=1,L),(Y(J),J=1,L) I indicated the record type, L the length of the arrays, A,B,C,D,X,Y were all REAL variables. -- glen
Post Follow-up to this messageRichard E Maine wrote: > rgiordano@petrotel.com (Ron G.) writes: > > > > [snip] > Have you considered just something like a filedump utility > to help you look at the unformatted file? Admitedly, such utilities > can be a bit of a pain, but they don't require such surgery to the > code youu are trying to debug. I was going to suggest something along those lines also. Before I switched u nformatted file writing from "regular" Fortran to using the netCDF API, that's what I d id. I'd run the code and then dump the contents with my dump program. The only thing tha t has changed is that netCDF comes with its own filedump app, ncdump. For me it's the same dog, just a different leg. And, if it was possible to do what the OP asked, and the debugging is succes sful with the ASCII o/p option, wouldn't you then have to rerun the same case but with a " doBinary" just to get exactly the same output in the required/production non-ASCII format? cheers, paulv
Post Follow-up to this messageAll, Thank you for your suggestions and words of wisdom. They are very helpful. Regards, RonG
Post Follow-up to this messagePowered by vBulletin
Copyright 2000-2006 Jelsoft Enterprises Limited.