浏览一些遗留代码,我遇到了一些"空"除了块。它们都是出于类似的原因实现的,即处理从TEdit中的文本到数值的转换。由于TEdit可能为空,因此在这种情况下应该没有错误消息:
procedure TmyForm.EditExit(Sender: TObject);
begin
...
try
_value := StrToFloat(Edit.Text);
except
end;
...
end;
这很有效,但我认为这不是一个好的做法。有没有更好的方法来获得相同的行为?
答案 0 :(得分:4)
您应该使用TryStrToFloat
:
function reinitSwiper(swiper) {
setTimeout(function () {
swiper.reInit();
}, 500);
}
这是一个返回指示转换成功的布尔值的函数。成功时,转换后的值将以out参数返回。
答案 1 :(得分:3)
TLDR 请勿寻求“适合所有人”的“一刀切”。例外吞咽者的毯子更换选项。而是确定您在每种情况下尝试解决的具体问题,并确保您的代码明确传达其意图。
您可能已经知道这一点,但我想强调所提供代码中的一些问题。理解这些问题会在可能出错的地方产生明显的可能性。在每种情况下考虑您想要的行为是有帮助的,您应该确保您的代码明确反映您的决策,使其更易于阅读和维护。
begin
...
try
_value := StrToFloat(Edit.Text);
except
end;
...
end;
吞咽异常的原因解释如下:
由于TEdit可能为空,因此在这种情况下不应出现错误消息。
StrToFloat
中引发了异常,则会跳过对_value
的分配。所以它保留了之前的价值。
_value
的方法将正确分配给某些计算。_value
不正确。EDivByZero
或只是不正确的结果。如前所述,你如何修复异常吞咽者取决于你在每种情况下的意图(是的,这样做的工作更多,但是如果你正在修复它有助于解决它的问题"正确"。)
你真的需要隐瞒"用户犯了错误"
假设代码中没有其他错误处理错误:
'Hello' is not a valid floating point value.
。'' is not a valid floating point value.
。因此,值得认真考虑的一个选择是:只需删除吞咽者。
begin
...
_value := StrToFloat(Edit.Text);
...
end;
由于您在TEdit
为空时特别关注引发错误,因此您可能会将此视为特殊情况。
0
是合适的默认值可能是有意义的。 NB!只有在确实是适当的默认值时才这样做。 (见下一点) 在任何一种情况下,都明确地处理特殊情况并允许默认错误报告以其他方式启动。
begin
...
if (Trim(Edit.Text) = '') then
_value := 0
//or _valueIsNull := True;
else
_value := StrToFloat(Edit.Text);
...
end;
注意:您当然也可以在用户更新控件之前在控件值中设置默认值0
。这使得默认设置为用户。如果用户选择删除 默认值,则还原为选项1会通知用户不允许这样做。
可以使默认错误处理更加用户友好。例如。您可能需要更详细的信息,确保将焦点设置为“错误控制”,或设置提示消息。
在这种情况下,您希望根据David的回答使用TryStrToFloat()
。 据我所知,这是在Delphi 7中引入的。(在旧版本中,您可以使用TextToFloat()
。例如,检查StrToFloat()
的实现。)
以下是一个可能的示例,用于演示如何编写一些简单的实用程序函数来封装您的特定需求,并使您对某些案例的特殊处理是明确的。
type
TDefaultMode = (dmNone, dmDefaultEmptyValue, dmDefaultInvalidValue);
function ReadFloatFromEditControl(AEdit: TCustomEdit; ADefaultMode: TDefaultMode = dmNone; ADefaultValue: Double = 0.0): Double;
begin
if not TryStrToFloat(AEdit.Text, Result) then
begin
if (ADefaultMode = dmDefaultEmptyValue) and (Trim(AEdit.Text) = '') then
Result := ADefaultValue
else if (ADefaultMode = dmDefaultInvalidValue) then
Result := ADefaultValue
else
begin
AEdit.SetFocus;
raise EConvertError.Create('['+AEdit.Text+'] is an invalid floating point value.');
end;
{If default is applied, replace value in edit control}
AEdit.Text := FloatToStr(Result);
end;
end;
{Use as follows:}
v1 := ReadFloatFromEditControl(Edit1);
v2 := ReadFloatFromEditControl(Edit2, dmDefaultInvalidValue);
v3 := ReadFloatFromEditControl(Edit3, dmDefaultEmptyValue, 1.0);