从嵌入式文本文件使用File.ReadAllLines [英] Using File.ReadAllLines from embedded text file

查看:112
本文介绍了从嵌入式文本文件使用File.ReadAllLines的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我一直在运用我迄今为止在Bob Tabors绝对初学者系列中学到的知识,我为女儿写了一个小型的控制台文字游戏,要求我生成一个随机的5个字母的单词.

I have been applying what I have learned so far in Bob Tabors absolute beginners series and I wrote a small console word game for my daughter that requires me to generate a random 5 letter word.

我以前使用File.ReadAllLines(path)从系统上的文本文件(wordlist.txt)生成一个字符串数组,并使用Random.next生成我将从该数组中提取的索引.

I was previously using File.ReadAllLines(path) to generate a string array from a text file (wordlist.txt) on my system and Random.next to generate the index I would pull from the array.

我从这里的一些帖子中学到了如何将文件作为资源嵌入,但是现在我找不到指向它的语法(路径).还是现在它已经被嵌入,我是否必须以不同的方式访问它?

I learned from some posts here how to embed the file as a resource but now I am unable to find the syntax to point to it (path). Or do I have to access it differently now that it is embedded?

预先感谢

推荐答案

没有一个很好的,最小完整的代码示例是不可能提供具体建议的.

Without a good, minimal, complete code example it is impossible to offer specific advice.

但是,基本问题是这样的:将文件作为资源嵌入时,它不再是文件.也就是说,原始文件仍然存在,但是资源本身无论如何都不是文件.它作为某些特定类型的数据存储在程序集中.从文件源嵌入的资源通常以二进制数据对象的形式出现.

However, the basic issue is this: when you embed a file as a resource, it is no longer a file. That is, the original file still exists, but the resource itself is not a file in any way. It is stored as some specific kind of data in your assembly; resources embedded from file sources generally wind up as binary data objects.

如何使用此数据取决于嵌入"的含义.实际上,在C#程序中有两种常见的资源存储方式:您可以在项目中使用资源"对象,该对象通过项目的...Properties.Resources类(反过来使用.NET中的ResourceManager类)公开资源. ).或者,您可以简单地将文件添加到项目本身,然后选择嵌入式资源"构建选项.

How to use this data depends on what you mean by "embed". There are actually two common ways to store resources in a C# program: you can use the "Resources" object in the project, which exposes the resource via the project's ...Properties.Resources class (which in turn uses the ResourceManager class in .NET). Or you can simply add the file to the project itself, and select the "Embedded Resource" build option.

如果您使用的是资源"设计器,则可能有几种不同的方式来添加文件.一种是使用新建文本文件..."选项,该选项实际上允许您复制/粘贴或在资源中键入新文本.这在代码中显示为Properties.Resources对象上的string属性.如果使用现有文件..."选项添加资源,然后选择Visual Studio可以识别为文本文件的文件,则会发生同样的事情.

If you are using the "Resources" designer, then there are a couple of different ways you might have added the file. One is to use the "New Text File..." option, which allows you to essentially copy/paste or type new text into a resource. This is exposed in code as a string property on the Properties.Resources object. The same thing will happen if you add the resource using the "Existing File..." option and select a file that Visual Studio recognizes as a text file.

否则,该文件将作为由Properties.Resources类中的属性公开的byte[]对象包含.

Otherwise, the file will be included as a byte[] object exposed by a property in the Properties.Resources class.

如果您使用嵌入式资源"构建选项而不是资源"设计器,则可以通过调用Assembly.GetManifestResourceStream(string)方法获得数据,该方法将返回一个Stream对象.可以将其包装在StreamReader中,以便逐行读取.

If you have used the "Embedded Resource" build option instead of the "Resources" designer, then your data will be available by calling Assembly.GetManifestResourceStream(string) method, which returns a Stream object. This can be wrapped in StreamReader to allow it to be read line-by-line.

直接替换File.ReadAllLines(string)方法的外观类似于以下…

Direct replacements for the File.ReadAllLines(string) approach would look something like the following…

使用嵌入式资源":

string[] ReadAllResourceLines(string resourceName)
{
    using (Stream stream = Assembly.GetEntryAssembly()
        .GetManifestResourceStream(resourceName))
    using (StreamReader reader = new StreamReader(stream))
    {
        return EnumerateLines(reader).ToArray();
    }
}

IEnumerable<string> EnumerateLines(TextReader reader)
{
    string line;

    while ((line = reader.ReadLine()) != null)
    {
        yield return line;
    }
}

使用Properties.Resources:

Using Properties.Resources:

使用Properties.Resources类时,您可以执行类似的操作.看起来几乎一样:

You can do something similar when using the Properties.Resources class. It looks almost identical:

string[] ReadAllResourceLines(string resourceText)
{
    using (StringReader reader = new StringReader(resourceText))
    {
        return EnumerateLines(reader).ToArray();
    }
}

类似于string[] allLines = ReadAllResourceLines(Properties.Resources.MyTextFile);,其中MyTextFile是您在设计器中添加的资源的属性名称(即,在第二个示例中传递的string是文件本身的文本,而不是文件名).资源).

called like string[] allLines = ReadAllResourceLines(Properties.Resources.MyTextFile);, where MyTextFile is the property name for the resource you added in the designer (i.e. the string you pass in that second example is the text of the file itself, not the name of the resource).

如果添加了Visual Studio无法识别为文本文件的现有文件,则属性类型将为byte[]而不是string,并且您将需要另一种略有不同的方法:

If you added an existing file that Visual Studio didn't recognize as a text file, then the property type will be byte[] instead of string and you'll need yet another slightly different approach:

string[] ReadAllResourceLines(byte[] resourceData)
{
    using (Stream stream = new MemoryStream(resourceData))
    using (StreamReader reader = new StreamReader(stream))
    {
        return EnumerateLines(reader).ToArray();
    }
}

请注意,在所有三个示例中,关键是将数据封装在TextReader实现中,然后将其用于分别读取每一行以填充数组.这些都使用我上面显示的相同的EnumerateLines()辅助方法.

Note that in all three examples, the key is that the data winds up wrapped in a TextReader implementation, which is then used to read each line individually, to populate an array. These all use the same EnumerateLines() helper method I show above.

当然,既然您了解了如何检索数据,则可以将其改编为以多种其他方式使用数据,以防万一,例如,您确实不需要或不需要将文本表示为数组时string个对象.

Of course, now that you see how the data can be retrieved, you can adapt that to use the data in a variety of other ways, in case for example you don't really want or need the text represented as an array of string objects.

这篇关于从嵌入式文本文件使用File.ReadAllLines的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