在C#中存储永远不会改变的静态数据的最佳方法是什么

我有一个类,它在asp.net c#应用程序中存储数据,永远不会改变。 我真的不想把这些数据放在数据库中 – 我希望它留在应用程序中。 这是我在应用程序中存储数据的方法:

public class PostVoteTypeFunctions { private List postVotes = new List(); public PostVoteTypeFunctions() { PostVoteType upvote = new PostVoteType(); upvote.ID = 0; upvote.Name = "UpVote"; upvote.PointValue = PostVotePointValue.UpVote; postVotes.Add(upvote); PostVoteType downvote = new PostVoteType(); downvote.ID = 1; downvote.Name = "DownVote"; downvote.PointValue = PostVotePointValue.DownVote; postVotes.Add(downvote); PostVoteType selectanswer = new PostVoteType(); selectanswer.ID = 2; selectanswer.Name = "SelectAnswer"; selectanswer.PointValue = PostVotePointValue.SelectAnswer; postVotes.Add(selectanswer); PostVoteType favorite = new PostVoteType(); favorite.ID = 3; favorite.Name = "Favorite"; favorite.PointValue = PostVotePointValue.Favorite; postVotes.Add(favorite); PostVoteType offensive = new PostVoteType(); offensive.ID = 4; offensive.Name = "Offensive"; offensive.PointValue = PostVotePointValue.Offensive; postVotes.Add(offensive); PostVoteType spam = new PostVoteType(); spam.ID = 0; spam.Name = "Spam"; spam.PointValue = PostVotePointValue.Spam; postVotes.Add(spam); } } 

当调用构造函数时,运行上面的代码。 我有一些函数可以查询上面的数据。 但这是在asp.net中存储信息的最佳方式吗? 如果不是你会推荐什么?

