web-dev-qa-db-ja.com

PHP変数が整数かどうかを確認

私はこれを持っていますPHPコード:

$entityElementCount = (-($highScore-$totalKeywordCount))/0.29;

私が知りたいのは、$ entityElementCountが整数(2、6、...)か部分的(2.33、6.2、...)かを確認する方法です。

ありがとうございました!

31
spacemonkey
$entityElementCount = (-($highScore-$totalKeywordCount))/0.29;
if (ctype_digit($entityElementCount) ){
    // (ctype_digit((string)$entityElementCount))  // as advised.
    print "whole number\n";
}else{
    print "not whole number\n";
}
18
ghostdog74
if (floor($number) == $number)
42
Tyler Carter

これは古いことはわかっていますが、見つけたばかりのものを共有したいと思いました。

fmod を使用し、0を確認します

_$entityElementCount = (-($highScore-$totalKeywordCount))/0.29;
if (fmod($entityElementCount,1) !== 0.0) {
    echo 'Not a whole number!';
} else {
    echo 'A whole number!';
}
_

fmodは%とは異なります。小数がある場合、%は機能しないようです(たとえば、0を返します...たとえば、_echo 9.4 % 1;_は_0_を出力します)。 fmodを使用すると、小数部分が得られます。例えば:

echo fmod(9.4, 1);

_0.4_を出力します

39
Joseph

私は intval 関数を次のように使用します:

if($number === intval($number)) {

}

テスト:

var_dump(10 === intval(10));     // prints "bool(true)"
var_dump("10" === intval("10")); // prints "bool(false)"
var_dump(10.5 === intval(10.5)); // prints "bool(false)"
var_dump("0x539" === intval("0x539")); // prints "bool(false)"

その他の解決策

1)

if(floor($number) == $number) {   // Currently most upvoted solution: 

テスト:

$number = true;
var_dump(floor($number) == $number); // prints "bool(true)" which is incorrect.

2)

if (is_numeric($number) && floor($number) == $number) {

コーナーケース:

$number = "0x539";
var_dump(is_numeric($number) && floor($number) == $number); // prints "bool(true)" which depend on context may or may not be what you want

3)

