validate parseerror error php exception divide-by-zero

parseerror - PHP, ¿cómo atrapar una división por cero?



php parseerror (12)

Aquí hay otra solución:

<?php function e($errno, $errstr, $errfile, $errline) { print "caught!/n"; } set_error_handler(''e''); eval(''echo 1/0;'');

Ver set_error_handler()

Tengo una gran expresión matemática que debe crearse dinámicamente. Por ejemplo, una vez que haya analizado "algo" el resultado será una cadena como: "$foo+$bar/$baz"; .

Entonces, para calcular el resultado de esa expresión, estoy usando la función eval ... algo como esto:

eval("/$result = $expresion;"); echo "The result is: $result";

El problema aquí es que a veces recibo errores que dicen que hubo una división por cero, y no sé cómo atrapar esa excepción. He intentado cosas como:

eval("try{/$result = $expresion;}catch(Exception /$e){/$result = 0;}"); echo "The result is: $result";

O:

try{ eval("/$result = $expresion;"); } catch(Exception $e){ $result = 0; } echo "The result is: $result";

Pero no funciona. Entonces, ¿cómo puedo evitar que mi aplicación falle cuando hay una división por cero?

Editar:

Primero, quiero aclarar algo: la expresión está construida dinámicamente, por lo que no puedo simplemente evaluar si el denominador es cero. Entonces ... con respecto al comentario de Mark Baker, permítanme darles un ejemplo. Mi analizador podría construir algo como esto:

"$foo + $bar * ( $baz / ( $foz - $bak ) )"

El analizador construye la cadena paso a paso sin preocuparse por el valor de los vars ... así que en este caso si $foz == $bak de hecho hay una división por cero: $baz / ( 0 ) .

Por otro lado, como sugirió Pete, probé:

<?php $a = 5; $b = 0; if(@eval(" try{ /$res = $a/$b; } catch(Exception /$e){}") === FALSE) $res = 0; echo "$res/n"; ?>

Pero no imprime nada.


Como han mencionado otros, considere probar una solución que le permita verificar si el denominador es 0.

Dado que ese consejo parece inútil para su propósito, aquí hay un poco de información sobre el manejo de errores de PHP.

Las primeras versiones de PHP no tenían excepciones. En cambio, se generaron mensajes de error de varios niveles (avisos, advertencias, etc.). Un error fatal detiene la ejecución.

PHP5 trajo excepciones a la tabla, y las nuevas librerías proporcionadas por PHP arrojarán excepciones cuando ocurran cosas malas / inesperadas. Sin embargo, el código base del núcleo NO fue reescrito para usar la excepción. Las funciones principales y las operaciones aún se basan en el antiguo sistema de error.

Cuando divides por 0, obtienes una Advertencia, no una excepción

PHP Warning: Division by zero in /foo/baz/bar/test.php(2) : eval()''d code on line 1 PHP Stack trace: PHP 1. {main}() /foo/baz/bar/test.php:0 PHP 2. eval() /foo/baz/bar/test.php:2

Si desea "atraparlos", deberá establecer un controlador de error personalizado que detectará errores de división por cero y hará algo al respecto. Desafortunadamente, los manejadores de errores personalizados son una trampa, lo que significa que también necesitará escribir algún código para hacer algo apropiado con todos los demás errores.


En PHP7 puedes usar DivisionByZeroError

try { echo 1/0; } catch(DivisionByZeroError $e){ echo "got $e"; }


Estaba enfrentando ese problema también (expresiones dinámicas). Idid de esa manera, que podría no ser la mejor manera, pero funciona. En lugar de arrojar una Excepción, por supuesto puede devolver nulo o falso o lo que sea que desee. Espero que esto ayude.

function eval_expression($expression) { ob_start(); eval(''echo ('' . $expression . '');''); $result = ob_get_contents(); ob_end_clean(); if (strpos($result, ''Warning: Division by zero'')!==false) { throw new Exception(''Division by zero''); } else return (float)$result; }


Problema:

b=1; c=0; a=b/c; // Error Divide by zero

Solución simple:

if(c!=0) a=b/c; else // error handling



Solo necesita configurar un manejador de errores para lanzar una excepción en caso de errores:

set_error_handler(function () { throw new Exception(''Ach!''); }); try { $result = 4 / 0; } catch( Exception $e ){ echo "Divide by zero, I don''t fear you!".PHP_EOL; $result = 0; } restore_error_handler();


También he estado luchando con esto, las soluciones set_error_handler no me funcionaban, probablemente basadas en las diferencias de versión de PHP.

La solución para mí fue intentar detectar un error al apagarlo:

// Since set_error_handler doesn''t catch Fatal errors, we do this function shutdown() { $lastError = error_get_last(); if (!empty($lastError)) { $GLOBALS[''logger'']->debug(null, $lastError); } } register_shutdown_function(''shutdown'');

No estoy seguro de por qué se cierra una división por 0 en lugar de ser manejado por el set_error_handler pero esto me ayudó a ir más allá y morir en silencio.


Una cadena que contiene números y los operadores matemáticos + - * / se pasa como entrada. El programa debe evaluar el valor de la expresión (según BODMAS) e imprimir la salida.

Ejemplo de entrada / salida: si el argumento es "7 + 4 * 5", la salida debe ser 27. Si el argumento es "55 + 21 * 11 - 6/0", la salida debe ser "error" (como la división por cero es no definida).


Use un @ (un operador de control de errores ). Esto le dice a php que no emita advertencias en caso de errores.

eval("/$result = @($expresion);"); if ($result == 0) { // do division by zero handling } else { // it''s all good }


if ($baz == 0.0) { echo ''Divisor is 0''; } else { ... }

En lugar de usar eval, que es muy peligroso si está utilizando la entrada de usuario dentro de la expresión evaluada, ¿por qué no usar un analizador apropiado como evalmath en PHPClasses y que genera una excepción limpia en dividir por cero?


if(@eval("/$result = $expresion;")===FALSE){ $result=0; }

Sin embargo, no solo se dividirán por 0 errores.