我有一个设计问题,希望能得到一些建议。假设我们的新应用程序需要(多么原创啊...)员工信息。通常我会像这样做:
public interface IEmployee
{
string EmployeeId { get; }
string Name { get; }
void Update(string newName, ...);
...
}
public class Employee : IEmployee
{
public Employee(string id, string name, ...)
{
}
...
}
从数据源获取员工信息
public class SqlEmployeeRepository : IEmployeeRepository
{
...
public IEmployee GetEmployee(string id)
{
...
IEmployee employee = new Employee(id, name, ...);
return employee
}
public IEmployee SaveEmployee(IEmployee employee)
{
// Execute SQL command.
}
}
可视化将看起来像这样:
TextBox nameTextBox = new TextBox();
...
nameTextBox.Text = employee.Name;
保存的样子如下:
string name = nameTextBox.Text;
employee.Update(name, ...);
myEmployeeRepository.Save(employee);
到目前为止,一切都很好。但是,当我看到this和this这两篇文章时,我开始想象如果没有getter,该应用程序(静态和动态)会是什么样子,因此我尝试使用第二篇文章中描述的技术来实现上述应用程序,不使用getter。我得到了以下代码:
public interface IEmployee
{
public interface Importer
{
string ProvideId();
string ProvideName();
...
}
public interface Exporter
{
void AddId();
void AddName();
...
}
void Export(IExporter exporter)
...
}
public class Employee : IEmployee
{
private string _id;
private string _name;
public Employee(IEmployee.Importer importer)
{
_id = importer.ProvideId();
_name = importer.ProvideName();
...
}
public void Export(IEmployee.Exporter exporter)
{
exporter.AddId(_id);
exporter.AddName(_name);
...
}
}
然后仓库变成:
public class SqlEmployeeExporter : IEmployee.Exporter
{
...
public void Save() { ... }
}
public class SqlEmployeeRepository : IEmployeeRepository
{
...
public IEmployee GetEmployee(string id)
{
IEmployee.Importer importer = new SqlEmployeeImporter(id);
IEmployee employee = new Employee(importer);
return employee
}
public IEmployee SaveEmployee(IEmployee employee)
{
SqlEmployeeExporter exporter = new SqlEmployeeExporter();
employee.Export(exporter);
exporter.Save();
}
}
可视化变成了:
EmployeeNameTextBoxExporter exporter = new EmployeeNameTextBoxExporter();
employee.Export(exporter);
exporter.Render();
关于保存操作,也有类似的实现方式。
虽然后一种实现方式去掉了对 Employee
的 getters 的需求,因此是更好的数据封装形式,但它似乎有点臃肿和过于复杂。您对此有何看法?我是否在文章中漏掉或误解了什么?您对使用 getters(和 setters)的一般看法是什么?
这个小实验让我倾向于暂时使用访问器方法。也许您可以改变我的想法 :-)
Exporter
对象实际上是一个 DTO:http://en.wikipedia.org/wiki/Data_transfer_object - Sjoerd