如何重构一系列if-then语句?

我正在编写一个脚本来检查一堆Excel电子表格的特定值,我已经完成了看起来像这样的代码:

public bool checkContents(Excel._Worksheet sht, string address, string cellValue) { Excel.Range tempRange = sht.get_Range(address); return Convert.ToString(tempRange.Value) == cellValue; } public string getVersion(Excel._Worksheet sht) { if (checkContents(sht,"a4","Changes for Version 24")) { return "24"; } else if (checkContents(sht,"a1","Changes for Version 23 (Official)")) { return "23"; } else if (checkContents(sht,"a2","Changes for Version 22")) { return "22"; } //and so on for another 10 if-else blocks } 

我知道,对于给定的表格,只有一个if语句是真的。

有没有一个更简洁的方法来写这个函数,而不是作为一个长的序列if

你可以尝试这样的事情(未经testing,所以可能会有一些语法错误)

  private class VersionSpec { public string Address { get; private set; } public string CellValue { get; private set; } public string Version { get; private set; } public VersionSpec (string address, string cellValue, string version) { Address = address; CellValue = cellValue; Version = version; } } public string getVersion(Excel._Worksheet sht) { VersionSpec[] versionSpecs = new [] { new VersionSpec("a4", "Changes for Version 24", "24"), new VersionSpec("a1", "Changes for Version 23 (Official)", "23"), new VersionSpec("a2", "Changes for Version 22", "22"), // other versions... } foreach(VersionSpec versionSpec in versionSpecs) { if(checkContents(sht, versionSpec.Address, versionSpec.CellValue)) { return versionSpec.Version; } } } 

由于您的单元格值看起来不一致,因此可以将所有参数放入自定义对象的列表中,这些列表沿着。

 public class Version { public string CellAddress { get; set; } public string CellValue { get; set; } public string ReturnValue { get; set; } } 

然后用你的各种版本加载一个List<Version> 。 之后,您可以在列表中使用一个foreach循环,并在其中一个命中时作出反应。

使用.Net 4.0 Excel Interop,您不需要使用下划线_Types,而使用方括号。

 public bool checkContentsStartsWith(Worksheet sht, string address, string cellValue) { Range tempRange = sht.Range[address]; return cellValue.StartsWith(tempRange.Value2); } public string getVersion(Worksheet sht) { for (int j = 1; j < 4;j++) { for (int i = 24; i > 0; i--) { if (checkContentsStartsWith(sht, "A" + j.ToString(), "Changes for Version " + i)) { return i; } } } } 

如果其余的if-blocks与发布的样本结构相同,这里有一个清晰的模式; 难道你不能检查更大的范围(例如:“a1:a4”)是否存在string“版本变更”,返回该string,并parsing出你想返回的整数。 如果你稍微调整一下你的想法,你应该能够把它降低到2-3 LOC。

一些代码来阐明;

  public static string getVersion(Worksheet sht) { Range range = sht.Range["A1:A10"]; foreach (Range c in range.Cells) { if (null == c.Value2) continue; string val = c.Value.ToString(); if (val.Contains("Changes for Version ")) { int startIndex = ("Changes for Version ").Length; return val.Substring(startIndex, 2).Trim(); } } return null; } 

我有另一个答案:

 using (var usedRange = sheet.UsedRange.WithComCleanup()) { string firstAddress = string.Empty; string nextAddress = string.Empty; using (var firstCell = usedRange.Resource.Find("Changes for Version", LookIn: XlFindLookIn.xlValues).WithComCleanup()) { if (firstCell.Resource != null) { firstAddress = firstCell.Resource.Address; AppendListOfVersion(sheet.Name, firstCell.Resource); nextAddress = firstAddress; } } } if (firstAddress != "") // the first Find attempt was successful, so keep looking (FindNext) { var keepLooking = true; while (keepLooking) { using (var prevCellToFindNextFrom = sheet.Range[nextAddress].WithComCleanup()) using (var nextCell = usedRange.Resource.FindNext(prevCellToFindNextFrom.Resource).WithComCleanup()) { if (nextCell.Resource == null) keepLooking = false; else { nextAddress = nextCell.Resource.Address; if (nextAddress == firstAddress) keepLooking = false; else AppendListOfVersion(sheet.Name, nextCell.Resource); } } } } 

你可以在这里了解WithComCleanUp(): http ://jake.ginnivan.net/vsto-com-interop

这里有几个选项:

  public string getVersion(Excel._Worksheet sht) { if (checkContents(sht, "a4", "Changes for Version 24")) return "24"; if (checkContents(sht, "a1", "Changes for Version 23 (Official)")) return "23"; if (checkContents(sht, "a2", "Changes for Version 22")) return "22"; //and so on for another 10 if-else blocks } public string getVersion(Excel._Worksheet sht) { string[][] values = new string[3][]{ new string[3]{"a4","Changes for Version 24","24"} ,new string[3]{"a1", "Changes for Version 23 (Official)","23"} ,new string[3]{"a2", "Changes for Version 22","22"} }; foreach (string[] strings in values) { if (checkContents(sht, strings[0], strings[1])) return strings[2]; } return null; //or throw not found error }