Note
Access to this page requires authorization. You can try signing in or changing directories.
Access to this page requires authorization. You can try changing directories.
Question
Tuesday, December 11, 2012 2:47 AM | 1 vote
I found this code, works great. but want to change it to display just the date and time not full path and file name.
Private Sub btn_check_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btn_check.Click
Dim files() As String = System.IO.Directory.GetFiles("C:\Workarea")
System.Array.Sort(files, New FileInfoComparer)
MessageBox.Show("Latest file: " & files(files.Length - 1))
MessageBox.Show("Oledest file: " & files(0))
End Sub
Public Class FileInfoComparer
Implements IComparer
Public Function Compare(ByVal x As Object, ByVal y As Object) As Integer Implements System.Collections.IComparer.Compare
Dim firstFile As New System.IO.FileInfo(x.ToString)
Dim secondFile As New System.IO.FileInfo(y.ToString)
Return DateTime.Compare(firstFile.LastWriteTime, secondFile.LastWriteTime)
End Function
I want to stay away from any next or loop as the directory I am reading has thousands of files
any help is greatly appreciated.
All replies (15)
Tuesday, December 11, 2012 3:27 PM ✅Answered | 1 vote
Dim fi As New System.IO.DirectoryInfo("C:\WorkFolder")
Dim files = fi.GetFiles.ToList
Dim first = (From file In files Select file Order By file.CreationTime Ascending).FirstOrDefault
Dim last = (From file In files Select file Order By file.CreationTime Descending).FirstOrDefault
Success
Cor
Tuesday, December 11, 2012 7:49 PM ✅Answered
Any solution you come up with will involve iterating through every file in the directory. You can mitigate this somewhat by using the EnumerateFiles method (available starting with .Net 4.0). This method will begin to return results before all the files have been returned, rather than waiting for all files. Either way, though, since you want the oldest and newest, you will have to iterate over all the files. It's best to do this only once and keep track of the oldest and newest ones.
Here is some code that uses it. It searched a directory tree of about 47000 files in about 4 seconds.
Sub Main()
Dim sw As New Stopwatch()
Dim folderToSearch As String = "folder name here"
Dim oldestFile As FileInfo = Nothing
Dim newestFile As FileInfo = Nothing
Dim fileCount As Integer = 0
Dim folder As New DirectoryInfo(folderToSearch)
Console.Clear()
Console.WriteLine("Searching {0}", folderToSearch)
Console.WriteLine()
sw.Start()
For Each finfo In folder.EnumerateFiles("*", IO.SearchOption.AllDirectories)
If oldestFile Is Nothing OrElse finfo.LastWriteTime <= oldestFile.LastWriteTime Then
oldestFile = finfo
End If
If newestFile Is Nothing OrElse finfo.LastWriteTime >= newestFile.LastWriteTime Then
newestFile = finfo
End If
fileCount += 1
Next
sw.Stop()
Console.WriteLine("Oldest file is {0} {1}.", oldestFile.LastWriteTime, oldestFile.Name)
Console.WriteLine("Newest file is {0} {1}.", newestFile.LastWriteTime, newestFile.Name)
Console.WriteLine()
Console.WriteLine("{0} files searched. Elapsed time: {1}", fileCount, sw.Elapsed.ToString("mm\:ss\.fff"))
Console.WriteLine()
Console.WriteLine("Press ENTER to exit...")
Console.ReadLine()
End Sub
YMMV
Tuesday, December 11, 2012 3:00 AM
How about replacing you two MessageBox statements with
Dim lastDate As DateTime = New IO.FileInfo(files(files.Length - 1).LastWriteTime
MessageBox.Show("Newest file Date: " & lastDate.ToString())
Dim firstDate As DateTime = New IO.FileInfo(files(0).LastWriteTime
MessageBox.Show("Oldest file Date: " & firstDate.ToString())
Tuesday, December 11, 2012 7:07 AM
try this
Dim directory = New DirectoryInfo("C:\MyDirectory")
Dim myFile = (From f In directory.GetFiles() Order By f.LastWriteTime Descending f).First().CreationTime
good luck
Please mark the post as an answer that helps/solves your problem.
Tuesday, December 11, 2012 7:09 AM
In addition to Blackwood,
Or using Linq that I comparer is a little bit a homework question (it is done like was done with punch cards).
Dim fi As New System.IO.DirectoryInfo("C:\Workfolder")
Dim files = fi.GetFileSystemInfos.ToList
Dim first = (From file In files Select file Order By file.CreationTime Ascending).FirstOrDefault
Dim last = (From file In files Select file Order By file.CreationTime Descending).FirstOrDefault
Success
Cor
Tuesday, December 11, 2012 2:18 PM
Thanks Cor, is there a way to look at files only and omit subdirectories?
Tuesday, December 11, 2012 4:07 PM
Cor, I guess I need to re-think this. my original code and your code takes too long to return as the archive folder has thousands of files. thoughts?
Dim fi As New System.IO.DirectoryInfo("C:\Workarea\Archive") Dim files = fi.GetFileSystemInfos.ToList Dim first = (From file In files Select file Order By file.CreationTime Ascending).FirstOrDefault ' Dim last = (From file In files Select file Order By file.CreationTime Descending).FirstOrDefault TxtBx1.Text = first.LastWriteTime
Tuesday, December 11, 2012 4:09 PM
If it takes long than is it your file access not the Linq part.
You can do nothing to go around that beside buying a faster storage device.
Success
Cor
Tuesday, December 11, 2012 4:53 PM
How about using timers and storing your file information as long as the archive directory doesn't change in length?
Imports System.IO
Public Class Form1
Dim first As Object
Dim Counter As Integer = 0
Dim FileInformation As String
Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
Timer1.Interval = 1
Timer2.Interval = 1
Timer1.Start()
End Sub
Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
RichTextBox1.Text = FileInformation
End Sub
Private Sub Timer1_Tick(sender As Object, e As EventArgs) Handles Timer1.Tick
If Directory.GetFiles("C:\Users\John\Desktop\Test Folder").Length <> Counter Then
Timer2.Start()
Counter = Directory.GetFiles("C:\Users\John\Desktop\Test Folder").Length
End If
End Sub
Private Sub Timer2_Tick(sender As Object, e As EventArgs) Handles Timer2.Tick
Dim fi As New System.IO.DirectoryInfo("C:\Users\John\Desktop\Test Folder")
Dim files = fi.GetFileSystemInfos.ToList
first = (From file In files Select file Order By file.CreationTime Ascending).FirstOrDefault
FileInformation = first.LastWriteTime
Timer2.Stop()
End Sub
You've taught me everything I know but not everything you know.
Tuesday, December 11, 2012 5:14 PM | 1 vote
How about using timers and storing your file information as long as the archive directory doesn't change in length?
Imports System.IO Public Class Form1 Dim first As Object Dim Counter As Integer = 0 Dim FileInformation As String Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load Timer1.Interval = 1 Timer2.Interval = 1 Timer1.Start() End Sub Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click RichTextBox1.Text = FileInformation End Sub Private Sub Timer1_Tick(sender As Object, e As EventArgs) Handles Timer1.Tick If Directory.GetFiles("C:\Users\John\Desktop\Test Folder").Length <> Counter Then Timer2.Start() Counter = Directory.GetFiles("C:\Users\John\Desktop\Test Folder").Length End If End Sub Private Sub Timer2_Tick(sender As Object, e As EventArgs) Handles Timer2.Tick Dim fi As New System.IO.DirectoryInfo("C:\Users\John\Desktop\Test Folder") Dim files = fi.GetFileSystemInfos.ToList first = (From file In files Select file Order By file.CreationTime Ascending).FirstOrDefault FileInformation = first.LastWriteTime Timer2.Stop() End Sub
You've taught me everything I know but not everything you know.
Mr, Monkeyboy,
That is not sorting, but maybe he simply wants the filewatcher
http://msdn.microsoft.com/en-us/library/system.io.filesystemwatcher(v=vs.110).aspx
Only his question was about the Icomparer a synonym for sort so quite confusing as this is market as answer for those searching for this question.
Success
Cor
Tuesday, December 11, 2012 7:14 PM
This has a problem in that you are calling Directory.GetFiles twice which will perform the disk I/O twice!
Thursday, December 13, 2012 5:38 PM
Thank you, Chris Dunaway much faster!!!
Thursday, December 20, 2012 4:53 PM
Chris, I have another question on this topic. I am needing to change my folder to search to an FTP folder for security reasons. here is the code
Dim folderToSearch As String = ("ftp://username:userpassword@servername/foldername")
Dim oldestFile As FileInfo = Nothing
Dim newestFile As FileInfo = Nothing
Dim fileCount As Integer = 0
Dim folder As New DirectoryInfo(folderToSearch)
For Each finfo In folder.EnumerateFiles("*", IO.SearchOption.AllDirectories)
If oldestFile Is Nothing OrElse finfo.LastWriteTime <= oldestFile.LastWriteTime Then
oldestFile = finfo
End If
If newestFile Is Nothing OrElse finfo.LastWriteTime >= newestFile.LastWriteTime Then
newestFile = finfo
End If
fileCount += 1
Next
txtbx_folderactivity.Text &= ("Searching: " & folderToSearch) & vbNewLine
txtbx_folderactivity.Text &= ("Oldest file: " & oldestFile.LastWriteTime) & vbNewLine
txtbx_folderactivity.Text &= ("Newest file: " & newestFile.LastWriteTime) & vbNewLine
TxtBx_INAsn.Text = newestFile.LastWriteTime
End If
I can open a new thread to get someone elses help.
Friday, December 21, 2012 7:25 PM
I'm not sure if the EnumerateFiles method supports a path like that. You may need to map the ftp site to a drive letter in Windows. Once done, I think it should work. See this link for information. I have no experience in this.
http://www.windowsitpro.com/article/ftp/how-can-i-map-to-an-ftp-server-as-a-drive-
Or you can use software such as WebDrive: (http://www.webdrive.com/products/webdrive/index.html) or ExpanDrive (http://www.expandrive.com/). Both of these are not free, but have trials so you can at least see if they will help you. There may be free alternatives, but I don't know them.
Saturday, December 22, 2012 3:36 PM
Thanks Chris!