Question Marek Bernád · Jul 28, 2017

How to detect if string data is number and integer in COS ?

Good day,

I would like to know how to detect in Caché ObjectScript if data saved in string is number and furthermore, if it's type is integer.


I maybe found a solution:
 

set value = "44.2d3"

try{
     set status = $INUMBER(value,"")
     if ('$FIND(+value,".")){
          w "your variable: '"_value_"' is number and integer"
     }else{
          w "variable is number but no integer"
     }
}catch(e){
     w "variable is not number" 
}



But I don't know how to do it correctly or if there exist better solution in COS (or maybe my solution is incorrect).

Thanks in advance for answers.

Comments

Rubens Silva · Jul 28, 2017

set number = "1234"
write number?.N // 1, so it's integer.
set number = "44.2d3"
write number?.N // 0, so it's float, double or whatever data type with precison.
You can read more about Pattern Matching here.

0
Marek Bernád  Jul 29, 2017 to Robert Cemper


Are you sure that this will work?
USER > set number = "21d20"

USER > if (number\1 = +number) { w "number and integer" } else { w "not number and not integer" }
will output that it is "number and integer", because number\1 will turn string "21d20" to "21" as a result. 
Moreover +number will result from "21d20" to "21" ... and will tell that really 21 equals 21 ... but "21d20" is not number

0
Ed de Moel · Jul 28, 2017

Well, that's an interesting one.

One way to check whether the value of a string is a number is:

   If +value=value

which will work in most cases.

However, when the value of a string is something like "1E12345", you'd get an error (<MAXNUMBER>), because "exponential notation" is assumed. But in all other cases, that would work.

Similarly:

   If +value?1.N

Would get close to determining that a value is an integer, but "00000123" would also match that pattern, so

   If value?1.N,+value=value

would do the trick in this case.

Hope this helps

0
Robert Cemper  Jul 29, 2017 to Marek Bernád

You are right. The check for pure number got lost

if  +number=number  has to precede 

so the combined is  if  +number=number,number\1=+number

0
Sergei Shutov  Jul 30, 2017 to Robert Cemper

I believe that would be equal to just 

if number\1=number

0
Robert Cemper  Jul 31, 2017 to Sergei Shutov

This is a matter of interpretation.
If you also allow leading 0 for integers   (eg. 00123) then you need to normalize it.

0
Sergei Shutov  Jul 31, 2017 to Robert Cemper

But 

if  +number=number,number\1=+number

doesn't allow leading zeroes either.

0
Robert Cemper · Jul 28, 2017

The oldest and most simple and fastest integer check is
if value\1=+value

\1 strips trailing decimals,  + strips leading 0

; just pure integer arithmetics no string checks

0
Alexey Maslov · Aug 1, 2017

If +value=value

This classic code is good for checking if the value is canonical number, while the term number can be interpreted in some other ways, e.g. a number in scientific format, double precision number, etc. Caché has a set of out-of-the-box functions to perform some of these checks, e.g. $isvalidnum, $isvaliddouble, $number, $normalize.

So, the answer depends on topic starter's conditions.

E.g., if I need to check if a number is a numlit (scientific numbers and numbers with starting zeroes are allowed), I'd use `$isvalidnum(x)`. Addition check on being integer (an intlit) can look like: `$isvalidnum(x)&&(+x\1=+x)`. Here are some testing results: 

USER> w !,?6,"Is number?",?20,"Is integer?",?35,"Is canonic?"
USER> for x="001a","002",0,1,"-1.2","+1.3","1E3" w !,x,?10," ",$isvalidnum(x),?20," ",$isvalidnum(x)&&(+x\1=+x),?35,x=+x
 
      Is number?    Is integer?    Is canonic?
001a       0         0             0
002        1         1             0
0          1         1             1
1          1         1             1
-1.2       1         0             1
+1.3       1         0             0
1E3        1         1             0

In other conditions I'd write another code. There is no universal answer to topic starter's question.

P.S. As to "Annotated MUMPS Standard" (http://71.174.62.16/Demo/AnnoStd):
An intlit is not necessarily a canonic representation of a number.

numlit is not necessarily a canonic representation of a number.

The reduction to a canonical numeric representation involves (colloquially) the removal of any redundant leading and trailing zeroes, the conversion of exponentionential notation to "mantissa only" notation, and the reduction of any leading plus (+) and minus (-) signs to at most one leading minus sign (see also Numeric interpretation of data).

0