Delphi isNumber
Posted
技术标签:
【中文标题】Delphi isNumber【英文标题】: 【发布时间】:2011-02-03 09:22:39 【问题描述】:Delphi 中是否有方法可以检查字符串是否为数字而不引发异常?
它用于 int 解析。
如果使用
会引发异常try
StrToInt(s);
except
//exception handling
end;
【问题讨论】:
什么是“无限异常”? 数字是指整数?还是您也想允许实数? 字符串中的数字是否必须是Delphi数字类型可以存储的数字? 19 quintillion 是一个数字,但它不适合任何 Delphi 整数类型。十万分之一是一个数字,但没有任何 Delphi 数字类型可以容纳它。 @Rob Kennedy:if Application.MessageBox('Is this a number?'#13#10+str, MB_YESNO + MB_ICONQUESTION + MB_DEFBUTTON1) = IdYes then ShowMessage(str +' IS a number!') else ShowMessage('Sorry. ''+str+'' doesn't seem to be a number...');
@Jørn,这是一个严肃的问题。我只是想避免显示诸如“19000000000000000 不是数字”之类的无意义错误消息的尴尬。
【参考方案1】:
function TryStrToInt(const S: string; out Value: Integer): Boolean;
TryStrToInt 将字符串 S(以十进制或十六进制表示的整数类型数字表示)转换为分配给 Value 的数字。如果 S 不代表有效数字,则 TryStrToInt 返回 false;否则 TryStrToInt 返回 true。
要在输入字符串中接受十进制但不接受十六进制值,您可以使用如下代码:
function TryDecimalStrToInt( const S: string; out Value: Integer): Boolean;
begin
result := ( pos( '$', S ) = 0 ) and TryStrToInt( S, Value );
end;
【讨论】:
【参考方案2】:var
s: String;
iValue, iCode: Integer;
...
val(s, iValue, iCode);
if iCode = 0 then
ShowMessage('s has a number')
else
ShowMessage('s has not a number');
【讨论】:
这个解决方案的优点是它也适用于实数。以比TryStrToInt
更难阅读为代价。而且它至少需要两个局部变量。
@none: TryStrToInt
应该在 D7 中可用。您为什么接受此解决方案而不是 bassfriend 发布的解决方案?
@Smasher @none TryStrToInt
在 D7 中,以及它的朋友 TryStrToInt64
、TryStrToBool
、TryStrToFloat
、TryStrToCurr
、TryStrToDate
、TryStrToTime
和 @987654331 @。在我看来,OP 接受了错误的答案。
您应该知道 Val 支持以 0x 或 $ 开头的十六进制数字,这可能是您需要的,也可能不是。以下两行都将'16'放入'i'。 val('$10', i, c); val('0x10', i, c);
我不喜欢这个解决方案,因为它会提示您没有使用 iValue。【参考方案3】:
试试这个功能StrToIntDef()
来自帮助
将表示整数(十进制或十六进制表示法)的字符串转换为具有错误默认值的数字。
帕斯卡
function StrToIntDef(const S: string; Default: Integer): Integer;
编辑
刚才查了一下Delphi 2007中TryStrToInt()
函数的来源。如果Delphi 7没有这个函数可以这样写。它只是da-soft answer的精美代码
function TryStrToInt(const S: string; out Value: Integer): Boolean;
var
E: Integer;
begin
Val(S, Value, E);
Result := E = 0;
end;
【讨论】:
这是一个不错的选择如果有一个明显的默认值实际上是有意义的。如果仅用于检查之后的结果是否为-1(例如),TryStrToInt
的健壮性和可读性要好得多。
一个有用的功能,但没有解决所提出的问题。无法判断输入是否为数字。
@David:是的,你是对的,但我只是想提出一个替代方案,它可以帮助用户也设置一些默认值
明白,我只是为了 OP 的利益而指出这一点,以便他意识到这个问题
@David:有可能。字符串 test
包含一个有效整数 iff StrToIntDef(test,-1) = StrToIntDef(test,0)
,并伴随着对前导 '$'
字符的测试。我不会提倡这种解决方案,但它是可能的。【参考方案4】:
XE4 及更新版本:
for ch in s do
TCharacter.IsNumber(ch);
别忘了:
uses System.Character
【讨论】:
【参考方案5】:在 delphi 7 中,您可以使用Val
过程。来自帮助:
单位: 系统
Delphi 语法: procedure Val(S; var V; var Code: Integer);
S 是字符串类型的表达式;它必须是形成有符号实数的字符序列。
V 是整数型或实型变量。如果 V 是整数型变量,则 S 必须是整数。
代码是一个整数类型的变量。
如果字符串无效,则将违规字符的索引存储在 Code 中;否则,代码设置为零。对于以 null 结尾的字符串,Code 中返回的错误位置比错误字符的实际从零开始的索引大一。
【讨论】:
【参考方案6】:使用这个功能
function IsNumber(N : String) : Boolean;
var
I : Integer;
begin
Result := True;
if Trim(N) = '' then
Exit(False);
if (Length(Trim(N)) > 1) and (Trim(N)[1] = '0') then
Exit(False);
for I := 1 to Length(N) do
begin
if not (N[I] in ['0'..'9']) then
begin
Result := False;
Break;
end;
end;
结束;
【讨论】:
【参考方案7】:对于来自 delphi 5 帮助示例的旧 Delphi 版本:
uses Dialogs;
var
I, Code: Integer;
begin
Get text from TEdit control
Val(Edit1.Text, I, Code);
Error during conversion to integer?
if Code <> 0 then
MessageDlg('Error at position: ' + IntToStr(Code), mtWarning, [mbOk], 0);
else
Canvas.TextOut(10, 10, 'Value = ' + IntToStr(I));
end;
【讨论】:
【参考方案8】:在某些语言中,小数分隔符是不同的(例如,“.”用于英语,“,”用于俄语)。对于这些将字符串转换为实数的情况,建议使用以下程序:
function TryStrToFloatMultiLang(const S : String; out Value : Extended) : Boolean;
var
dc : char;
begin
Result := false;
dc := DecimalSeparator;
DecimalSeparator := '.';
try
Result := TryStrToFloat(S, Value);
except
DecimalSeparator := ',';
Result := TryStrToFloat(S, Value);
end;
DecimalSeparator := dc;
end;
更新
正如@Pep 提到的 TryStrToFloat 捕获异常,但它返回布尔值。所以正确的代码是:
function TryStrToFloatMultiLang(const S : String; out Value : Extended) : Boolean;
var
dc : char;
begin
Result := false;
dc := DecimalSeparator;
DecimalSeparator := '.';
Result := TryStrToFloat(S, Value);
if not Result then begin
DecimalSeparator := ',';
Result := TryStrToFloat(S, Value);
end;
DecimalSeparator := dc;
end;
【讨论】:
虽然关于不同小数分隔符的注释非常重要,但您的示例代码试图捕获没有异常的异常,因为 TryStrToFloat 已经捕获了任何可能的异常。这意味着您的“except”子句永远不会执行。 “好球!”,你可能会想 :)【参考方案9】:当你使用程序时
val(s, i, iCode);
并设置值 xd ....
val('xd', i, iCode)
因此我们得到:13
【讨论】:
【参考方案10】:标准单位变体
function VarIsNumeric(v:Variant):Boolean
【讨论】:
这告诉你变体的类型,而不是字符串是否包含数字。以上是关于Delphi isNumber的主要内容,如果未能解决你的问题,请参考以下文章