Una buena práctica es evitar los ifs anidados o switch case, para ello se puede usar el Polimorfismo.
Voy a poner un ejemplo
Tengo un switch el cual, según el tipo de documento llama a una función de una clase estática.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 |
// doc --> es el Path del documento switch (Path.GetExtension(doc).ToLower()) { case ".txt": { return CreatePdf.ConvertirTextoaPdf(doc); break; } case ".doc": case ".docx": { return CreatePdf.ConvertirDocaPdf(doc); break; } case ".xls": case ".xlsx": { return CreatePdf.convertirExcelaPdf(doc); break; } case ".bmp": case ".jpeg": case ".jpg": case ".gif": case ".png": { return CreatePdf.ConvertirImagenaPdf(doc); break; } case ".msg": { return CreatePdf.ConvertirMsgaPdf(doc); break; } } |
Clase estática.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 |
public static class CreatePdf { public static byte[] ConvertirTextoaPdf(string path) { } public static byte[] ConvertirImagenaPdf(string path) { } public static byte[] ConvertirDocaPdf(string path) { } public static byte[] convertirExcelaPdf(string path) { } public static byte[] ConvertirMsgaPdf(string path) { } } |
Ahora voy a crear las clases y cambiar el código para quitar el switch.
Lo primero creo una clase de tipo Interfaces, y creo para cada tipo de documento su clase.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 |
//Interface public interface IDocumentoTipo { public byte[] ConvertirPdf(string path); } // Clases por tipo public class DocumentoDoc:IDocumentoTipo { public byte[] ConvertirPdf(string path) {} } public class DocumentoImg:IDocumentoTipo { public byte[] ConvertirPdf(string path) {} } public class DocumentoMsg:IDocumentoTipo { public byte[] ConvertirPdf(string path) {} } public class DocumentoTxt:IDocumentoTipo { public byte[] ConvertirPdf(string path) {} } public class DocumentoXls:IDocumentoTipo { public byte[] ConvertirPdf(string path) {} } |
Ahora en la función lo cambio, usando una constante de tipo diccionario para identificar la clase correspondiente.
1 2 3 4 5 6 7 8 9 10 11 12 |
//Utilizaremos un diccionarío para identificar cada tipo a que clase corresponde. Dictionary<string, IDocumentoTipo> _conversorDocumento = new Dictionary<string, IDocumentoTipo>() { { ".txt", new DocumentoTxt() }, {".doc", new DocumentoDoc() }, { ".docx", new DocumentoDoc() }, {".xls", new DocumentoXls()},{".xlsx", new DocumentoXls()}, {".bmp", new DocumentoImg()},{".jpeg", new DocumentoImg()}, {".jpg", new DocumentoImg()},{".gif", new DocumentoImg()}, {".png", new DocumentoImg()}, {".msg", new DocumentoMsg()}}; //El switch lo sustituimos por var conversor = _conversorDocumento[Path.GetExtension(doc).ToLower()]; return conversor.ConvertirPdf(doc); |
Hola! En la clase estática inicial CreatePdf, el método convertirExcelaPdf tiene dos parámetros por lo que no alcanzaría con implementar la interface IDocumentoTipo en la clase DocumentoXls. Cómo lo resolviste?
Saludos
Hola Dari
Realmente obvie el parámetro y me quedo la estructura. Lo he quitado para que no cree confusión
Lo que se me ocurre es que podrías crear una estructura con dos parámetros para todos los casos y el segundo parámetro que sea opcional.
public byte[] ConvertirPdf(string path, string encabezado=””)
Si se te ocurre una forma mejor o a alguien, lo podría compartir
Gracias