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 wOOdy-Soft on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Number of LINES in a file

Status
Not open for further replies.

exodus300

Programmer
Mar 22, 2002
262
AU
Hello,

It is possible to obtain the number of records in a random access file using this code:
Code:
Open "C:\abc.dat" For Random As 1 Len = Len(MyRecord)
NumRecords = LOF(1) \ Len(MyRecord)
This is fine, but how can I obtain the number of lines in a text input file, so I can read a random line from the file, eg:
Code:
Dim L As Integer, I As Integer, TempLine As String
Open "C:\abc.txt" For Input As 1
NumLines = ?????                   ' What to put here?
L = Int(Rnd * NumLines) + 1
For  I = 1 To L
   Line Input #1, TempLine
Next
' Now, TempLine contains a random line from the file

I suppose I should have asked, How can I get a random line from a file, without knowing how many lines are in the file? [Thanks in advance|Hope I helped you]
Exodus300
World-Wide Alliance of Evil and Twisted People
[red]"Experimentation by Example is the best learning tool" - Exodus300[/red]
Code:
if (pop_tarts == 0)
{
   tantrum = 1;
}
[pc3]
 
You could have a function open the file and step through each line until the end of the file and return the number of lines found. I tried the following function on a 14000 line file and it returned the count almost instantly.

Public Function CountFileLines(strFileName) As Long

Dim intFileHandle As Integer
Dim lngCount As Long
Dim strTemp As String

intFileHandle = FreeFile()

Open strFileName For Input As #intFileHandle

lngCount = 0
Do While Not EOF(intFileHandle)
Line Input #1, strTemp
lngCount = lngCount + 1
Loop

close #intFileHandle

CountFileLines = lngCount

End Function

In your example:
NumLines = CountFileLines(strYourFile)

just pass the function the name and path of the file you wish to open (or include the code of the function right in your routine)

 
Dim MyStrSet as Variant
MyFil = "C:\abc.dat"
Code:
    InFile = FreeFile                   'Revisit the file
    Open MyFil For Binary As #InFile
    MyStr = String$(LOF(InFile), 0)     'Prepare a string of Nulls to Receive the contents
    Get #InFile, 1, MyStr               'Get the entire contents
    Close #InFile
    MyStrSet = Split(MyStr, vbcrlf)

    NumLines = UBound(MyStrSet) + 1

Of course, this does NOT mean that you can access individual LINES in the file in Random access mode unless the lines are actually of the SAME length. But, it DOES imply that you could -from this point- treat [MyStrSet]as an array of strings which may be operated on. Each element of the array representing a "line" from hte input file - similar to the content which would be obtained by using line input.

It is also interesting to note that the process may be continued by asigning each line to a UDT and obtaining an array of UDTs which very much "look Like" a recordset.

However the process does require the re-insertion of delimiters to 'write' the contents back to permanant storage. There are numerous threads discssing the approach some of which may be found by searching for "LOF" when the search engine is somewhat working.





MichaelRed
m.red@att.net

There is never time to do it right but there is always time to do it over
 
Thank you both for your help. I haven't tried these as yet, but they look like they'll work :) Can't believe I didn't think of djsiders' idea... it's so simple! [Thanks in advance|Hope I helped you]
Exodus300
World-Wide Alliance of Evil and Twisted People
[red]"Experimentation by Example is the best learning tool" - Exodus300[/red]
Code:
if (pop_tarts == 0)
{
   tantrum = 1;
}
[pc3]
 
Well, it DOES 'work', although to JUST find out the number of lines it is a bit I/O intensive. For SMALL files, it is not an issue, but larger files will be noticably slower than your original soloution. For all but the largest files and 'smallest' (Available memory / disc space) machines, there is little point in the operation you described and even less in the line input method (particularly when discarding the input). It does -of course- depend somewhat on the actual process, but either creating a recordset of the input or generating an array of the inputs residing in memory have clear advantages to reading and discarding on a line by line basis. Line input has to be close to the worst workable soloution available -and particularly poor for larger files.


MichaelRed
m.red@att.net

There is never time to do it right but there is always time to do it over
 
I have a text file with (at the moment) seven lines from which to randomly choose one. For my purposes, it seems ok (and simple). All I need is to return to the start of the file to begin looping thru the lines after seeing how many there are. [Thanks in advance|Hope I helped you]
Exodus300
World-Wide Alliance of Evil and Twisted People
[red]"Experimentation by Example is the best learning tool" - Exodus300[/red]
Code:
if (pop_tarts == 0)
{
   tantrum = 1;
}
[pc3]
 
Split? Returns an array. Can't usually get Ms. A. to place an array into a simple string.

Attempting to point out the obvious?

MichaelRed
m.red@att.net

Searching for employment in all the wrong places
 
OK Please forget my original post now.

The question here now is how can I go to the start of a file after reaching the end. The file is opened as Input, not Random. [Thanks in advance|Hope I helped you]
Exodus300
World-Wide Alliance of Evil and Twisted People
[red]"Experimentation by Example is the best learning tool" - Exodus300[/red]
Code:
if (pop_tarts == 0)
{
   tantrum = 1;
}
[pc3]
 

As someone posted in another thread I cannot find you can use the seek statement (from help)...

Seek Statement


Sets the position for the next read/write operation within a file opened using the Open statement.

Syntax

Seek [#]filenumber, position

The Seek statement syntax has these parts:

Part Description
filenumber Required. Any valid file number.
position Required. Number in the range 1 – 2,147,483,647, inclusive, that indicates where the next read/write operation should occur.


Remarks

Record numbers specified in Get and Put statements override file positioning performed by Seek.

Performing a file-write operation after a Seek operation beyond the end of a file extends the file. If you attempt a Seek operation to a negative or zero position, an error occurs.


so you would use...

Seek #intFileHandle, 1

Good Luck
 
Thank you. [Thanks in advance|Hope I helped you]
Exodus300
World-Wide Alliance of Evil and Twisted People
[red]"Experimentation by Example is the best learning tool" - Exodus300[/red]
Code:
if (pop_tarts == 0)
{
   tantrum = 1;
}
[pc3]
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top