在网上看到了个帖子如题:有三个线程ID分别是A、B、C,请有多线编程实现,在屏幕上循环打印10次ABCABC…
自己想尝试下,可才尝试到下面就不知道错在哪里了
请高手帮忙public class ThreeThread implements Runnable {
Print print = new Print();
public void run() {
for(int i=0;i<10;i++){
//调用打印方法
print.print(Thread.currentThread().getName());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
public static void main(String[] args) {
ThreeThread test = new ThreeThread();
//创建3个线程对象
Thread a = new Thread(test, "a");
Thread b = new Thread(test, "b");
Thread c = new Thread(test, "c");
a.start();
System.out.println(a.getState());
b.start();
System.out.println(a.getState());
a.notify();
}
}class Print {
public void print(String name) {
System.out.println(name);
}}按我的想法是 想先尝试下通过{a.notify(); } 把进入sleep了的 a唤醒,
观察得到 a的状态为 TIMED_WAITING 难道这个状态不可以调用 notify方法???
控制台输出如下代码a
RUNNABLE
TIMED_WAITING
b
Exception in thread "main" java.lang.IllegalMonitorStateException
at java.lang.Object.notify(Native Method)
at cn.com.Thread.ThreeThread.main(ThreeThread.java:36)
a
b
a
b
a
b请大家帮我看下,或则留下解题思路了 小弟在此谢过。。
自己想尝试下,可才尝试到下面就不知道错在哪里了
请高手帮忙public class ThreeThread implements Runnable {
Print print = new Print();
public void run() {
for(int i=0;i<10;i++){
//调用打印方法
print.print(Thread.currentThread().getName());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
public static void main(String[] args) {
ThreeThread test = new ThreeThread();
//创建3个线程对象
Thread a = new Thread(test, "a");
Thread b = new Thread(test, "b");
Thread c = new Thread(test, "c");
a.start();
System.out.println(a.getState());
b.start();
System.out.println(a.getState());
a.notify();
}
}class Print {
public void print(String name) {
System.out.println(name);
}}按我的想法是 想先尝试下通过{a.notify(); } 把进入sleep了的 a唤醒,
观察得到 a的状态为 TIMED_WAITING 难道这个状态不可以调用 notify方法???
控制台输出如下代码a
RUNNABLE
TIMED_WAITING
b
Exception in thread "main" java.lang.IllegalMonitorStateException
at java.lang.Object.notify(Native Method)
at cn.com.Thread.ThreeThread.main(ThreeThread.java:36)
a
b
a
b
a
b请大家帮我看下,或则留下解题思路了 小弟在此谢过。。
Print print = new Print(); Object locka = new Object();
Object lockb = new Object();
Object lockc = new Object(); private Hashtable<String, Object> map = new Hashtable<String, Object>(); public ThreeThread() {
map.put("a", locka);
map.put("b", lockb);
map.put("c", lockc);
} public void run() {
for (int i = 0; i < 10; i++) {
String threadName = Thread.currentThread().getName();
print.print(threadName); Object nextLock = getNextThreadLock(threadName);
synchronized (nextLock) {
nextLock.notify();
} try {
Object myLock = map.get(threadName);
synchronized (myLock) {
myLock.wait();
}
} catch (InterruptedException e1) {
e1.printStackTrace();
} try {
Thread.sleep(1000); } catch (InterruptedException e) {
e.printStackTrace();
}
}
} private Object getNextThreadLock(String threadName) {
if (threadName.equals("a")) {
return lockb;
} else if (threadName.equals("b")) {
return lockc;
} else if (threadName.equals("c")) {
return locka;
}
return null; // It's impossible.
} public static void main(String[] args) {
ThreeThread test = new ThreeThread();
Thread a = new Thread(test, "a");
Thread b = new Thread(test, "b");
Thread c = new Thread(test, "c"); a.start(); b.start();
c.start(); }
}class Print {
public void print(String name) {
System.out.println(name);
}
}附:如果楼主吃透这个小例子,那么Thread基本就过关了。
另外,你这个a.nitify();根本就不可能把a唤醒。 a.notify() 只能唤醒哪些正在等待a的线程...(说得不太清楚,楼主还是看代码吧。)
private String str;
public ThreadPrint(String str) {
this.str = str;
} public void run() {
System.out.println(str);
}
}public class Test {
public static void main(String[] args) throws InterruptedException {
while (true) {
Thread a = new Thread(new ThreadPrint("a"));
a.start();
a.join();
Thread b = new Thread(new ThreadPrint("b"));
b.start();
b.join();
Thread c = new Thread(new ThreadPrint("c"));
c.start();
Thread.sleep(1000);
}
}
}
a
c
b
a
c
b
a
b
c
a
b
c
a
b
c
a
b
c
public class Test2 {
public static void main(String[] args) {
Myt myt1 = new Myt("A",0);
Myt myt2 = new Myt("B",1);
Myt myt3 = new Myt("C",2);
myt1.start();
myt2.start();
myt3.start();
}
}class Myt extends Thread {
private static Object obj = new Object(); private static int cnt=0;
private int code; public Myt(String threadName,int code) {
super( threadName);
this.code=code;
} @Override
public void run() {
while (true) {
try {
synchronized (obj) {
Thread.sleep(100);
if(cnt%3==this.code){
System.out.println(this.currentThread().getName());
cnt++;
obj.notifyAll();
} else{
obj.wait();
}
if(cnt>29){
break;
}
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
public class Exec{
static Object obj = new Object();
public static void main(String[] args){
CharThread ct = new CharThread();
NumberThread nt = new NumberThread(ct);
nt.start();
}
}
class NumberThread extends Thread{
CharThread t;
public NumberThread(CharThread ct){
t = ct;
}
public void run(){
synchronized(Exec.obj){
t.start();
for(int i = 1;i<=26;i++){
System.out.println(i);
try{
Exec.obj.wait();
Exec.obj.notify();
}
catch(Exception e){}
}
}
}
}
class CharThread extends Thread{
public void run(){
synchronized(Exec.obj){
for(char c = 'a';c<='z';c++){
System.out.println(c);
try{
Exec.obj.notify();
Exec.obj.wait();
}
catch(Exception e){} }
}
}
}
static Object obj = new Object();
public static void main(String[] args){
CharThread ct = new CharThread();
NumberThread nt = new NumberThread(ct);
nt.start();
}
}
class NumberThread extends Thread{
CharThread t;
public NumberThread(CharThread ct){
t = ct;
}
public void run(){
synchronized(Exec.obj){
t.start();
for(int i = 1;i<=26;i++){
System.out.println(i);
try{
Exec.obj.wait();
Exec.obj.notify();
}
catch(Exception e){}
}
}
}
}
class CharThread extends Thread{
public void run(){
synchronized(Exec.obj){
for(char c = 'a';c<='z';c++){
System.out.println(c);
try{
Exec.obj.notify();
Exec.obj.wait();
}
catch(Exception e){} }
}
}
}
每个线程只能拿到符合自己特点参数的时候才能执行打印
这个构思我觉得很不错,虽然没有实际上控制线程顺序,但是控制了线程的方法是否执行。
看了大家的代码我似乎了解线程一些了。我以前 直接Thread a =new Thread() , a.wait ,实际上一个线程应该是用来控制其他的方法或则对象的吧 ,所以就像 7楼 的 obj.wait一样。
希望还有高手来讲解讲解线程,这个特殊的类
5楼你的方法能实现,代码也简洁,但你毕竟new 了很多个线程对象啊另外我很好奇那个 join 就是
start之后就直接调用 join方法 能保证不被其他线程给抢占CPU时 对么??
join之后那几个线程还有意义么??
int currentThreadIndex;
int currentTurn;
static final int MAX_TURN = 10;
public static void main(String[] args){
String[] threadNames = {"A","B","C","D"};
ThreadTest threadTest = new ThreadTest();
for(int i = 0;i < threadNames.length;i++ )
new Thread(new MyThread(threadNames,i,threadTest)).start();
}
}class MyThread extends Thread{
private String[] threadNames;
private int threadIndex;
private ThreadTest threadTest;
MyThread(String[] threadNames, int threadIndex, ThreadTest threadTest){
this.threadNames = threadNames;
this.threadIndex = threadIndex;
this.threadTest = threadTest;
}
public void run() {
while (true){
synchronized(threadTest){
while (threadTest.currentThreadIndex != threadIndex){
try {
threadTest.notifyAll();
threadTest.wait(100);
if (threadTest.currentTurn == ThreadTest.MAX_TURN)
break;
} catch (InterruptedException e) {
e.printStackTrace();
}
}
if (threadTest.currentTurn == ThreadTest.MAX_TURN)
break;
System.out.print(threadNames[threadIndex]);
threadTest.currentThreadIndex =
(threadTest.currentThreadIndex + 1)%threadNames.length;
if (threadIndex == threadNames.length - 1){
threadTest.currentTurn+=1;
System.out.print("\n");
}
}
}
}
}
用join 是理解错题意了 考的是同步
public class TestThreadPrint implements Runnable {
//这个题目得用同步来做,否则就不会是出现以上的结果 (ABC ABC ABC ABC ...)
public void run() {
for (int i=0; i < 10; i++) {
System.out.print(Thread.currentThread().getName());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
} /**
* @param args
*/
public static void main(String[] args) throws InterruptedException {
// TODO 自动生成方法存根
TestThreadPrint a = new TestThreadPrint();
TestThreadPrint b = new TestThreadPrint();
TestThreadPrint c = new TestThreadPrint();
Thread ta = new Thread(a);
ta.setName("A");
ta.start();
Thread.sleep(100);
Thread tb = new Thread(b);
tb.setName("B");
tb.start();
Thread.sleep(100);
Thread tc = new Thread(c);
tc.setName("C");
tc.start(); }}
如题:有三个线程ID分别是A、B、C,请有多线编程实现,在屏幕上循环打印10次ABCABC… 没要求通过打印线程名来实现打印ABCABC~~~的顺序吧~~
o(╯□╰)o