验证货币允许超过两位小数

Validating currency allows more than two decimal places

情况:

我正在 VS2013 和 .NET4.0 中使用 C# 编写 Winforms 应用程序。

datagridview 中的某些单元格需要验证为格式正确的英国货币值。 dgv 单元格格式设置为带两位小数的货币。为了进行验证,我使用了以下代码:

decimal convertedCurrency;

if (decimal.TryParse(dataGrid.Rows[e.RowIndex].Cells[e.ColumnIndex].EditedFormattedValue.ToString(), NumberStyles.Currency, null, out convertedCurrency))
{
    if (convertedCurrency > columnDetails.MaxValue || convertedCurrency < 0)
    {
        this.ReportError(dataGrid, e, dataGrid.Columns[e.ColumnIndex].HeaderText + " must be between £0 and £" + columnDetails.MaxValue);
    }
}
else
{
    this.ReportError(dataGrid, e, "Incorrect format for a money value");
} 

问题:

除非用户输入的值超过两位小数,例如100.001。这被认为是有效的,这个值被写入数据库。

问题:

我怎样才能最好地验证捕获并处理小数点后两位以上的用户输入?我当然可以进行一些混乱的字符串处理,但有没有更优雅的方式,最好继续使用 TryParse?

我建议三种可能的解决方案:

1) 使用 MaskedTextBox 从一开始就避免了问题

2) 创建一个 keyup 事件 parse/check 输入正确格式

3) 在输入中使用正则表达式:^[0-9].[0-9]{2}$ 或 ^[0-9].[0- 9][0-9]$

参见 Find number of decimal places in decimal value regardless of culture 查找小数位数。只需验证它 <= 2.

例如

decimal value = 123.456m;
if (GetDecimalPlaces(value) > 2)
{
    // Error
}

int GetDecimalPlaces(decimal d)
{
    int count = BitConverter.GetBytes(decimal.GetBits(argument)[3])[2];
}