47

在 PHP 中,我有时会使用 try/catch 捕获一些异常:

try {
    ...
} catch (Exception $e) {
    // Nothing, this is normal
}

使用这种代码,我最终得到了一个无用创建的变量$e(大量资源),而 PHP_MD(PHP Mess Detector)由于未使用的变量而创建了一个警告。

4

7 回答 7

21

从 PHP 8 开始,可以使用非捕获捕获。

这是相关的 RFC,以 48-1 的赞成票投票。

现在可以执行以下操作:

try {
    readFile($file);
} catch (FileDoesNotExist) {
    echo "File does not exist";
} catch (UnauthorizedAccess) {
    echo "User does not have the appropriate permissions to access the file";
    log("User attempted to access $file");
}

这样,对于一些异常细节不相关且异常类型已经提供所有必要上下文的边缘情况,可以在不创建新变量的情况下捕获异常。

于 2020-05-14T16:16:24.673 回答
17

您可以使用 PHP 8 @see

PHP 5,7

不,但您可以取消设置。

try {
    ...
} catch (Exception $e) {
    // Nothing, this is normal
    unset($e);
}

如果是 PHPMD 导致了这个问题,那么您可以取消警告。

PHPMD 抑制警告

class Bar {
    /**
     * This will suppress UnusedLocalVariable
     * warnings in this method
     *
     * @SuppressWarnings(PHPMD.UnusedLocalVariable)
     */
    public function foo() {

        try {
            ...
        } catch (Exception $e) {
            // Nothing, this is normal
            unset($e);
        }
    }
}

我假设您只是捕获异常,因为您不需要,因为您愿意。在 PHP 5,7 中,catch如果要使用try,则必须使用 a,如果使用 a catch,则必须声明变量。

于 2015-02-06T12:25:35.280 回答
8

这就是异常的全部意义——您可以有多个不同的 catch 块来捕获您想要处理的任何异常。异常的数据必须分配到某个地方,因此是变量。unset($e)如果您真的不想看到这些警告,则可以在 catch 块内执行类似操作...或禁用警告(通常是个坏主意)。

于 2011-01-27T18:21:57.043 回答
7

不。

在任何情况下,捕获异常而什么都不做通常是个坏主意。异常的存在正是为了迫使您处理异常情况(否则执行将中止),因此可以理解该语言不利于这种用例。

于 2011-01-27T18:22:53.560 回答
7

我从根本上不同意 Marc B 和 Artefacto 的回答。在某些情况下,忽略捕获是更好的选择,甚至是唯一的选择。特别是在使用外部库(您无法控制抛出哪些异常)和/或异步操作时。

例如:

我只想在文件不存在的情况下创建一个文件。我正在使用外部 I/O 库。想象一下它有File::exists($fileName)File::create($fileName)方法。

选项 1(如果可以省略捕获):

try {
    File::create($fileName);
}
// Go on with the rest of the code.

选项 2(没有 try/catch):

if (!File::exists($fileName))
    File::create($fileName);

在这里,选项 1 完全有效,因为选项 2 有两个重要问题:

  1. 如果多个线程同时运行并通过此代码段,则可能是线程 A 首先检查文件是否存在。接下来,线程 B 检查文件是否存在。他们都发现它不存在。线程 A 创建文件。线程 B 然后尝试再次创建它并抛出异常,即使您正在使用 if 检查。
  2. 库本身很可能已经执行了!File::exists($fileName)检查。因此,您正在浪费一个已经拨打的电话。

请注意,如果File::create抛出其他可能出乎意料的异常,最好抓住这些异常。

结论

说某事从来都不是一个好主意,几乎从来都不是一个好主意。规则总是有例外(呵呵)。与任何约定或设计模式一样,它只是一个经验法则,旨在帮助经验不足的开发人员做出正确的决定。

于 2018-12-25T11:39:24.773 回答
0

PHP 8.0开始,它可以不带变量地键入,但Exception现在每个的一般情况是Throwable. 类Exception实现Throwable

try {
    ...
} catch (CustomException) {
    // CustomException
} catch (Throwable) {
    //All other classes implementing Throwable interface
}
于 2020-10-01T17:36:35.760 回答
-4

例外不仅用于特殊情况。

此方案实际上使用异常来确保用户已注销。在脚本的这一点上,找出应该修剪哪些数据是非常耗费资源的,因此实际上只修剪所有数据并捕获异常会更快。

        try {
        GDS::$DB->exec('DELETE FROM sessions WHERE session_id = ' . session_id());
        GDS::$DB->exec('DELETE FROM sessions WHERE user_id = ' . $this->data['user_id']);
    } catch(PDOException $ex) {}
    session_regenerate_id(true);
    setcookie('bis_[user_id]', 0, time() - 1, null, null, false, true);
    setcookie('bis_[session_start]', 0, time() - 1, null, null, false, true);
    setcookie('bis_[session_time]', 0, time() - 1, null, null, false, true);
于 2013-05-13T17:26:08.787 回答