假设我的第一个类有一个公共属性,它返回要导出的文件的标题。例如:
private readonly List<string> fileHeaders = new List<string>
{
"Last Name",
"First Name",
"Middle Name",
"Suffix",
"Degree",
};
public List<string> FileHeaders
{
get { return fileHeaders; }
}
现在我有一个class B
,它导出的文件头只有区别在于它还有一个要导出的列标题,例如一个地址列。
什么是良好的面向对象设计可以做到这一点?
答案 0 :(得分:4)
使fileHeaders
成为基类的受保护成员。类似的东西:
public class Base
{
protected List<string> fileHeaders;
public List<string> FileHeaders
{
get
{
return fileHeaders;
}
}
}
public class A : Base
{
public A()
{
fileHeaders = new List<string>
{"Last Name", "First Name", "Middle Name", "Suffix", "Degree"};
}
}
public class B : Base
{
public B()
{
fileHeaders = new List<string>
{"Last Name", "First Name", "Middle Name", "Suffix", "Degree", "Something Else"};
}
}
如果它有意义(语义上),你也可以将A
作为基类,并且B
继承,例如,如果它只是B
的情况还有一个专栏。如下所示:
public class A
{
protected readonly List<string> fileHeaders = new List<string>
{
"Last Name", "First Name", "Middle Name", "Suffix", "Degree",
};
public List<string> FileHeaders
{
get
{
return fileHeaders;
}
}
}
public class B : A
{
public B()
{
fileHeaders.Add("Something Else");
}
}
答案 1 :(得分:2)
由于两个实例仅在数据上有所不同,为什么不创建一个具有列表作为成员和只读属性的类(如上所述)并使用构造函数中的参数初始化它?不需要不同的课程。
答案 2 :(得分:1)
I'd prefer this solution with an interface and abstract base class that enforces the implementation in derived classes.
This covers the SOLID open-closed principle
public interface IFileHeaders
{
IList<string> GetFileHeaders();
}
public abstract class FileHeaderBase : IFileHeaders
{
protected abstract IList<string> FileHeaders { get; }
public IList<string> GetFileHeaders() => FileHeaders;
}
This covers a basic implementation:
public class FileHeaderList1 : FileHeaderBase
{
private readonly IList<string> _fileHeaders = new List<string>
{
"Last Name" ,
"First Name" ,
"Middle Name" ,
"Suffix" ,
"Degree" ,
};
protected override IList<string> FileHeaders => _fileHeaders;
}
This covers lazy loading:
public class FileHeaderList2 : FileHeaderBase
{
private IList<string> _fileHeaders;
protected override IList<string> FileHeaders
{
get
{
if ( _fileHeaders == null )
{
_fileHeaders = new List<string>
{
"Address" ,
};
}
return _fileHeaders;
}
}
}
This covers dependency injection:
public class FileHeaderList3 : FileHeaderBase
{
private readonly IList<string> _fileHeaders;
public FileHeaderList3( IList<string> fileHeaders )
{
_fileHeaders = fileHeaders;
}
protected override IList<string> FileHeaders => _fileHeaders;
}