if (ctype_digit($number)) {

テスト:

var_dump(ctype_digit("0x539")); // prints "bool(false)"
var_dump(ctype_digit(10)); // prints "bool(false)"
var_dump(ctype_digit(0x53)); // prints "bool(false)"
10
Martin Vseticka

チャチャが言ったように、基本的な方法は

if (floor($number) == $number)

ただし、浮動小数点型は数値を正確に格納できません。つまり、1は0.999999997として格納される可能性があります。もちろん、これは上記のチェックが失敗することを意味します。目的のためであっても、0に切り捨てられるためです。 十分近い 1から整数と見なされます。したがって、次のようなことを試してください:

if (abs($number - round($number)) < 0.0001)
9
Aistina

数値であることがわかっている場合(つまり、_"ten"_や_"100"_のように、文字列としてキャストされた整数ではない場合)、is_int()を使用できます。

_$entityElementCount = (-($highScore-$totalKeywordCount))/0.29;
$entityWholeNumber = is_int($entityElementCount);

echo ($entityWholeNumber) ? "Whole Number!" : "Not a whole number!";
_
6
Anthony

私は提案されたすべてのソリューションをテストしましたが、問題のある多くの値が言及されていましたが、それらはすべて少なくとも1つのテストケースで失敗しました。 _$value_がis_numeric($value)を使用して数値であるかどうかのチェックを開始すると、多くのソリューションの失敗の数が減少しますが、最終的なソリューションにはなりません。

_$test_cases = array(0.29, 2, 6, 2.33, 6.2, '10.00', 1.4, 10, "10", 10.5, "0x539", true,
    false, 0x53, 9.4, "ten", "100", 1, 0.999999997, 0, 0.0001, 1.0, 0.9999999,
    (-(4.42-5))/0.29);

function is_whole_number($value) {
    // Doing this prevents failing for values like true or "ten"
    if (!is_numeric($value)) {
        return false;
    }

    // @ghostdog74's solution fails for "10.00"
    // return (ctype_digit((string) $value));

    // Both @Maurice's solutions fails for "10.00"
    // return ((string) $value === (string) (int) $value);
    // return is_int($value);

    // @j.hull's solution always returns true for numeric values
    // return (abs($value) % 1 == 0 ? true : false);

    // @ MartyIX's solution fails for "10.00"
    // return ($value === intval($value));

    // This one fails for (-(4.42-5))/0.29
    // return (floor($value) == $value);

    // This one fails for 2
    // return ctype_digit($value);

    // I didn't understand Josh Crozier's answer

    // @joseph4tw's solution fails for (-(4.42-5))/0.29
    // return !(fmod($value, 1) != 0);

    // If you are unsure about the double negation, doing this way produces the same
    // results:
    // return (fmod($value, 1) == 0);

    // Doing this way, it always returns false 
    // return (fmod($value, 1) === 0);

    // @Anthony's solution fails for "10.00"
    // return (is_numeric($value) && is_int($value));

    // @Aistina's solution fails for 0.999999997
    // return (abs($value - round($value)) < 0.0001);

    // @Notinlist's solution fails for 0.999999997
    // return (round($value, 3) == round($value));
}

foreach ($test_cases as $test_case) {
    var_dump($test_case);
    echo ' is a whole number? ';
    echo is_whole_number($test_case) ? 'yes' : 'no';
    echo "\n";
}
_

@Aistinaや@Notinlistで提案されているような解決策は、エラーしきい値を使用して値が整数であるかどうかを判断するため、最良の解決策だと思います。それらが式_(-(4.42-5))/0.29_で期待どおりに機能したのに対し、他のすべてはそのテストケースで失敗したことに注意することが重要です。

読みやすさから、@ Notinlistのソリューションを使用することにしました。

_function is_whole_number($value) {
    return (is_numeric($value) && (round($value, 3) == round($value)));
}
_

値が整数、通貨、またはパーセンテージかどうかをテストする必要があります。2桁の精度で十分だと思うので、@ Notinlistのソリューションは私のニーズに適合します。

このテストを実行する:

_$test_cases = array(0.29, 2, 6, 2.33, 6.2, '10.00', 1.4, 10, "10", 10.5, "0x539", true,
    false, 0x53, 9.4, "ten", "100", 1, 0.999999997, 0, 0.0001, 1.0, 0.9999999,
    (-(4.42-5))/0.29);

function is_whole_number($value) {
    return (is_numeric($value) && (round($value, 3) == round($value)));
}

foreach ($test_cases as $test_case) {
    var_dump($test_case);
    echo ' is a whole number? ';
    echo is_whole_number($test_case) ? 'yes' : 'no';
    echo "\n";
}
_

次の出力を生成します。

_float(0.29)
 is a whole number? no
int(2)
 is a whole number? yes
int(6)
 is a whole number? yes
float(2.33)
 is a whole number? no
float(6.2)
 is a whole number? no
string(5) "10.00"
 is a whole number? yes
float(1.4)
 is a whole number? no
int(10)
 is a whole number? yes
string(2) "10"
 is a whole number? yes
float(10.5)
 is a whole number? no
string(5) "0x539"
 is a whole number? yes
bool(true)
 is a whole number? no
bool(false)
 is a whole number? no
int(83)
 is a whole number? yes
float(9.4)
 is a whole number? no
string(3) "ten"
 is a whole number? no
string(3) "100"
 is a whole number? yes
int(1)
 is a whole number? yes
float(0.999999997)
 is a whole number? yes
int(0)
 is a whole number? yes
float(0.0001)
 is a whole number? yes
float(1)
 is a whole number? yes
float(0.9999999)
 is a whole number? yes
float(2)
 is a whole number? yes
_
if(floor($number) == $number)

安定したアルゴリズムではありません。値が1.0の場合、数値は0.9999999になります。これにfloor()を適用すると、0になり、0.9999999に等しくありません。

たとえば3桁の精度半径を推測する必要があります

if(round($number,3) == round($number))
3
Notinlist
(string)floor($pecahformat[3])!=(string)$pecahformat[3]
2
Artron

これは、この質問にそれほど答えようとする試みではありません。彼らはすでにたくさんの答えを出している。質問が意味するように統計を行っている場合、@ antonio-vinicius-menezes-medeiの回答が最適です。しかし、入力検証にはこの答えが必要でした。このチェックは、入力文字列が整数であることを検証するために、より信頼性が高いことがわかりました。

is_numeric($number) && preg_match('/^[0-9]+$/', $number)

「is_numeric」は、preg_matchで「true」が「1」に変換されることを単に修正します。

だから@ antonio-vinicius-menezes-medeiの答えをオフにプレー。これをテストするスクリプトを以下に書きました。 ini_set('precision', 20)に注意してください。 preg_matchは引数を文字列に変換します。精度がfloat値の長さ未満に設定されている場合、それらは単に指定された精度で丸められます。 @ antonio-vinicius-menezes-medeiの回答と同様に、この精度設定は同様の推定長を強制します。

  ini_set('precision', 20);
  $test_cases = array(0.29, 2, 6, 2.33, 6.2, '10.00', 1.4, 10, "10", 10.5, "0x539", true,
    false, 0x53, 9.4, "ten", "100", 1, 0.999999997, 0, 0.0001, 1.0, 0.9999999,
    (-(4.42-5))/0.29);

  foreach ($test_cases as $number)
  {
    echo '<strong>';
    var_dump($number);
    echo '</strong>';
    echo boolFormater(is_numeric($number) && preg_match('/^[0-9]+$/', $number));
    echo '<br>';
  }

  function boolFormater($value)
  {
    if ($value)
    {
      return 'Yes';
    }
    return 'No';
  }

これはこの出力を生成します:

float(0.28999999999999998002)いいえ
int(2)はい
int(6)はい
float(2.3300000000000000711)いいえ
float(6.2000000000000001776)いいえ
string(5) "10.00"いいえ
float(1.3999999999999999999112)いいえ
int(10)はい
string(2) "10"はい
float(10.5)いいえ
string(5) "0x539"いいえ
bool(true)いいえ
bool(false)いいえ
int(83)はい
float(9.4000000000000003553)いいえ
string(3) "ten"いいえ
string(3) "100"はい
int(1)はい
float(0.99999999699999997382)いいえ
int(0)はい
float(0.00010000000000000000479)いいえ
float(1)はい
float(0.999999900000000050005264)いいえ
float(2.0000000000000004441)いいえ

1
danielson317

@Tyler Carterのソリューションの改良版であり、元のEdgeケースよりもEdgeケースを適切に処理します。

function is_whole_number($number){
    return (is_float(($f=filter_var($number,FILTER_VALIDATE_FLOAT))) && floor($f)===$f);    
}

(タイラーのコードは、文字列 "123foobar"が整数ではないことを認識できません。この改善されたバージョンでは、間違いはありません。バグを発見したコメントの@Shafizadehの功績です。また、これはphp7ですstrict_types=1互換)

1
hanshenrik
floor($entityElementCount) == $entityElementCount

これが整数の場合、これは当てはまります

1

私はこれが非常に古い投稿であることを知っていますが、これは有効な整数を返し、それをintにキャストする単純な関数です。失敗した場合はfalseを返します。

function isWholeNumber($v)
{
    if ($v !='' && is_numeric($v) && strpos($v, '.') === false) {
        return (int)$v;
    }
    return false;
}

使用法 :

$a = 43;
$b = 4.3;
$c = 'four_three';

isWholeNumber($a) // 43
isWholeNumber($b) // false
isWholeNumber($c) // false
0
spice

ローカライズされた文字列/数値と私のソリューションを共有するためだけに、このコンボは私にとって魅力のように機能しました。

public static function isWholeNumber ($input, $decimalDelimiter = ',')
{
    if (is_string($input)){
        $input = str_replace($decimalDelimiter, '.', $input);
        $input = floatval($input);
    }

    if (fmod($input,1) !== 0.0) {
        return false;
    }

    return true;
}
0
The Vojtisek
$entityElementCount = (-($highScore-$totalKeywordCount))/0.29;

Method 1-
    By using ctype_digit() function. 

    if ( ctype_digit($entityElementCount )) { 
        echo "Whole Number\n"; 
    } else { 
        echo "Not a whole Number\n"; 
    } 


Method 2-
    By using is_float() function. 

    if (is_float($entityElementCount )) { 
        echo "Not a Whole Number\n"; 
    } else { 
        echo "Whole Number\n"; 
    } 


Method 3-
    By using is_int() function. 

    if (is_int($entityElementCount )) { 
        echo "Whole Number\n"; 
    } else { 
        echo "Not a whole Number\n"; 
    } 


Method 5-
    By using fmod() function. 

    It needs 2 parameters one dividend and other is divisor
    Here $dividend=$entityElementCount and divisor=1
    if (fmod($dividend,$divisor) !== 0.0) {
        echo 'Not a whole number!';
    } else {
     echo 'A whole number!';
    }

there are some more function like intval(), floor(),... can be used to check it`enter code here`
0
sanjaya

正の整数のみの単純なソリューション。これはすべてに対して機能するわけではありません。

$string = '0x539';
$ceil = ceil($string);

if($ceil < 1){
  $ceil = FALSE; // or whatever you want i.e 0 or 1
}

echo $ceil; // 1337

必要に応じて、ceil()の代わりにfloor()を使用できます。

0
Kyle Coots
function isInteger($value)
{
    // '1' + 0 == int, '1.2' + 0 == float, '1e2' == float
    return is_numeric($value) && is_int($value + 0);
}

function isWholeNumber($value)
{
    return is_numeric($value)
        && (is_int($value + 0)
            || (intval($value + 0) === intval(ceil($value + 0))));
}

整数と10進数の両方を確認する場合は、次の操作を実行できます。

if (isInteger($foo))
{
    // integer as int or string
}
if (isWholeNumber($foo))
{
    // integer as int or string, or float/double with zero decimal part
}
else if (is_numeric($foo))
{
    // decimal number - still numeric, but not int
}

これにより、数値を丸めたり、整数にキャストしたり(10進数の場合、小数部分が失われます)、または計算を行わなくても、数値が正しくチェックされます。ただし、1.00を整数として扱いたい場合は、まったく別の話です。

0
jurchiks

単純なアプローチのように思われるのは、係数(%)を使用して、値が完全かどうかを判断することです。

x = y % 1  

yがそれ以外の整数の場合、結果はゼロ(0)ではありません。テストは次のようになります。

if (y % 1 == 0) { 
   // this is a whole number  
} else { 
   // this is not a whole number 
}

var isWhole = (y % 1 == 0? true: false);  // to get a boolean return. 

これにより、負の数が整数として表示され、その後、ABS()をyで囲むだけで、常に正の数でテストされます。

0
j.hull

私は常に型キャストを使用して、変数に整数が含まれているかどうかを確認します。これは、値の起源または型がわからない場合に便利です。

if ((string) $var === (string) (int) $var) {
    echo 'whole number';
} else {
    echo 'whatever it is, it\'s something else';
}

あなたの特定のケースでは、私は is_int() を使用します

if (is_int($var) {
    echo 'integer';
}
0
Maurice