为两种完全不同的类型编写泛型方法
我目前向别人的代码中添加了附加内容,并遇到了使用PdfSharp dll的PdfBuilder类。直到此时,该类在构造函数中采用了称为BoxRequest
的类型。像这样:为两种完全不同的类型编写泛型方法
public PdfDocument GenerateAddressLabelPdf(int id)
{
var box = _unitOfWork.BoxRepository.GetById(id);
var generator = new PdfBuilder(box);
return generator.BuildPdfDocument();
}
而且PdfBuilder
类看起来是这样的:
public class PdfBuilder
{
private readonly BoxRequest _boxRequest;
public PdfBuilder(BoxRequest boxRequest)
{
_boxRequest = boxRequest;
}
public PdfDocument BuildPdfDocument()
{
PdfDocument pdfDocument = new PdfDocument();
PdfPage page = pdfDocument.AddPage();
page.Orientation = PageOrientation.Landscape;
XGraphics gfx = XGraphics.FromPdfPage(page);
XFont font = new XFont("Arial", 40, XFontStyle.Regular);
XTextFormatter tf = new XTextFormatter(gfx);
XRect rect = new XRect(0, (page.Height/4), page.Width, page.Height);
gfx.DrawRectangle(XBrushes.White, rect);
tf.Alignment = XParagraphAlignment.Center;
tf.DrawString(GetText(), font, XBrushes.Black, rect);
return pdfDocument;
}
private string GetText()
{
StringBuilder sb = new StringBuilder();
sb.AppendLine(_boxRequest.Name);
sb.AppendLine(_boxRequest.Department);
sb.AppendLine(_boxRequest.Location.LocationName);
return sb.ToString();
}
}
因此,大家可以看到在GetText
使用的属性从FileRequest
类型采取。
我现在需要再次使用这个类,这次为一个新类型,称为FileRequest
,只要我打电话给这个类,看到它只需要BoxRequest
我认为这可能是一件好事,使通用。
到目前为止,我已经改变了类,像这样:
public class PdfBuilder<T>
{
private readonly T _pdfType;
public PdfBuilder(T t)
{
_pdfType = t;
}
//additional class stuff
}
但现在我为我应该怎么做GetText
方法一般有点困惑,因为我需要使某些线路的每一个类型。
在这一点上,我想我可以将类型传递给GetText
,然后检查类型并根据类型添加不同的行,但它看起来不再是通用的?
我不认为仿制药的处理这个问题的最好方式......
如果所有不同的是,多数民众赞成在GetText
最简单的(不是最好的)的方式来解决,这将是压倒一切的BoxRequest和其他类ToString()
方法而不关心类型。
public class BoxRequest
{
// ...
public override string ToString()
{
StringBuilder sb = new StringBuilder();
sb.AppendLine(this.Name);
sb.AppendLine(this.Department);
sb.AppendLine(this.Location.LocationName);
return sb.ToString();
}
}
public class PdfBuilder
{
private readonly object request;
public PdfBuilder(object request)
{
this.request = request;
}
public PdfDocument BuildPdfDocument()
{
// ...
tf.DrawString(request.ToString(), font, XBrushes.Black, rect);
// ...
}
}
这样,您可以使用该类来PDF任何对象。如果这是通用的(对我来说),你可以提取一个接口ToString()
/GetText()
,并让你的PdfBuilder
消耗(这将是更清洁的海事组织)。
public interface IPdfConvertible
{
public string GetText()
}
// same for FileRequest...
public class BoxRequest : IPdfConvertible
{
// ...
public string GetText()
{
StringBuilder sb = new StringBuilder();
sb.AppendLine(this.Name);
sb.AppendLine(this.Department);
sb.AppendLine(this.Location.LocationName);
return sb.ToString();
}
}
public class PdfBuilder
{
private readonly IPdfConvertible request;
public PdfBuilder(IPdfConvertible request)
{
this.request = request;
}
public PdfDocument BuildPdfDocument()
{
// ...
tf.DrawString(request.GetText(), font, XBrushes.Black, rect);
// ...
}
}
我个人赞成用'GetText()'方法声明一个新的'IPdfPrintable'接口,以便:1)'PdfBuilder'需要该接口的对象(而不是任何对象)。 2)'ToString()'的众所周知的含义是不变的。 –
我只是编辑exaclty,D – nozzleman
有道理,谢谢! – JsonStatham
这不太可能需要泛型。您需要从BoxRequest和FileRequest或\中提取接口,并为它们创建单独的PdfBuilder类(从当然继承)。 – Evk
也许你可以让T成为一个由所有具体对象实现的接口? –
如果所有不同的是'GetText'如何重写'BoxRequest'和其他类'ToString'方法而不关心类型?你可以用'替换'GetText()'。 'input.ToString()'否则,将'GetText()'提取到一个接口并让两个类以合适的方式实现 – nozzleman