parsing error when getting the file depends on file creation time
I have path like this..."C:\restore\restoredb\"
In that path i have files like this..
backup-2011-10-12T17-16-51.zip
backup-2011-10-11T13-24-45.zip
I have a form , in that form i have a listbox and combobox(cbrestore) I have got the combobox items like this ...Month, 3 months,6 months,year...
what i want is , if i select the combobox item(month) i want to display the file names which are stored in that folder between these dates (12-10-2011 to 12-09-2011) using file creation time i.e, like this .. File.Getcreationtime
..
If i select combobox item(3 months) i want to display the file names which are stored in that folder between these dates (12-10-2011 to 12-07-2011)..in listbox..
For that i have tri开发者_StackOverflow中文版ed like this ...
List<String> t = Directory.GetFiles(@"C:\restore\restoredb\").ToList();
List<String> y = new List<string>();
List<String> u = new List<string>();
foreach (var zzz in t)
{
y.Add(Path.GetFileName(zzz));
}
if (comboBox1.Text == "Month")
{
u =
(from String s in y where ((DateTime.Now.Month - (DateTime.Parse(File.GetCreationTime(s)) < 1) && (DateTime.Now.Year - DateTime.Parse(s.Substring(8, 10)).Year == 0) select s).
ToList();
}
but i am getting error saying that
"The best overloaded method match for system.datatime.parse(string) Has some invalid arguments.... like this i got error at this line (DateTime.Parse(File.GetCreationTime(s))
would any one pls help on this..... many thanks In advance...
I seem to have needed to make some additional changes to the code you've been using. Below is the new code for the comboBox:
private void comboBox1_SelectedIndexChanged(object sender, EventArgs e)
{
List<Files> yourNewList = Files.GetFiles();
List<String> u = new List<string>();
if (comboBox1.Text == "Month")
{
u = (from Files f in yourNewList
where DateTime.Parse(f.CreationDate.Substring(0, 10)) > DateTime.Now.AddMonths(-1)
select f.FileName).ToList();
}
else if (comboBox1.Text == "3 Month")
{
u = (from Files f in yourNewList
where DateTime.Parse(f.CreationDate.Substring(0, 10)) > DateTime.Now.AddMonths(-3)
select f.FileName).ToList();
}
else if (comboBox1.Text == "1 Year")
{
u = (from Files f in yourNewList
where DateTime.Parse(f.CreationDate.Substring(0, 10)) > DateTime.Now.AddMonths(-12)
select f.FileName).ToList();
}
listBox1.DataSource = u;
}
This is using a class I made that stores File objects that have both a filename and a creation date/time:
As you can see a lot of those share the same creation date (the one from April is an old zip file I found to use), this is intended as I made those files yesterday to help you. I can not spoof the creation date that windows pulls from the file.
The class itself uses this code:
public class Files
{
public string FileName { get; private set; }
public string CreationDate { get; private set; }
public List<Files> theseFiles
{
get
{
return GetFiles();
}
}
public Files(string fileName, string creationDate)
{
this.FileName = fileName;
this.CreationDate = creationDate;
}
public static List<Files> GetFiles()
{
//Gets full file names
List<String> t = Directory.GetFiles(@"C:\Users\justin\Desktop\New folder (2)\").ToList();
List<String> t2 = new List<string>();
foreach (var yyy in t)
{
t2.Add(Path.GetFileName(yyy));
}
//Creation Dates
var dirInfo = new DirectoryInfo(@"C:\Users\justin\Desktop\New folder (2)");
List<String> fct = (from f in dirInfo.GetFiles("*", SearchOption.TopDirectoryOnly)
select f.CreationTime.Date.ToShortDateString()).ToList();
List<String> y = new List<string>();
foreach (var zzz in fct)
{
y.Add(zzz);
}
//Creats a collection of the file objects for you to use
List<Files> gg = new List<Files>();
for (int x = 0; x < t2.Count(); x++)
{
//Adjusts the dates to add 0's in the off chance that they aren't there
if(DateTime.Parse(y[x]).Month < 10)
{
y[x] = "0" + y[x];
}
if(DateTime.Parse(y[x]).Day < 10)
{
y[x] = y[x].Insert(3, "0");
}
Files thefile = new Files(t2[x].ToString(), y[x].ToString());
gg.Add(thefile);
}
return gg;
}
public override string ToString()
{
return string.Format("{0} , {1}", FileName, this.CreationDate);
}
}
All you need to do is add a class to your project called Files, and paste that code inside. (Make sure you change the directory in the class, due to it currently pointing to my folder)
Then paste the code from up top into the SelectedIndexChanged method in your form's .cs page.
Remember, the if conditionals are based on the creation time, so thats why you will see the filenames (like the one with date 9/11/2010) that don't belong there. (Once again, I created all those files yesterday and the one that has the date from 04/04/2011 is an older zip file that I found from April and placed it in the folder to test with).
In the two pictures, you see the addition of 1 file, which makes sense based on the SS up top where you see the return gg collection. In that SS the only file to fall outside of yesterday's creation date is the one from 04/07/2011, which is why it appears when I pick "1 year".
DateTime.Parse(argument) argument type is String
and File.GetCreationTime(argument) returns DateTime
so you are trying to pass DateTime value as String type argument
So just change condition like below:
where ((DateTime.Now.Month - File.GetCreationTime(s).Month) < 1)
&&
(DateTime.Now.Year - DateTime.Parse(s.Substring(8, 10)).Year == 0)
EDIT:
To check whether file creation Month is previous I would suggest using something like this:
DateTime now = DateTime.Now;
DateTime fileCreationTime = File.GetCreationTime(s);
bool isPreviousMonth = (DateTime.Now.Month == 1 ? 12 : DateTime.Now.Month - 1)
== fileCreationTime.Month;
EDIT2:
string path = @"C:\restore\restoredb\";
IList<String> allFiles = Directory.GetFiles(path).ToList();
IList<String> fileNames = new List<string>();
IList<String> filesCreatedInThisMonth = new List<string>();
fileNames = allFiles.Select(filePath => Path.GetFileName(filePath)).ToList();
if (comboBox1.Text == "Month")
{
filesCreatedInThisMonth =
allFiles.Where(fileName =>
{
return File.GetCreationTime(fileName).Month
== (DateTime.Now.Month == 1 ? 12 : DateTime.Now.Month - 1)
&&
(DateTime.Now.Year == DateTime.Parse(fileName.Substring(8, 10)).Year);
}).ToList();
}
EDIT3:
IList<String> filesCreatedInThisMonth = new List<string>();
IList<String> fileNames = new List<string>();
// Key - Full file path
// Value - File creation DateTime extracted from the file name
IDictionary<string, DateTime> filePathToDateMap =
Directory.GetFiles(path).ToDictionary(
filePath => filePath,
filePath => DateTime.Parse(Path.GetFileName(filePath).Substring(8, 10)));
// mapEntry - KeyValuePair
// Key - filePath, Value - creation DateTime extracted from the file name
filesCreatedInThisMonth =
filePathToDateMap.Where(mapEntry =>
{
return File.GetCreationTime(mapEntry.Key).Month
== (DateTime.Now.Month == 1 ? 12 : DateTime.Now.Month - 1)
&&
(DateTime.Now.Year == mapEntry.Value.Year);
}).Select(entry => entry.Key)
.ToList();
OR Case when file creation time do not retrieved from a file name but from a real creation time:
IDictionary<string, DateTime> filePathToDateMap =
Directory.GetFiles(path).ToDictionary(
filePath => filePath,
filePath => File.GetCreationTime(filePath));
Your error is here:
(DateTime.Parse(File.GetCreationTime(s))
File.GetCreationTime(s) returns a DateTime, not a string (the type that DateTime.Parse expects...)
You should replace the previous code for File.GetCreationTime(s) without DateTime.Parse
In your example code you're using the file creation time via File.GetCreationTime
for the month comparison, but you're using what appears to be a file creation time embedded in the file name (starting at index 7) to examine the year. Side note: Substring(int, int)
uses zero-based indexing, so your code should use Substring(7, 10)
vice Substring(8, 10)
which will be off by one.
If using the date embedded in the file name is acceptable (versus the time stamp from the operating system), then this will get all file names created within the previous month:
string path = @"C:\restore\restoredb\";
IList<String> allFiles = Directory.GetFiles(path).ToList();
IList<String> fileNames = allFiles.Select(filePath => Path.GetFileName(filePath)).ToList();
List<String> filesCreatedInLastMonth = new List<string>();
DateTime endDate = DateTime.Now;
DateTime beginDate = endDate.AddMonths(-1);
foreach (var fileName in fileNames)
{
DateTime dt = DateTime.Parse(fileName.Substring(7, 10));
if ((beginDate <= dt) && (dt <= endDate))
{
filesCreatedInLastMonth.Add(fileName);
}
}
This can be easily modified for other date ranges.
To use file creation time instead, change the first line inside the foreach
block to:
DateTime dt = File.GetCreationTime(path + fileName);
精彩评论