0

为什么这个简单的皮肤检测代码总是返回Message=Arithmetic 运算导致溢出。

xMax = bmp.Width - 1 : yMax = bmp.Height - 1
For y = 0 To yMax
    For x = 0 To xMax
       tmpColor = fixColor(bmp.GetPixel(x, y))
       If (((tmpColor.R > 95) And (tmpColor.G > 40) And (tmpColor.B > 20) And (tmpColor.R - tmpColor.G > 15) And (tmpColor.R > tmpColor.G) And (tmpColor.R > tmpColor.B)) Or _
                ((tmpColor.R > 220) And (tmpColor.G > 210) And (tmpColor.B > 170) And (tmpColor.R - tmpColor.G <= 15) And (tmpColor.R > tmpColor.B) And (tmpColor.G > tmpColor.B))) Then bmp.SetPixel(x, y, Color.Black)
    Next x
Next y
4

1 回答 1

0

假设tmpColor定义为System.Color,有根据的猜测是,当此错误发生时tmpColor.G大于tmpColor.R,这将导致结果小于零,并且无法存储到 中byte

一种可能的解决方案是这样做

Dim r as integer = tmpColor.R
Dim g as integer = tmpColor.G
Dim b as integer = tmpColor.B

然后在您的计算中使用这些新值。它会使代码更清晰一些(如果你要在 if 语句中进行强制转换,则更清晰)。

另一种选择是根据该减法重新排序测试,并使用AndAlso运算符:

(tmpColor.R - tmpColor.G > 15) And (tmpColor.R > tmpColor.G)
'To
(tmpColor.R > tmpColor.G) AndAlso (tmpColor.R - tmpColor.G > 15)

AndAlso是 VB.Net 的短路逻辑与运算符,将导致表达式的计算在第一个False. 由于您使用的只是Ands,因此将它们全部替换为AndAlso可能会看到轻微的性能提升。

总体而言,这两项的组合可能会使代码更具可读性。

于 2012-08-02T06:09:15.053 回答