这是一个“ 看起来像 ”枚举的不可变结构的候选者:(另外,我注意到你为其中两个使用了相同的id值,所以我修复了……你可以使用以下内容,就像枚举一样…

 PostVoteTypeFunctions myVar = PostVoteTypeFunctions.UpVote; 

而且真正的好处是这种方法不需要4字节整数以外的实例存储(它将存储在堆栈中,因为它是一个结构)。 所有硬编码值都存储在类型本身中…每个AppDomain只存在一个…

 public struct PostVoteTypeFunctions { private int id; private bool isDef; private PostVoteTypeFunctions ( ) { } // private to prevent direct instantiation private PostVoteTypeFunctions(int value) { id=value; isDef = true; } public bool HasValue { get { return isDef; } } public bool isNull{ get { return !isDef; } } public string Name { get { return id==1? "UpVote": id==2? "DownVote": id==3? "SelectAnswer": id==4? "Favorite": id==5? "Offensive": id==6? "Spam": "UnSpecified"; } } public int PointValue { get { return // Why not hard code these values here as well ? id==1? PostVotePointValue.UpVote: id==2? PostVotePointValue.DownVote id==3? PostVotePointValue.SelectAnswer: id==4? PostVotePointValue.Favorite: id==5? PostVotePointValue.Offensive: id==6? PostVotePointValue.Spam: 0; } } // Here Add additional property values as property getters // with appropriate hardcoded return values using above pattern // following region is the static factories that create your instances, // .. in a way such that using them appears like using an enumeration public static PostVoteTypeFunctions UpVote = new PostVoteTypeFunctions(1); public static PostVoteTypeFunctions DownVote= new PostVoteTypeFunctions(2); public static PostVoteTypeFunctions SelectAnswer= new PostVoteTypeFunctions(3); public static PostVoteTypeFunctions Favorite= new PostVoteTypeFunctions(4); public static PostVoteTypeFunctions Offensive= new PostVoteTypeFunctions(5); public static PostVoteTypeFunctions Spam= new PostVoteTypeFunctions(0); } 

很难从您发布的代码片段中判断出是否公开了类之外的任何数据。

如果没有,那么这将有效。 但是,如果没有,有几个问题:

  • 如果要公开List,则只应使用yield关键字将其副本作为IEnumerable返回。
  • 确保您的PostVoteType是不可变的,否则可以更改引用并且可以更改使用的字段

“从不”确实是一个非常难的词。

在您的特定情况下,您断言您的PostVoteType数据不仅是绝对的和不可变的,而且容器集合也是如此。 坦率地说,我不相信你可以知道,因为你不是生意(你对要求的解释是不完美的)而你并不是通灵的(你对未来的了解并不完美)。

我建议您始终存储任何无法在某种存储库中表示为枚举的数据。 你期望关系和/或事务和/或可变需求意味着数据库,如果你期望高读写比率,可以是一个配置文件(我相信这种情况应该是)。

编辑:就内存持久性而言,我同意其他人认为缓存是存储它的最佳位置,或者更确切地说是在缓存支持的域对象中。


旁白:你的PostVoteTypes的构造太可怕了 – 强烈建议你想要一个重构器:)

看看你的代码,看起来你只是想创建一组实际上只是将枚举PostVotePointValue放入某​​种列表中的对象。 也就是说,你已经在enum本身中已经定义了你需要的东西。 我鼓励你不要在两个地方定义相同的信息(你要求的这个数据存储和枚举)。 这是我看到人们常犯的错误。 他们创建一个查找表/列表,然后创建一个镜像表行的枚举,这意味着他们必须修改两个位置才能对列表进行任何更改。

如果PostVotePointValue不是枚举,而只是一些常量,或者如果有更多信息要计划打包,那么这是不相关的。

以下是一些如何使用http://www.csharp-station.com/Tutorials/Lesson17.aspx将“枚举”作为“列表”的示例

  // iterate through Volume enum by name public void ListEnumMembersByName() { Console.WriteLine("\n---------------------------- "); Console.WriteLine("Volume Enum Members by Name:"); Console.WriteLine("----------------------------\n"); // get a list of member names from Volume enum, // figure out the numeric value, and display foreach (string volume in Enum.GetNames(typeof(Volume))) { Console.WriteLine("Volume Member: {0}\n Value: {1}", volume, (byte)Enum.Parse(typeof(Volume), volume)); } } // iterate through Volume enum by value public void ListEnumMembersByValue() { Console.WriteLine("\n----------------------------- "); Console.WriteLine("Volume Enum Members by Value:"); Console.WriteLine("-----------------------------\n"); // get all values (numeric values) from the Volume // enum type, figure out member name, and display foreach (byte val in Enum.GetValues(typeof(Volume))) { Console.WriteLine("Volume Value: {0}\n Member: {1}", val, Enum.GetName(typeof(Volume), val)); } } } 

您应该能够将上述内容调整为一种方法,该方法将为您提供一个列表,您可以根据需要使用该列表进行数据绑定。

我想知道为什么你不能只使用一个简单的枚举?

 public enum PostVoteType { UpVote = 0, DownVote = 1, SelectAnswer = 2, Favorite = 3, Offensize = 4, Spam = 5 } 

如果它没有改变,通常被访问,并且对所有用户都是一样的,那么.NET缓存就是合适的地方。 有一个产生这些值的属性。 在内部,属性检查此列表的缓存并返回存储的值; 否则,它从头开始构造它,添加到缓存中,并返回值。

尽管如此,即使您将其缓存,仍应该在数据库中配置它。 我想你需要将这些值与数据库中的其他数据结合使用。

当您需要经常访问相同的数据,并且不需要将其存储到底层数据库中,并且该数据在应用程序可能遇到的每种情况下大致相同时,我建议使用缓存。 缓存源于这些要求。 缓存通常是提供数据的最快方式,因为它们始终保存在内存中或类似于易用性,并且使应用程序更容易访问。

这是一个很好的缓存工具,提供Microsoft Enterprise LibraryCaching Application Block

我认为值得花时间学习如何有效地使用它。

创建一个单例类。