Make method parameter strongly typed without if/switch
Given a class method can generate report based on the type passed in from method parameter, an easy way to make parameter strongly typed is using enum:
class ReportGenerator
{
string _reportTypeInString;
enum ReportType
{
PDF = 0,
EXCEL,
HTML
}
void GetReport(ReportType reportType)
{
switch (reportType)
{
case ReportType.PDF:
_reportTypeInString = "PDF";
break;
case ReportType.EXCEL:
_reportTypeInString = "EXCEL";
break;
case ReportType.HTML:
_reportTypeInString = "HTML40";
break;
}
// logic to generate real report...
}
}
The problem here is: enum type in dotnet only supports integer, converting to string has to be done somewhere usually in a place different than the type define area, maintenance is problematic. Besides, the evil if/switch code smell.
Here is my way to do the same job:
public class ReportFormat
{
public string ReportFormatString { get; private set; }
public static ReportFormat HTML32 = new ReportFormat("HTML3.2");
public static ReportFormat HTML40 = new ReportFormat("HTML4.0");
public static ReportFormat EXCEL = new ReportFormat("EXCEL");
public static ReportFormat CSV = new ReportFormat("CSV");
public static ReportFormat PDF = new ReportFormat("PDF");
public static ReportFormat MHTML = new ReportFormat("MHTML");
ReportFormat(string reportFormatString)
{
ReportFormatString = reportFormatString;
}
}
//in my report generator class:
public FileContentResult GetReport(string reportName, ReportFormat reportFormat, IList<ParameterValue> parameters)
{...}
// how to use
var fileContentResult = reportingServiceProxy.GetReport(ReportName, ReportingServiceProxy.ReportFormat.HTML40, parameters);
Work amount is almost same, the type maintenance is in same place, the biggest selling point, no evil if/switch statement anymore.
Which design pattern is used here?






WellKnownType
Never heard it, but I think it’s a variation of Null object pattern.
How about using
Dictionary _reportType = new Dictionary
{
{ ReportType.PDF, “PDF” },
//…
}
instead of those “if else”‘s
This was my original plan actually. I realize this dictionary must sit somewhere outside of the ReportFormat class in which I really want encapsulate the mapping data. Basically both solution are almost same, while non-dictionary one is more maintainable, I think.