当前位置: 首页 > 面试题库 >

如何使外部方法可中断?

章绪
2023-03-14
问题内容

问题

我正在通过ExecutorService运行某些外部方法的多次调用。我希望能够中断这些方法,但是不幸的是,它们不能自行检查中断标志。有什么办法可以强制从这些方法引发异常?

我知道从任意位置抛出异常是潜在的危险,在我的具体情况下,我愿意抓住这次机会并准备处理后果。

细节

“外部方法”是指某些来自外部库的方法,并且我无法修改其代码(可以,但是,每当发布新版本时,这都会成为维护的噩梦)。

外部方法计算量大,不受IO限制,因此它们不响应常规中断,因此无法强制关闭通道或套接字等。如前所述,它们也不检查中断标志。

代码在概念上类似于:

// my code
public void myMethod() {
    Object o = externalMethod(x);
}

// External code
public class ExternalLibrary {
    public Object externalMethod(Object) {
        innerMethod1();
        innerMethod1();
        innerMethod1();
    }

    private void innerMethod1() {
        innerMethod2();
        // computationally intensive operations
    }

    private void innerMethod2() {
        // computationally intensive operations
    }
}

我尝试过的

Thread.stop()理论上将执行我想要的操作,但不仅不赞成使用它,而且还仅适用于实际线程,而我正在使用执行程序任务(例如,在线程池中工作时,它们也可能与将来的任务共享线程)
。不过,如果找不到更好的解决方案,我将把代码转换为使用老式线程,然后使用此方法。

我尝试过的另一种选择是myMethod()使用特殊的“
Interruptable”注释标记和类似的方法,然后使用AspectJ(我承认是新手)来捕获那里的所有方法调用-类似于:

@Before("call(* *.*(..)) && withincode(@Interruptable * *.*(..))")
public void checkInterrupt(JoinPoint thisJoinPoint) {
    if (Thread.interrupted()) throw new ForcefulInterruption();
}

但是withincode它并不递归到匹配方法所调用的方法,因此我将不得不将此注释编辑到外部代码中。


问题答案:

我已经解决了我的问题的丑陋解决方案。它不是很漂亮,但是可以在我的情况下使用,因此我将其发布在这里,以防它对其他人有帮助。

我所做的是 分析
应用程序的库部分,希望我可以隔离一小部分被重复调用的方法,例如某些get方法equals()或类似的东西;然后我可以在其中插入以下代码段:

if (Thread.interrupted()) {
    // Not really necessary, but could help if the library does check it itself in some other place:
    Thread.currentThread().interrupt();
    // Wrapping the checked InterruptedException because the signature doesn't declare it:
    throw new RuntimeException(new InterruptedException());
}

通过编辑库的代码手动插入它,或者通过编写适当的方面自动插入它。请注意,如果库尝试捕获并吞下一个RuntimeException,则抛出的异常可以替换为库未尝试捕获的其他内容。

幸运的是,使用的VisualVM,我能找到一个 单一
的具体用法我正在图书馆的过程中调用了非常高数十倍方法。添加以上代码段后,它现在可以正确响应中断。

这当然是不可维护的,再加上什么也不能保证库在其他情况下会重复调用此方法。但这对我有用,并且由于配置其他应用程序并在其中插入检查相对容易,因此我认为这是一个通用的解决方案,尽管很难看。



 类似资料:
  • 我想抑制特定异常的堆栈跟踪:org。每件事。json。模式。验证异常。 这个特殊的异常在我们的应用程序中引发了很多,我想限制性能的影响。 我试着用我自己的扩展: 但是当我抓住了抑制验证时,验证异常就消失了。有没有办法实现我想做的?

  • 问题内容: 我有一个非常简单的Java类,它使用输入验证以及明显的void set()和String get()方法来有效地装饰Map。 我希望能够有效地调用这些方法并从JVM外部处理返回值和异常,但仍在同一台计算机上 更新:我想到的调用者不是另一个JVM; 谢谢@戴夫雷 我的实施注意事项很典型 性能 易于实施和维护(简单吗?) 可靠性 灵活性(例如,我可以从远程计算机上拨打电话等) 有“正确的方

  • 问题内容: 我希望打破PHP中的外部for / foreach循环。 可以在ActionScript中完成,如下所示: PHP等效项是什么? 问题答案: 对于2个嵌套循环: http://php.net/manual/en/control- structures.break.php

  • 首先,我是新来的Java,Groovy和Jenkins,所以请对我有耐心;) 我正在准备一个带有管道支持的Jenkins服务器,以备将来在构建环境中使用。我们使用一种特殊的内部脚本语言,为此我必须用java编写一个包装器。只有在Groovy中才能完成这项工作,我们必须使用这种特殊的语言。 我尝试过很多方法将java库引用到这个jenkins项目中,但都没有成功。我主要是在https://githu

  • 本文向大家介绍如何在C#中使用linq扩展方法执行左外部联接?,包括了如何在C#中使用linq扩展方法执行左外部联接?的使用技巧和注意事项,需要的朋友参考一下 使用INNER JOIN 时,结果集中仅包含匹配的元素。不匹配的元素将从结果集中排除。 使用LEFT OUTER JOIN时 ,左集合中的所有匹配元素+所有非匹配元素都包含在结果集中。 让我们通过一个示例了解实现左外部联接。考虑以下部门和雇

  • 问题内容: 我有一个具有称为的私有方法的类。我想从外面打电话。我认为应该可以反思,但是我得到了。有任何想法吗??? 问题答案: 利用使用其之前的Method对象的方法。