Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations IamaSherpa on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

'OPEN' a file ONLY if it exists ? 1

Status
Not open for further replies.

Socko

Programmer
Jan 11, 2002
3
GB
I'm currently writing a small application in QB (4.5 I believe) in which I need the program to 'open' and 'read' the contents of a file. Now here's the problem ... the file in question won't always exist.

Is there any way I can get the program to check whether the file exists (before attempting to open it) to prevent an error message occuring ?

Many thanks in advance, Troy.
 
One way would be to open the file and determine whether it exists based on its length with the LOF function. If LOF(FileNumber) returns a zero we might assume that the file didn't exist. Unfortunately, the simple act of opening a file and then closing it creates the file if it didn't already exist. We could simply delete the file after determining that it is zero bytes in length....
[tt]
FileSpec$ = "C:\AUTOEXEC.BAT"
OPEN FileSpec$ FOR BINARY AS #1
FileLen& = LOF(1)
IF FileLen& > 0 THEN
((Do some stuff))
ELSE
CLOSE #1
KILL FileSpec$
END IF
[/tt]

...unfortunately, this really doesn't tell us whether or not the file existed. It only tells us whether or not the file was greater than zero bytes in length (some files are meant exist in a directory without containing actual data).
A better way is use "Find First Matching File" to check for the existence of the file before we try to open it....
[tt]
DEFINT A-Z
TYPE RegTypeX
AX AS INTEGER
BX AS INTEGER
CX AS INTEGER
DX AS INTEGER
BP AS INTEGER
SI AS INTEGER
DI AS INTEGER
FLAGS AS INTEGER
DS AS INTEGER
ES AS INTEGER
END TYPE
DECLARE FUNCTION FileExists (FileSpec$)
FileSpec$ = "C:\AUTOEXEC.BAT"
IF FileExists(FileSpec$) THEN
PRINT FileSpec$; " exists."
ELSE
PRINT FileSpec$; " doesn't exist."
END IF

FUNCTION FileExists (FileSpec$)
DIM InRegs AS RegTypeX, OutRegs AS RegTypeX
'[/tt]
Convert the file name to ASCIZ format[tt]
ASCIZfile$ = FileSpec$ + CHR$(0)
'[/tt]
Get the address of the string containing the file name[tt]
InRegs.DS = VARSEG(ASCIZfile$)
InRegs.DX = SADD(ASCIZfile$)
InRegs.CX = 15 '[/tt]
any file attribute[tt]
InRegs.AX = &H4E00
'[/tt]
Call Interrupt 21h, function 4Eh[tt]
CALL INTERRUPTX(&H21, InRegs, OutRegs)
IF OutRegs.FLAGS AND 1 THEN
FileExists = 0
ELSE
FileExists = 1
END IF
END FUNCTION
[/tt]

VCA.gif
 
Thank you Alt255, that was exactly the kind of information I was looking for.

Although the file in question might not exist, I know it will never be a zero byte file, so I will try your first suggestion and take it from there.

Thanks again, Troy. :)
 
Wouldn't using the DIR$ command be MUCH easier? Thought for the day: Beware of Gods who cannot laugh...
 
BobTheMad, you might have posted in the wrong forum.

The Dir function would be the way to go in Visual Basic. QB45 doesn't provide a way to detect the existence of a file. You have to guess using the file methods or resort to calls to the interrupts.


VCA.gif
 
There is another way. It's in ADVBAS.LIB - now freeware and obtainable from one of the sites. It has a command
'call exist(filename)'. That will tell you if the file exists, without opening it.
 
Well, as it turns out, method #1 works a treat in this instance (thanks again Alt255). However, I'll certainly get the file that you mentioned pebe and take a look :)
 
Alt255, I do not believe I have... I just checked, and QB supports the DIR$ command. Here is a code sample
-------------------------------

DECLARE FUNCTION GetFileCount& (filespec$)

filespec$ = "*.*"
count = GetFileCount(filespec$)
PRINT count; "files match the file specification."

FUNCTION GetFileCount& (filespec$)

'This function evaluates a file specification and returns the
'number of files that match the specification. Wild card characters
'("*" and "?") are permitted. Drive and directory path specifications
'may also be included in filespec$.
DIM FileCount AS LONG

IF LEN(DIR$(filespec$)) = 0 THEN 'Ensure filespec is valid.
FileCount& = 0 'It's not.
ELSE
FileCount = 1 'It is, so count files.
DO WHILE LEN(DIR$) > 0
FileCount& = FileCount& + 1
LOOP
END IF
GetFileCount = FileCount&
END FUNCTION

-------------------------------
Thought for the day: Beware of Gods who cannot laugh...
 
