java 如何在java中重新启动线程?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/468266/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to restart thread in java?
提问by raja
I have created a program which searches for files in a source folder. If it finds any file, it processes that file and moves it to a destination folder, then looks for a new file in the source folder. It has to keep on checking the source folder for a file.
我创建了一个程序,用于在源文件夹中搜索文件。如果找到任何文件,它会处理该文件并将其移动到目标文件夹,然后在源文件夹中查找新文件。它必须不断检查文件的源文件夹。
I have used a thread to look for files in the source folder. The problem I am facing is whenever any exception is thrown during file processing, the thread gets stopped. I want the thread to be running even if an exception is thrown. It has to move the file that caused the error to some other folder and look for a new file in the source folder. How can I make the thread keep on running?
我使用了一个线程来查找源文件夹中的文件。我面临的问题是,只要在文件处理过程中抛出任何异常,线程就会停止。即使抛出异常,我也希望线程正在运行。它必须将导致错误的文件移动到其他文件夹并在源文件夹中查找新文件。如何让线程继续运行?
Eg:
例如:
public void run() {
try {
searchfile();
}
catch(Exception e) {
e.printStackTrace();
}
}
public void searchfile(){
...
}
Update:
更新:
I should be more clear in my question. Actually there are 4 source folders and 4 destination folders. I have to perform the same operation in each source & destination pair. So i have created 4 threads in one class and do the operation in separate class.
我的问题应该更清楚。实际上有 4 个源文件夹和 4 个目标文件夹。我必须在每个源和目标对中执行相同的操作。所以我在一个类中创建了 4 个线程,并在单独的类中执行操作。
class MainClass
{
public static void main(String[] args){
for(int i=0;i<4;i++){
SearchClass search = new SearchClass();
Thread thread = new Thread(search);
thread.start();
}
}
}
class SearchClass
{
public void run() {
try {
searchfile();
} catch(Exception e) {
e.printStackTrace();
}
}
public void searchfile(){ ... } }
All the thread wont stop running eventhough it caught any exception in middle. How can i do that?
即使在中间捕获任何异常,所有线程也不会停止运行。我怎样才能做到这一点?
回答by Jon Skeet
If a thread is dying due to an uncaught exception, the answer is simple: catch the exception at an appropriate place so that you can keep going. Either catch the exception within your searchfile method, or make the run method call searchfile in a loop.
如果线程由于未捕获的异常而死亡,答案很简单:在适当的位置捕获异常,以便您可以继续运行。要么在 searchfile 方法中捕获异常,要么让 run 方法在循环中调用 searchfile。
回答by Peter Lawrey
If you want your thread to keep running use a loop.
如果您希望您的线程继续运行,请使用循环。
public void run() {
while(!Thread.interrupted())
try {
searchfile();
}
catch(Exception e) {
e.printStackTrace();
}
}
回答by John
I'm not entirely sure if this will work, yet here's a try.
我不完全确定这是否有效,但可以尝试一下。
public void run() {
try {
searchFile();
} catch(Exeption e) {
e.printStackTrace();
if(!Thread.currentThread().isAlive())
Thread.currentThread().start();
}
}
回答by Bashar Kokash
Inside your catch, you can move the file to the error folder then create a new object of the same thread and start it again.
在您的捕获中,您可以将文件移动到错误文件夹,然后创建同一线程的新对象并再次启动它。
回答by Rahel Lüthy
unless i got you wrong, your code is missing the "keep running" nature, i.e. you need to have a loop somewhere:
除非我弄错了,否则您的代码缺少“继续运行”的性质,即您需要在某处有一个循环:
public static void main(String[] args){
ExecutorService service = Executors.newFixedThreadPool(4);
// for each of your 4 folders
while (true) {
Future<File> searchResult = service.submit(new SearchTask());
try {
File foundFile = searchResult.get();
// handle found file
} catch (Exception e) {
// handle exception
}
}
}
private static class SearchTask implements Callable<File> {
@Override
public File call() {
return searchFile();
}
public File searchFile() {
// search & return found file
}
}
note that this is just a very simple extension of your example. it is still missing the parametrization of the SearchTask to actually be specific for a folder, handling of files & exceptions, etc. as mentioned in previous answers, your SearchTask should implement Runnable (i prefer Callable...), and IMHO it's always better to use an ExecutorService than to spawn threads manually. hope this helps...
请注意,这只是您示例的一个非常简单的扩展。它仍然缺少 SearchTask 的参数化以实际特定于文件夹、文件和异常的处理等。如前面的答案所述,您的 SearchTask 应该实现 Runnable(我更喜欢 Callable...),恕我直言,它总是更好使用 ExecutorService 而不是手动生成线程。希望这可以帮助...
回答by Rahel Lüthy
you said that the exception may be thrown during file process , so i put the processFile()in a try-catch block. but if it may be thrown during search, you may put it in a try-catch too.
你说在文件处理过程中可能会抛出异常,所以我把它processFile()放在一个 try-catch 块中。但是如果它可能在搜索过程中被抛出,你也可以把它放在一个 try-catch 中。
public void run() {
while(!terminated) {
findNextFile();
try {
processFile();
} catch {
// handle error
}
}
}
回答by yurko
You can easily go with a workaround. Just run the needed logic for some amount of times and finish the job based on some criteria.
您可以轻松地使用解决方法。只需运行所需的逻辑一段时间,然后根据某些标准完成工作。
public class ThreadRestartWorkaround extends Thread {
public static void main(String[] args) {
ThreadRestartWorkaround th = new ThreadRestartWorkaround(5);
th.start();
}
private int maxCycles;
private int currentCycle;
public ThreadRestartWorkaround(int maxCycles) {
this.maxCycles = maxCycles;
}
@Override
public void run() {
while(executeSomeLogicUntilReachingTheLimit());
System.out.println("Finished due to exceeding the maxCycles config");
}
private boolean executeSomeLogicUntilReachingTheLimit() {
currentCycle++;
System.out.println("Executing logic for " + currentCycle + " time");
return currentCycle < maxCycles;
}
}
And the output is
输出是
Executing logic for 1 time
Executing logic for 2 time
Executing logic for 3 time
Executing logic for 4 time
Executing logic for 5 time
Finished due to exceeding the maxCycles config
回答by Eddie
Here are my assumptions based on your question and your clarification:
以下是我根据您的问题和您的澄清做出的假设:
- Each thread, in the
run()method, only callssearchfile()once and not in a loop - your
searchfile()method has a loop in it and you want that loopto continue running even if an exception is thrown in it. - you have some way of initializing each thread that you aren't showing us (and that isn't terribly important for this specific quiestion)
searchfile()does not declare that it throws anyException- You aren't using a logging framework, but are instead using
System.out(although using a logging framework is a Really Good Idea - Java 5 is OK (otherwise you'll have to use a different
for()loop below
- 每个线程,在
run()方法中,只调用searchfile()一次而不是在循环中 - 您的
searchfile()方法中有一个循环,并且即使在其中抛出异常,您也希望该循环继续运行。 - 您有某种方法可以初始化您没有向我们展示的每个线程(这对于这个特定的问题并不是非常重要)
searchfile()不声明它抛出任何Exception- 您没有使用日志记录框架,而是使用
System.out(尽管使用日志记录框架是一个非常好的主意 - Java 5 没问题(否则你必须在
for()下面使用不同的循环
With these assumptions, you don't want to plan to catch an Exceptionin your run()method except for the purpose of logging that something went very wrong:
有了这些假设,您不想计划Exception在您的run()方法中捕获一个,除非是为了记录出现非常错误的情况:
public void run() {
try {
searchfile();
} catch (RuntimeException e) {
System.out.println("Something went very wrong! Unexpected RuntimeException");
e.printStackTrace();
}
}
Note that the code catches RuntimeException. Always catch the most specific Exceptionthat will do what you need. Then what you need is something such as the following in your searchfile()method:
请注意,代码捕获RuntimeException. 始终捕捉最具体的内容Exception,可以满足您的需求。那么你需要的是你的searchfile()方法中的以下内容:
File[] files = directory.listFiles();
for (File file : files) {
try {
// Do your normal file/directory processing here
} catch (Exception e) {
System.out.println("Exception processing file " + file.getName() + " " + e);
// Move "file" to another area
}
}
Since you are trapping unexpected Exceptions in the main loop of your Thread, your thread will continue processing after handling the Exception.
由于您Exception在主循环中捕获了意外的s Thread,您的线程将在处理Exception.

