Reputation: 1211
I'm looking to ensure the number of characters on a given value are less than 1000. My function is unsure whether the value is an array, hash or scalar.
if (ref($value) eq 'SCALAR' && length($value) >= 1000 ) {
return;
}
However, what happens if a number is passed in? Will I be unknowingly converting a number value to a string, and if so, is there a way of checking for a numeric value before checking its length?
Upvotes: 0
Views: 191
Reputation: 54373
In your question, you are saying that you check the number of characters in a string, and that the variable containing it could also be a hash ref or array ref.
if (ref($value) eq 'SCALAR' && length($value) >= 1000 ) { return; }
However, your code does not check the length of the string or number. It assumes the variable might be a scalar reference, but then checks the length of the stringification of the scalar reference.
say \"asdf";
# SCALAR(0x268e7f8)
say length \"asdf";
# 17
This length should always be 17 on 64 bit systems, or 16 on 32 bit systems.
Once you actually dereference your scalar reference, the following will apply.
# here and here
# ## #
if (ref($value) eq 'SCALAR' && length( ${ $value } ) >= 1000 ) {
return;
}
Since Perl has no types, the number will be treated as a string. Passing "500"
is the same as passing 500
.
say length 500;
say length "500";
__END__
3
3
The variable itself will not be converted. You don't need to care about that at all. Your code is fine, as long as you contain the number in a scalar reference.
The scalar reference doesn't care if it references a string or a number.
say length ${ \500 };
say length ${ \"500" };
__END__
3
3
Upvotes: 7
Reputation: 386331
If $value
is a number as you claim, then ref
will return an empty string, so execution will continue on to the next statement. You simply want
if (!ref($value) && length($value) >= 1000 ) {
return;
}
This will take the length of the stringification of the $value
, so length(500)
is the same as length("500")
, which is 3
.
If $value
is a reference to a number, your code is wrong too. length($value)
will take the length of the stringification of the reference. You want
if (ref($ref) eq 'SCALAR' && length($$ref) >= 1000 ) {
return;
}
$$ref
(short for ${ $ref }
) is the scalar to referenced by $ref
.
(Note that it's very rare to have a reference to a scalar.)
Upvotes: 1