TorqueScript: determine if a string is numeric
by Daniel Buckmaster · in Torque 3D Beginner · 05/04/2013 (9:39 pm) · 16 replies
Okay, here's one for you TorqueScript smarties: how would I determine if a string contains nothing but digits? I'm actually trying to do this in T2D but AFAIK the engine functions available are the same between engines.
About the author
Studying mechatronic engineering and computer science at the University of Sydney. Game development is probably my most time-consuming hobby!
#2
Personally I would just add a callback either from C++ or Python into TS to do this test.
05/04/2013 (10:28 pm)
Can you coerce it using?:string strformat ( string format, string value ) Format the given value as a string using printf-style formatting. Parameters: format A printf-style format string. value The value argument matching the given format string. Example: // Convert the given integer value to a string in a hex notation. %hex = strformat( "%x", %value ); See also: http://en.wikipedia.org/wiki/Printf
Personally I would just add a callback either from C++ or Python into TS to do this test.
#3
Demolishun: didn't even know about that function! Thanks. But yes, I would also use a better language... if I could ;P.
05/04/2013 (10:52 pm)
Richard: ok, that's some black magic. Makes good sense, thanks!Demolishun: didn't even know about that function! Thanks. But yes, I would also use a better language... if I could ;P.
#4
(Hand written code):
Should work, not tested.
05/05/2013 (1:20 am)
You could expose isdigit to TorqueScript, or a function isstringnumeric and use that.(Hand written code):
DefineEngineFunction(iStringNumeric, bool, (const char* text), (), "")
{
for(char c : text)
if(!isdigit(c))
return false;
return true;
}Should work, not tested.
#5
Edit: added . for decimals :S
05/05/2013 (7:28 am)
Could also use this :P if you want to use script.// Jeff: checks to see if a string is a number.
function strIsNum(%str)
{
%table = "-.1234567890";
%len = strlen(%str);
for (%i = 0; %i < %len; %i ++)
{
if (strPos(%table, getSubStr(%str, %i, 1)) == -1)
return false;
}
return true;
}untested but should workEdit: added . for decimals :S
#6
05/05/2013 (8:37 am)
Ah, this is what we used....// check for all numbers
%invalidCharacters = "0123456789";
%strippedName = stripChars(%name, %invalidCharacters);
if (%strippedName $= "")
{
// do stuff here
return false;
}We were using this snipped in a file name validation function enforcing at least one non-number character - along with a check for "-+*/%$&§=()[].?\"#,;!~<>|°^{}" and a few other conditions. So, stripChars, not strReplace....
#7
05/05/2013 (9:16 am)
// Returns true if a string passed to it consists of nothing but digits and/or
// decimals. Passes false for strings with more than one decimal, or with a +
// or - as anything but the first character (+ or - are only allowed as the
// first character in the string)
function isCleanNumber(%string)
{
%dot = 0;
for(%i = 0; (%char = getSubStr(%string, %i, 1)) !$= ""; %i++)
{
switch$(%char)
{
case "0" or "1" or "2" or "3" or "4" or "5" or "6" or "7" or "8" or "9":
continue;
case ".":
if(%dot > 1)
return false;
%dot++;
continue;
case "-":
if(%i) // only valid as first character
return false;
continue;
case "+":
if(%i) // only valid as first character
return false;
continue;
default:
return false;
}
}
// %text passed the test
return true;
}
#8
-Jeff
05/05/2013 (9:39 am)
Michael Hall that script seems familiar...was that from the old ancient library.cs from "founder" ?-Jeff
#9
05/05/2013 (9:45 am)
Zodd, I think...
#10
05/05/2013 (9:24 pm)
Okay, next thing I need to look into: adding regular expressions to TS...
#11
Isn't that an enhanced for loop from java? ;)
you probably want this:
untested but should work...
05/06/2013 (7:49 pm)
@LukasQuote: DefineEngineFunction(iStringNumeric, bool, (const char* text), (), "")
{
for(char c : text)
if(!isdigit(c))
return false;
return true;
}
Isn't that an enhanced for loop from java? ;)
you probably want this:
DefineEngineFunction(isStringNumeric, bool, (const char* text), (), "")
{
U32 len = dStrlen(text);
for (U32 i = 0; i < len; i ++)
{
if (!isDigit(text[i]))
return false;
}
return true;
}untested but should work...
#12
05/06/2013 (10:21 pm)
@Jeff probably, did a search on google and someone said you could use the : operator, didn't confirm it before posting.
#13
05/07/2013 (6:19 am)
I think that's a C++11 thing. So it should work for modern versions of VC++. Though the example on Wikipedia uses a handle, not a raw value.
#14
05/07/2013 (12:25 pm)
@Daniel hey thanks for pointing that out, didn't realize that was going to be part of c++. Is it just me or is c++ becoming more like java ;p
#15
05/07/2013 (3:41 pm)
Don't even talk to me about Java :P. Unfortunately I feel like C++11 is fighting a losing battle to make C++ more modern.
#16
05/13/2013 (5:58 pm)
Update, rewrote my function, tested and works in torque3D MIT 3.0. Although this has been "solved" figured what the heck, why not post it.// Jeff: checks to see if a string is numeric
function strIsNumeric(%str)
{
%numeric = "0123456789";
%dot = false;
for (%i = strlen(%str) - 1; %i > -1; %i --)
{
%char = getSubStr(%str, %i, 1);
if (strPos(%numeric, %char) == -1)
{
if (%char $= ".")
{
if (%dot)
return false;
%dot = true;
continue;
}
else if (%char $= "-")
{
if (%i != 0)
return false;
continue;
}
return false;
}
}
return true;
}
Torque Owner Richard Ranft
Roostertail Games