我擅长使用C#。但是我对一个部分感到困惑,这促使我提出这个问题。
我的代码是 -
public class UsersModel
{
public List<string> Users
{
get
{
// Some code to connect to database and get list of users from database
// return list of users
}
}
}
public class HomeController
{
var um = new UsersModel();
var users = um.Users;
}
现在,当我从 ANTS Performance Profiler 检查此类代码时,我发现该属性被命中2次,我相信它会影响性能。
问题 -
修改 -
作为参考,我将添加有良好想法的链接Property Design。
我喜欢语句属性getter应该是没有任何先决条件的简单操作。如果getter可能抛出异常,请考虑将该属性重新设计为方法。
答案 0 :(得分:6)
来自MSDN "Choosing Between Properties and Methods"(强调我的):
在以下情况下,请使用方法而不是属性。
- 操作比字段设置慢几个数量级。如果您甚至考虑提供异步版本 一个避免阻塞线程的操作,很有可能 操作太昂贵,不能成为财产。特别是操作 访问网络或文件系统(除了一次) 初始化)应该很可能是方法,而不是属性。
在这种情况下,您应该选择一种方法,因为您的类的调用者会希望属性快速返回。
否则,粗心的调用者可能会随意编写代码,例如:
for (int i = 0; i < um.Users.Count; i++)
{
Console.WriteLine("User {0}: {1}", i, um.Users[i].Name);
}
导致N+1
对数据库的调用,其中N
是用户数。
通过使其成为一种方法,您正在将缓存结果的责任转移给调用者。
为什么属性用户被击中2次?
我怀疑它实际上可能是调试器或探查器检查属性值的结果。另一个答案中提到的唯一知道方法是检查调用堆栈。
答案 1 :(得分:2)
如果比简单地返回支持字段需要更多的努力,那么将其转换为方法。特别是对于数据库调用,请使用一个方法名称,使其明确表示在数据库上运行查询。
我个人会添加一个从数据库加载/检索用户的方法,并将该列表存储在属性中
public class UsersModel {
public List<string> Users { get; private set; }
public void LoadUsers() {
Users = ...
}
}
public class HomeController
{
var um = new UsersModel();
um.LoadUsers();
var users = um.Users;
}
答案 2 :(得分:0)
我应该在构造函数中初始化属性值吗? - 没必要,这取决于你想要如何使用该属性。 或者我应该为此类任务创建单独的方法? - 对于加载用户,是的,你肯定需要创建一个方法。该属性应仅返回包含用户的列表。用户加载方法也应该是异步的,否则会阻塞调用线程。根据您的情况,您可以考虑使用延迟初始化 - 仅在您需要时从数据库加载用户。 为什么属性用户被击中2次? - 查看ANTS中的呼叫树,它将回答你的问题。