【问题标题】:Store values to collection, suggestion please将值存储到收藏中,请提出建议
【发布时间】:2011-07-24 08:57:21
【问题描述】:

新手问题。我应该使用什么集合类型来存储这样的结构?

Files collection
---------------
FileId: Int
FileName : String
Path: String

我需要将几个文件数据存储到该集合中,通过 FileId 字段查找 Path,通过 FileId 字段删除项目。

【问题讨论】:

    标签: .net collections types


    【解决方案1】:

    有几种可能的方法。

    假设这样的结构:

      class File
      {
        int FileId { get; set; }
        string FileName { get; set; }
        string Path { get; set; }
      }
    

    简单的通用列表
    您可以将数据保存在一个简单的通用列表中:

    List<File> File { get; set; }
    

    可观察的集合
    如果您需要将集合绑定到 WPF UI 并且其内容从代码中的某处更新,我建议:

    ObservableCollection<File> Files { get; set; }
    

    字典
    如果 FileId 是唯一的,并且它是您用于查找项目的唯一属性,则可以将它们放入字典中,如下所示:

    Dictionary<int, File> File { get; set; }
    

    【讨论】:

      【解决方案2】:

      由于您有几条预定义的信息要与每个值实例关联,因此我将首先定义一个结构来保存每个文件所需的信息:

      public struct CustomFileInfo  //pick a name that avoids conflicts with System.IO
      {
          public readonly int FileId;
          public readonly string FileName;
          public readonly string Path;
      
          // constructor
          public CustomFileInfo(int fileId, string fileName, string path)
          {
              this.FileId = fileId;
              this.FileName = fileName;
              this.Path = path;
          }
      }
      

      然后我会使用一个通用集合(例如List&lt;T&gt;)来保存该结构的实例:

      List<FileInfo> myFiles = new List<FileInfo>();
      

      或者,您可以使用Dictionary&lt;TKey, TValue&gt;,其中FileId 作为键,FileInfo 结构作为值。例如:

      Dictionary<int, FileInfo> myFiles = new Dictionary<int, FileInfo>();
      

      字典的优势在于它在按 ID 搜索文件时提供了更快的查找时间。这是因为字典是在内部使用哈希表实现的。

      编辑:请注意mutable structs are evil。如果您需要能够更改描述文件的单个信息(我无法想象您为什么会这样做),您应该将 CustomFileInfo 声明为 class 而不是 struct

      【讨论】:

      • Dictionary 是比List 更好的搜索解决方案。
      • @acoo:确实,如果您打算进行大量搜索。从问题中我可以看出,提问者只想要一种方法来存储这些信息的集合。
      • +1 用于建议结构,操作描述的数据结构是一个很好的候选者
      • @Cody Gray, Dictionary 不仅具有快速搜索和良好存储能力,而且还提供了控制密钥 (ID) 和使用它们的方法。
      • @acoo:您想到了哪些Dictionary 集合提供而List 没有提供的方法?
      【解决方案3】:

      创建一个File 类:

      public class File
      {
          public int Id { get; private set; }
          public string Path { get; private set; }
          public string FileName
          {
              get
              {
                  return System.IO.Path.GetFileName(this.Path);
              }
          }
          public File(int id, string path)
          {
              this.Id = id;
              this.Path = path;
          }
      }
      

      然后,您可以将对象存储在List&lt;File&gt; 中:

      List<File> files = GetFiles();
      files.RemoveAll(f => f.Id == 42);
      

      ..或Dictionary&lt;int, File&gt;:

      Dictionary<int, File> files = GetFiles(); // GetFiles should use File.Id as key
      files.Remove(42);
      

      Dictionary 的好处是您可以非常高效地查找密钥。 List 的好处是您具有灵活性并且可以轻松编写代码以根据包含的 File 对象的任何值进行删除,例如:

      files.RemoveAll(f => f.Path.Contains("stuff"));
      

      【讨论】:

      • 同意,但我不会调用类File,因为它与System.IO 中定义的类冲突。您很可能在使用此类的同时导入了该命名空间。
      • @Cody:是的,命名可以改进。属性PathSystem.IO.Path 之间的File 类型内部已经存在冲突(因此使用了完全限定名称)。附带说明; FileInfo 也会造成冲突 ;-)
      【解决方案4】:

      我会创建一个Dictionary,并以自定义类作为值:

      public class FileInfo
      {
          public string FileName {get;set;}
          public string Path {get;set;}
      }
      

      并存储在Dictionary&lt;int, FileInfo&gt; 字典中,您将FileId 作为Dictionary 中的键。

      【讨论】:

        猜你喜欢
        • 2017-12-25
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-11-26
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多