这一直是我遇到的最令人沮丧的愚蠢错误之一,我只是想看看其他人是否曾遇到此问题。
这是交易。我在VB 2008(.NET 3.5)中的Windows窗体应用程序中有一个TextBox,用户可以在其中键入估计数量。我允许他们兑换美元和美分,我想要四舍五入到最接近的美元。原始代码在将数据写回表时进行了舍入,并且运行正常 - 我将此代码放在“保存”例程中,当用户移动到不同的屏幕或记录时触发该例程:
Dim est As Decimal : Decimal.TryParse(txtEstimateAmount.Text.Trim, est)
Dim estimatedAmount As Integer = Math.Round(est)
我决定,一旦他们离开现场实际进行舍入可能会很好,所以当他们重新加载屏幕并发现1822.60现在是1823时他们并不感到惊讶。所以我采用完全相同的代码并将其添加到TextBox.Leave事件处理程序中。最奇怪的事情发生了:在解析之后,用1822.60填充变量 \ test ,而不是变量设置为-1!什么......?
调试处理程序会显示该值正确进入解析器,如果我通过Immediate窗口手动解析,它会正确解析,但是当我让代码执行时,它总是设置为-1。甚至更奇怪的是任何数字被解析为-1,而不仅仅是小数,而任何非数字都被解析为0(这是正确的)。
有没有其他人遇到此事?我尝试将代码移动到TextBox.LostFocus事件,但结果相同。我不知道到底发生了什么,显然有很多变通方法,但它没有任何意义。
编辑:这是完整的事件处理程序(当前行为是在TextBox中放置-1):
Private Sub txtEstimateAmount_Leave(ByVal sender As Object, ByVal e As System.EventArgs) Handles txtEstimateAmount.Leave
' Take any dollars-and-cents amount and round to the nearest dollar
Dim est As Decimal
est = Decimal.TryParse(txtEstimateAmount.Text.Trim, est)
txtEstimateAmount.Text = If(est <> 0, Math.Round(est).ToString(), String.Empty)
End Sub
答案 0 :(得分:5)
首先,您确实需要使用Validating事件处理程序执行此操作,以便您可以捕获垃圾并避免忽略TryParse的返回值。像这样:
Private Sub TextBox1_Validating(ByVal sender As System.Object, ByVal e As System.ComponentModel.CancelEventArgs) Handles TextBox1.Validating
Dim est As Decimal
If TextBox1.Text.Length = 0 then Exit Sub '' optional
If Not Decimal.TryParse(TextBox1.Text.Trim, est) Then
e.Cancel = True
TextBox1.SelectAll()
Else
TextBox1.Text = est.ToString("N0")
End If
End Sub
解释-1很困难。如果TryParse无法解析文本,则通常会写入0。注意更改UI线程的CurrentCulture属性。以及对“控制面板+区域和语言”小程序中的格式设置所做的任何更改。
答案 1 :(得分:2)
我认为您发布的代码不是您正在运行的代码。发生的事情是:
Dim est As Decimal = Decimal.TryParse(txtEstimateAmount.Text.Trim, est)
Dim estimatedAmount As Integer = Math.Round(est)
我会做一个干净的重建或尝试用不同的格式重写它,也许用布尔值来获得tryparse的结果。
编辑,我已经看到了你的实际代码。您确实将tryparse结果中的true / false放入了est十进制数。删除est =。 Est被加载,因为它通过引用传递给tryparse。