我当前正在创建一个简短的控制台应用程序,以读取多个子文件夹中的特定文件。该文件在所有目录中都具有相同的名称,因此将它们全部移至一个目录并重命名将是一个巨大的麻烦(其中有365个以上的文件。它们每天都会自动创建一个新名称,然后再返回几个年份)。但是,它们都在同一主文件夹下。
我调查了Read all files in directory sub folders。我知道我能够搜索每个单独的子文件夹并查看所有文件(我能够显示其fileName
来为在foreach
语句中找到的每个文件提供控制台。
到目前为止的代码:
static void Main(string[] args)
{
string readLine = string.Empty;
var dir = new DirectoryInfo(@"C:\MotherDir\");
// foreach loop to go through each subfolder to find FileINeed.txt
foreach (var file in dir.EnumerateFiles("FileINeed.txt", SearchOption.AllDirectories))
{
//I get an error here: "System.IO.FileNotFoundException: 'Could not file file-'"
using (StreamReader sr = new StreamReader(file.ToString())) //this is using the wrong directory, not the one set previously (var dir)
{
while (!sr.EndOfStream)
{
readLine = sr.ReadLine();
ProcessFiles(file.ToString());
}
}
}
Console.WriteLine("Finished.");
Console.ReadKey(); //Gets pause at the end of the program
}
// Method to pass files through in order to search for specific string
static fileEntry ProcessFiles(string fileName)
{
fileEntry inputFiles = new fileEntry();
string fileString = string.Empty;
string readLine;
using (StreamReader sr = new StreamReader(fileName))
{
while (!sr.EndOfStream)
{
readLine = sr.ReadLine();
if (readLine.Length < 1)
{
}
if (readLine.Contains("RUN DATE: "))
{
Console.Write("RUN DATE: ");
Console.WriteLine(readLine);
}
if (readLine.Contains("1234567"))
{
Console.Write("Found this: ");
Console.WriteLine(readLine);
}
if (readLine.Contains("7654321"))
{
Console.Write("Found this: ");
Console.WriteLine(readLine);
}
if (readLine.Contains("1346785"))
{
Console.Write("Found this: ");
Console.WriteLine(readLine);
}
if (readLine.Contains("2589632"))
{
Console.Write("Found this: ");
Console.WriteLine(readLine);
}
if (readLine.Contains("12587412"))
{
Console.Write("Found this: ");
Console.WriteLine(readLine);
}
}
}
inputFiles.FileName = fileString;
return inputFiles;
}
public class fileEntry
{
//stores file names and datetimes
public string FileName { get; set; }
public DateTime FileDate { get; set; }
}
我为寻找特定字符串的糟糕的if
语句表示歉意,我试图使用switch / case语句,但无法使其正常工作。
如果它找到了字符串之一,则只需要将其输出到控制台窗口即可(我知道我正在尝试输出整个readLine
)。该程序的目的是仅查看这些字符串是否存在于正在处理的文件中。
我对C#还是很陌生,这是我从头开始编写的第一个有价值的程序之一。因此,对于仍在学习中的不良编码做法(如果有),我深表歉意!如果您有任何建议或帮助,将不胜感激!请让我知道是否需要澄清!
提前谢谢!
答案 0 :(得分:4)
您在那里不必要使用StreamReader,您应该将其传递到ProcessFiles(不是file.ToString()而是file.FullName,它是文件的全名和路径,其他是FileInfo对象):
// foreach loop to go through each subfolder to find FileINeed.txt
foreach (var file in dir.EnumerateFiles("FileINeed.txt", SearchOption.AllDirectories))
{
//I get an error here: "System.IO.FileNotFoundException: 'Could not file file-'"
ProcessFiles(file.FullName);
}
注意:难以理解ProcessFiles的目的。即:为什么在处理新类时返回文件?您已经在第一时间获得清单的位置上。
注2:Bdir使用dir.EnumerateFiles或dir.GetFiles比使用Directory.GetFiles是更好的选择,特别是如果您还希望过滤其他文件属性(例如(CreationDate,ModificationDate ...)。)。
另一个示例:
void Main()
{
string[] searches = { "RUN DATE: ", "1234567", "7654321", "1346785", "2589632", "12587412"};
var dir = new DirectoryInfo(@"C:\MotherDir\");
var files = from fi in dir.GetFiles("FileINeed.txt", SearchOption.AllDirectories)
let content = File.ReadAllText(fi.FullName)
// sample filter
// where fi.CreationTime >= DateTime.Now.AddDays(-3)
where searches.Any(c => content.Contains(c))
select fi;
foreach (var file in files)
{
Console.WriteLine(file.FullName);
}
}
答案 1 :(得分:2)
错误地跳出的原因是,您正在打开每个文件,并将文件内容传递给ProcessFiles
,实际上它需要文件名而不是文件内容。尝试将main()
方法更改为此...
static void Main(string[] args)
{
// this gets all matching files in a string array...
string[] allfiles = Directory.GetFiles(@"C:\MotherDir\", "FileINeed.txt", SearchOption.AllDirectories);
// parse the string array and call ProcessFiles for each one...
foreach (var file in allfiles)
{
ProcessFiles(file);
}
Console.WriteLine("Finished.");
Console.ReadKey(); //Gets pause at the end of the program
}
答案 2 :(得分:0)
dir.EnumerateFiles
返回一个FileInfo
对象。使用file。FullName
属性来获取标准路径名。
答案 3 :(得分:0)
我认为这是您的使用
file.ToString()
我不确定它返回什么。要从FileInfo获取流,您需要使用
file.OpenText()
所以失败的代码将是
using (StreamReader sr = file.OpenText())
您的ProcessFiles可以使用FileInfo而不是字符串,然后您就可以获取
static fileEntry ProcessFiles(FileInfo file)
如果您想从FileInfo获取文件的完整路径,则可以使用
Path.Combine(file.DirectoryName, file.Name)