Когда вы вызываете Java thread.run()
вместо thread.start()
?
Когда вы вызываете java thread.run() вместо thread.start()?
Ответ 1
Возможно, вы захотите вызвать run() в конкретном unit test, который строго связан с функциональностью, а не с concurrency.
Ответ 2
Никогда. Вызов run() напрямую просто выполняет код синхронно (в том же потоке), как и обычный вызов метода.
Ответ 3
Взято из Часто задаваемые вопросы по темам Java в стиле кода:
В: Какая разница между методы запуска begin() и run()?
A: Отдельные методы start() и run() в классе Thread предоставляют два способа создания многопоточных программ. Метод start() запускает выполнение нового потока и вызовов метод run(). Метод start() возвращает сразу, а новый поток обычно продолжается до запуска() возвращает метод.
Метод run() класса Thread ничего не делает, поэтому подклассы должны переопределить метод с кодом выполнить во втором потоке. Если Тема создается с помощью Runnable аргумент, метод run() потока выполняет метод run() Runnable object в новом потоке вместо этого.
В зависимости от характера вашей потоковой программы, вызывающей поток run() напрямую может дать тот же вывод, что и вызов через start() метод, но в последнем случае код фактически выполняется в новом нить.
Ответ 4
Выполнение thread.run()
не создает новый Thread
, в котором ваш код запускается. Он просто выполняет код в текущем потоке, из которого вызывается код thread.run()
.
Выполнение thread.start()
создает новый поток уровня ОС, в котором вызывается метод run()
.
По существу:
Одиночное программирование с резьбой → Прямо вызов метода
run()
Многопоточное программирование → Вызов метода
start()
Кроме того, как отмечали другие, "тестирование", по-видимому, является единственным целесообразным случаем, когда вы можете ссылаться на run()
непосредственно из вашего кода.
Ответ 5
Об этом уже упоминалось, но просто для того, чтобы быть ясным: создание нового объекта Thread только для вызова метода run() бесполезно дорого и должно быть основным красным флагом. Было бы намного лучше, более развязанный дизайн создать Runnable impl и либо (a) вызвать его метод run() напрямую, если это желаемое поведение, либо (b) построить новый поток с этим Runnable и запустить Thread.
Еще лучше, для еще большей развязки, проверьте интерфейс и структуру Executor
в JDK 5 и новее. Это позволяет вкратце отделить выполнение задачи (экземпляр Runnable) от того, как он выполняется (реализация Executor, которая может выполнять Runnable в текущем потоке в новом потоке, используя существующий поток из пула, и еще что-то).
Ответ 6
Вызвать thread.start()
, он в свою очередь вызовет thread.run()
. Не могу придумать случай, когда вы хотите обойти thread.start()
и перейти непосредственно к thread.run()
Ответ 7
Отдельные методы start()
и run()
в классе Thread предоставляют два способа создания потоков программ. Метод start()
запускает выполнение нового потока и вызывает метод run()
. Метод start()
возвращается немедленно, и новый поток обычно продолжается до тех пор, пока метод run()
не вернется.
Метод Thread run()
ничего не делает, поэтому подкласс должен переопределить метод с кодом для выполнения во втором потоке. Если поток создается с помощью аргумента Runnable, поток run()
метод выполняет run()
метод объекта Runnable в новом потоке.
В зависимости от характера вашей потоковой программы вызов метода Thread run()
напрямую может дать тот же вывод, что и вызов через метод start()
, но в последнем случае код фактически выполняется в новом потоке.
Ответ 8
Если возник вопрос - "почему метод запуска потока вызывается вместо прямого метода запуска", то я ответил на приведенный ниже пример кода. Надеюсь, что это прояснится. В следующем примере:
/*
By calling t1.start(),
we are getting the main calling thread returned immediately
after the t1.start() called and is ready to proceed for other
operations.And the thread t1 starts executing the run method of the object r.
Hence the the output will be:
I am the main thread , i created thread t1 and had it execute run method, which is currently looping from 0 to 1000000
I am done executing run method of testThread
*/
/* If we call t1.run() instead of t1.start(), (just replace t1.start() with t1.run() in the code for testing)
its like a regular method call and the main thread will not return until the run method completes,
hence the output will be:
I am done executing run method of testThread
I am the main thread , i created thread t1 and had it execute run method, which is currently looping for i to 1000000
*/
class testThread implements Runnable{
public void run()
{
for(int i=0;i<1000000;i++){} //a simple delay block to clarify.
System.out.println("I am done executing run method of testThread");
}
}
public class mainClass{
public static void main(String [] args)
{
testThread r = new testThread();
Thread t1 = new Thread(r);
t1.start(); /* Question is: can we call instead t1.run() */
System.out.println("I am the main thread , i created thread t1 and had it execute run method, which is currently looping for i to 1000000");
}
}
Ответ 9
Если вы хотите, чтобы он выполнялся синхронно. Вызов метода run фактически не даст вам многопоточности. Метод start создает новый поток, который вызывает метод run.
Ответ 10
Если вы хотите выполнить содержимое run(), как и любой другой метод. Конечно, не запускать нить.
Ответ 11
Предполагая, что вы знаете использование метода запуска и запуска, то есть синхронное и асинхронное; метод run можно использовать только для проверки функциональности.
Плюс в некоторых случаях один и тот же класс потоков может использоваться в двух разных местах с требованиями к синхронизации и асинхронному использованию, имея два разных объекта с одним методом запуска и другим запущенным методом.
Ответ 12
По крайней мере, в JVM 1.6., бит проверки и запуска называется изначально:
public synchronized void start() {
/**
* This method is not invoked for the main method thread or "system"
* group threads created/set up by the VM. Any new functionality added
* to this method in the future may have to also be added to the VM.
*
* A zero status value corresponds to state "NEW".
*/
if (threadStatus != 0)
throw new IllegalThreadStateException();
group.add(this);
start0();
if (stopBeforeStart) {
stop0(throwableFromStop);
}
}
private native void start0();
Ответ 13
Просто примечание к замечательным замечаниям: иногда вы пишете многопоточный код, который использует метод "start" для запуска разных потоков. Вы найдете это намного проще, если вы используете "run" (вместо "start" ) для отладки, поскольку он заставляет код работать синхронно и отлаживать его намного проще.
Ответ 14
public class TestClass implements Runnable {
public static void main(String[] args) {
TestClass tc = new TestClass();
Thread t1 = new Thread(tc);
System.out.println("Before Starting Thread " + Thread.currentThread().hashCode());
t1.start();
System.out.println("After Starting Thread " + Thread.currentThread().hashCode());
}
@Override
public void run() {
System.out.println("TestClass Run method is Running with thread " + Thread.currentThread().hashCode());
}
}