我试图制作一个多线程程序,作为一个家具厂...例如,它需要3个钉子,2块木头和1块胶水制作1个桌子。我制作了胶水,木头和指甲类(作为Thread类的扩展)
现在,我的方式,它没有编译错误,但是当它运行时,我在thread.start()得到一个IlegalThreadState异常。这是我的主要()
public class Main
{
public static int mueble = 0;
public static void main(String[] args) throws InterruptedException
{
Semaphore smain = new Semaphore(1);
Madera m = new Madera();
Formica f = new Formica();
Clavo c = new Clavo();
boolean b = true;
while(b)
{
Random rand = new Random();
int r = (int)(rand.nextDouble()*6+0);
if(r < 1)
{
smain.acquire();
f.start();
}
else if ((r>1)&&(r<3))
{
smain.acquire();
m.start();
}
else
{
smain.acquire();
c.start();
}
if (mueble == 30)
{
b = false;
}
smain.release();
}
}
}
不要介意西班牙语。
我认为问题可能出在每个线程的run()部分,这里是(这三个类几乎相同)
@Override
public void run()
{
try {
sclavo.acquire();
System.out.println("Llega 1 clavo");
System.out.println("Hay " + (3-sclavo.availablePermits()) + " clavo(s)");
if((sclavo.availablePermits()==0)&&(Madera.smadera.availablePermits()==0)&&(Formica.sformica.availablePermits()==0))
{
System.out.println("Se ha creado 1 mueble");
Main.mueble++;
System.out.println("Hay" + Main.mueble + "mueble(s)");
Formica.sformica.release(1);
sclavo.release(3);
Madera.smadera.release(2);
}
} catch (InterruptedException ex) {
Logger.getLogger(Clavo.class.getName()).log(Level.SEVERE, null, ex);
}
}
任何帮助都会很棒!
答案 0 :(得分:2)
您无法重新启动线程。查看Thread.start
的文档。它说:
多次启动线程永远不合法。
你在循环中一遍又一遍地开始相同的线程。相反,您应该查看ExecutorService
如何工作并使用它。一个好的多线程系统是基于工作的,每个工作都是Runnable
或Callable
。当你只想运行某个任务时它使用Runnable
并且它没有任何输出(具体来说,如果作业基本上返回void
)。当您的作业 返回某些内容时,您可以使用Callable
。在SO和其他地方有很多关于如何使用ExecutorService
和相关类的例子。
如果你别无选择,只能手动使用线程,那么你需要在每个循环上创建并启动一个新线程,例如:
new Formica().start();
与反复启动相同的Formica
实例相反。