我希望在使用 C# 生成的 excel 表中进行验证,以便它允许在 excel 单元格中使用日期值或文本“train”。我发现XlDVType.xlValidateDate
用于验证单元格中的日期并XlDVType.xlValidateList
允许文本值。但我想要两者的结合,用户应该能够在单元格中输入日期或特定文本。这可以使用完成XlDVType.xlValidateCustom
吗?
对此的任何帮助将不胜感激。
我希望在使用 C# 生成的 excel 表中进行验证,以便它允许在 excel 单元格中使用日期值或文本“train”。我发现XlDVType.xlValidateDate
用于验证单元格中的日期并XlDVType.xlValidateList
允许文本值。但我想要两者的结合,用户应该能够在单元格中输入日期或特定文本。这可以使用完成XlDVType.xlValidateCustom
吗?
对此的任何帮助将不胜感激。
我想要两者的组合,用户应该能够在单元格中输入日期或特定文本。
以下代码片段为工作表中的单元格 A1 设置所需的验证:
Excel.Range range = xlWorkSheet.Range["A1"];
range.ClearFormats();
range.Validation.Delete();
range.Validation.Add(Excel.XlDVType.xlValidateCustom,
Formula1: "=OR(EXACT(LEFT(CELL(\"format\",A1)),\"D\"),EXACT(A1,\"train\"))");
最复杂的部分是实际的验证公式。它使用以下功能:
EXACT(cell,string)
将单元格的内容与文字字符串进行比较,TRUE
仅当它们完全相同时才返回。
CELL("format",cell)
返回包含指定单元格格式的代码,其中日期代码始终以D
. 有关说明和所有可能代码的列表,请参阅Office 帮助。CELL
此片段仅查看第一个字符,它必须是 aD
才能将内容格式化为某种日期。
LEFT(text,count)
返回 中最左边的count
字符text
,count
默认为 1。在这种情况下,TRUE
如果内容是某种日期,则返回。
OR(logical1, logical2)
返回logical1 OR logical2
,所以TRUE
如果内容是日期,或者完全等于字符串"train"
。
此解决方案尚不理想,因为A1
已硬编码到公式中。有一种方法可以解决这个问题,这里INDIRECT
描述。您可能需要这样做,例如,如果您想一次性将验证应用于整个单元格范围。在这种情况下,硬编码需要替换为,这是指示当前 shell 的机制。您可以将其作为.A1
INDIRECT("RC",FALSE)
INDIRECT("R"&ROW()&"C"&COLUMN(),FALSE)
通过这种调整,他的最后一行代码看起来像这样(在 Excel 中测试,但不是从 C# 中测试):
range.Validation.Add(Excel.XlDVType.xlValidateCustom,
Formula1: "=OR(EXACT(LEFT(CELL(\"format\",INDIRECT(\"RC\",FALSE))),\"D\"),EXACT(INDIRECT(\"RC\",FALSE),\"train\"))"
更新
正如 OP 指出的那样,如果首先将日期输入到单元格中,然后将日期更改为不正确的字符串或数字值,则这种方法似乎存在问题 - 请参阅下面的评论。因此,使用该CELL
功能似乎不是最好的方法。
但是,如果单元格格式被显式设置为(更灵活的)Text
格式,则可以使用以下行进行验证:
range.Validation.Delete();
range.NumberFormat = "Text";
range.Validation.Add(Excel.XlDVType.xlValidateCustom,
Formula1: =OR(ISNUMBER(DATEVALUE(INDIRECT(\"RC\",FALSE))),EXACT(INDIRECT(\"RC\",FALSE),\"train\"));
再次在 Excel 中测试,但不是在 C# 中测试。