【问题标题】:Console shared with Thread与 Thread 共享的控制台
【发布时间】:2011-12-09 21:07:23
【问题描述】:

我在 java 中遇到了简单的 MT 问题。我想同步访问控制台。一个例子: 第一个线程写入 System.out "Number one" Thread2 printl("Number two")。我想在不缓冲的情况下同步这个线程在控制台中按顺序写入数字。这是怎么做到的?

Thread one
Thread two
Thread one
Thread two
...

//代码

package com.example;

public class MyThread implements Runnable{


@Override
synchronized public void run(){
    while(true){
        System.out.println("Thread first");

    }
}

}

//

package com.example;

public class MyThread2 implements Runnable {


@Override
synchronized public void run() {
    // TODO Auto-generated method stub
    System.out.println("");

}

}

//

 package com.example;

import java.util.concurrent.Semaphore;

public class Main {

    /**
     * @param args
     */
    public static void main(String[] args) {
        // TODO Auto-generated method stub

Thread th1= new Thread(new MyThread());
Thread th2= new Thread(new MyThread2());

th2.setPriority(Thread.MAX_PRIORITY);
th1.start();
th2.start();
    }

}

【问题讨论】:

  • 如果您在使用现有代码时遇到问题,请发布一些。你试过什么了?另外,除了homework 或某种学习练习之外,我不确定您为什么要这样做。如果这是作业,请将该标签也添加到问题中,以便我们知道只是提供提示。
  • 如果要顺序写入,为什么要使用线程?这只是一个有趣的问题吗?
  • 你需要两个线程交替吗?或者你需要任意数量的线程,而这个例子恰好是两个?
  • 我喜欢阻塞线程并等待它访问控制台。这只是一个简单的例子..

标签: java multithreading console


【解决方案1】:

我担心这是一个相当无用的问题,因为如果我们想要一个顺序排序的线程是相当无用的,但是哦,这是一个解决方案:假设我们有 N 个线程。

线程 0 应该写数字 0, N, 2N, 3N,..

线程 1 应该写数字 1, N+1, 2N+1, 3N+1

好吧,你得到了模式。这该怎么做?很简单,我们基本上只需要一个等待轮到我们编写的方法。为简单起见,使用静态对象的真正简单解决方案:

private static volatile int globalVal = 0;
private static Object lock = new Object();

public void writeInt(int val) {
    synchronized(lock) {
        while (globalVal != val) {
            try {
                lock.wait();
            }
            catch(InterruptedException e) {
            }
        }
        System.out.println(val);
        globalVal++;
        lock.notifyAll();
    }
}

线程本身的逻辑留给读者练习。

【讨论】:

    【解决方案2】:

    使用Queue<String> 并将Strings 添加到队列中。然后有一个专用线程从队列中取出并将其写入控制台。这将根据线程的队列访问创建一个 FIFO 排序。

    如果您不想使用队列,您应该使用类似令牌管理器的东西来切换被阻塞的线程。 Exchanger<V>for 每个参与的线程将是一个很好的起点。

    【讨论】:

    • 这不能确保将序列号写入控制台。练习是线程之间的严格交替,每个线程在打印之间等待另一个线程。
    • 取决于队列实现,但如果是 2 个线程,可以使用 SynchronousQueue<E>
    • user949300:不,因为你不能确定线程调度。
    • 触摸 - 好点。我认为代码需要一个知道如何在线程之间严格交替的锁。
    猜你喜欢
    • 2017-11-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-05-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多