TO Alt255: I'v checked into it and DIR$ DOES EXIST in QB PDS ver.

TO BobTheMad: I'v check into it and DIR$ DOES NOT EXIST in QB 4.5 ver.

This is from the original post:

"application in QB (4.5 I believe) in which..."

Please note the operative word in bold. (Hopefully, I have added to the confusion in this post.) LOL

--MiggyD
It's better to have two heads to solve a problem from different angles than to have tunnel vision to a dead end.
 
Hi, Socko,

My approach has always been to generate an intentional error, which is caught by an ON ERROR statement.

Several of my home-grown engineering problems (written in QuickBasic 4.5) require an output file to be named and opened. Typically, my filenames are consecutive, eg CB01.out, CB02.out, etc.

To avoid overwriting a previously existing file my strategy has been to try to open each file in the sequence until an ON ERROR statement reacts to my opening a file which does not exist. I then set the new filename to the name which generated the error, RESUME and away I go.
 
Socko,

I made a program that finds all the current filesin the current directory. I saved every file name as a variable so you could just check the name of your file with each variable. The only problem with this is that it saves the name as the DOS short names instead of the long windows name that you may give to it.

The code is not exactly the best readable but it should work.



DIM d$(300)
CLS

'the y$ variable is the directory you want to find the
'files of and the z$ variable is where to write the names
'of all the files

'If you want the current directory just get rid of the
'next 3 lines

y$ = "cd\windows"
z$ = "cd\windows\desktop\family\qbasic"
SHELL y$
SHELL "dir > dir.tem"
OPEN "dir.tem" FOR INPUT AS #1
a$ = INPUT$(LOF(1), 1)
a = LOF(1)
CLOSE #1
SHELL "del dir.tem"
b = 5
FOR x = 1 TO a
b$ = MID$(a$, x, 3)
IF r = 1 THEN c$ = MID$(a$, x - 1, 5)
r = 1
IF a - 9 > 0 THEN IF LTRIM$(RTRIM$(c$)) = b$ THEN IF VAL(LTRIM$(RTRIM$(c$))) = 0 THEN IF (LTRIM$(RTRIM$(c$))) = UCASE$((LTRIM$(RTRIM$(c$)))) THEN b = b + 1: d$(b) = MID$(a$, x - 9, 12)
NEXT x
CLS
z = 0
FOR x = 1 TO b
IF z > 23 THEN z = 23
IF LTRIM$(d$(x)) = MID$(d$(x), 10, 3) THEN zx = 1
NEXT x
FOR x = 1 TO b
FOR y = 1 TO 9
IF MID$(d$(x), 1, y) = RTRIM$(MID$(d$(x), 1, y + 1)) THEN e$ = MID$(d$(x), 1, y)
NEXT y
f$ = MID$(d$(x), 10, 3)
CLS
d$(x) = e$ + "." + f$
IF d$(x) = "." THEN d$(x) = ""
NEXT x

FOR x = 1 TO b
FOR y = 1 TO b
IF d$(x) < d$(y) THEN SWAP d$(x), d$(y)
NEXT y
NEXT x

SHELL z$

' You can get rid of the last part because all it does is
' write the variables to a file and prints them

FOR x = 1 TO b
PRINT d$(x),
NEXT x

OPEN &quot;dir.tem&quot; FOR OUTPUT AS #1
WRITE #1, b
FOR x = 1 TO b
WRITE #1, d$(x)
NEXT x
CLOSE #1



Like i said before, I don't really like to comment my code for other people to read so well. I can understand what I am doing and that is good enough for me. If you don't understand anything you can e-mail me at:

SBecker08@att.net
 
The easiest way without the DIR$ command is to use the ON ERROR statement. Add this function to your code. It returns 1 if the file exists, 0 if it doesn't.

FUNCTION EXISTS% (FILENAME AS STRING)
EXISTS% = 1
ON LOCAL ERROR GOTO NOTFOUND
OPEN FILENAME FOR INPUT AS #1
CLOSE #1
EXIT FUNCTION
NOTFOUND:
EXISTS% = 0
RESUME NEXT
END FUNCTION

Use as follows:

FN$ = &quot;C:\FOLDER\TEST.EXT&quot;
IF EXISTS(FN$) THEN
OPEN FN$ FOR INPUT.....
....
CLOSE #1
ELSE
PRINT &quot;FILE NOT FOUND.&quot;
END IF

Cheers.


Be good. If you can't, don't get caught!
 
To MiggyD

Yes I did read the post. Your point?

Be good. If you can't, don't get caught!
 
To MiggyD:

Socko: &quot;Is there any way I can get the program to check whether the file exists (before attempting to open it) to prevent an error message occuring?&quot;

He did not say that he did not want an error. Just not an error message.
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top