关于线程基础的问题

dodomila_ 2016-07-01 05:30:05
用java编写一个程序实现多线程,在线程中输出线程的名字到文件test.txt中,隔300毫秒输出一次,共输出20次。
在做这道题的时候想用实现Runnable接口达到多个线程一共输出20次的效果。我是参考这段代码做的:
package test;

public class MutliThreadDemo {
public static void main(String [] args){
MutliThread m=new MutliThread();
Thread t1=new Thread(m,"window 1");
Thread t2=new Thread(m,"window 2");
Thread t3=new Thread(m,"window 3");
t1.start();
t2.start();
t3.start();
}
}
class MutliThread implements Runnable{
private int ticket=20;//所有线程一共拥有20张票
private int a;
public void run(){
while(ticket>0){
System.out.println(ticket--+" is saled by "+Thread.currentThread().getName());

}
}
}


但是给文件里输出的时候就是21条。这是我的代码:
package test;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.PrintWriter;

public class ThreadTest {
public static void main(String [] args){
DemoThread dt=new DemoThread();
Thread t1=new Thread(dt);
Thread t2=new Thread(dt);
Thread t3=new Thread(dt);
t1.start();
t2.start();
t3.start();
}
}
class DemoThread implements Runnable{
private int num=20;//所有线程一共输出0次

private String fl = "F:\\Test.txt";
File f = new File(fl);

public void run(){
if(f.exists() && f.isFile()){
System.out.println("使用已经存在的Test.txt文件");
}else{
try{
//创建文件
f.createNewFile();
System.out.println("创建Test.txt文件");
}catch(IOException e){
System.out.println("创建Test.txt文件失败,错误信息:"+e.getMessage());
return;
}
}
while(num>0){
try {
FileOutputStream fos = new FileOutputStream(f,true);
PrintWriter pw = new PrintWriter(fos);
pw.write(num--+" ---"+Thread.currentThread().getName());//每输出一次num-1
pw.println();
pw.close();
} catch (FileNotFoundException e) {
System.out.println(e.getMessage());
}
}
}
}

而且我总感觉我写的有问题,求大神讲解一下为什么,正确的应该是什么。
...全文
168 9 打赏 收藏 转发到动态 举报
写回复
用AI写文章
9 条回复
切换为时间正序
请发表友善的回复…
发表回复
dodomila_ 2016-07-01
  • 打赏
  • 举报
回复
引用 7 楼 txazo 的回复:

public class MutliThreadDemo {

    public static void main(String[] args) throws IOException {
        MutliThread m = new MutliThread();
        Thread t1 = new Thread(m, "window 1");
        Thread t2 = new Thread(m, "window 2");
        Thread t3 = new Thread(m, "window 3");
        t1.start();
        t2.start();
        t3.start();
        System.in.read();
    }

}

class MutliThread implements Runnable {

    private AtomicInteger a = new AtomicInteger(0);

    public void run() {
        int num = 0;
        while ((num = a.incrementAndGet()) <= 20) {
            System.out.println(num + " is saled by " + Thread.currentThread().getName());

        }
    }

}
给一个正确的例子,可以在网上搜下Java内存模型的文章学习下
那麻烦问一下,我贴的那个参考案例是错误的是么?但是那个运行下来是20没错啊
dodomila_ 2016-07-01
  • 打赏
  • 举报
回复
引用 7 楼 txazo 的回复:

public class MutliThreadDemo {

    public static void main(String[] args) throws IOException {
        MutliThread m = new MutliThread();
        Thread t1 = new Thread(m, "window 1");
        Thread t2 = new Thread(m, "window 2");
        Thread t3 = new Thread(m, "window 3");
        t1.start();
        t2.start();
        t3.start();
        System.in.read();
    }

}

class MutliThread implements Runnable {

    private AtomicInteger a = new AtomicInteger(0);

    public void run() {
        int num = 0;
        while ((num = a.incrementAndGet()) <= 20) {
            System.out.println(num + " is saled by " + Thread.currentThread().getName());

        }
    }

}
给一个正确的例子,可以在网上搜下Java内存模型的文章学习下
十分感谢
txazo 2016-07-01
  • 打赏
  • 举报
回复

public class MutliThreadDemo {

    public static void main(String[] args) throws IOException {
        MutliThread m = new MutliThread();
        Thread t1 = new Thread(m, "window 1");
        Thread t2 = new Thread(m, "window 2");
        Thread t3 = new Thread(m, "window 3");
        t1.start();
        t2.start();
        t3.start();
        System.in.read();
    }

}

class MutliThread implements Runnable {

    private AtomicInteger a = new AtomicInteger(0);

    public void run() {
        int num = 0;
        while ((num = a.incrementAndGet()) <= 20) {
            System.out.println(num + " is saled by " + Thread.currentThread().getName());

        }
    }

}
给一个正确的例子,可以在网上搜下Java内存模型的文章学习下
qq_15915835 2016-07-01
  • 打赏
  • 举报
回复
引用 5 楼 dodomila_ 的回复:
[quote=引用 4 楼 qq_15915835 的回复:] 用 AtomicInteger 来计数
没有基础的方法来解决吗?我不懂啊[/quote] 对非线程安全变量操作加锁,这里就是num
dodomila_ 2016-07-01
  • 打赏
  • 举报
回复
引用 4 楼 qq_15915835 的回复:
用 AtomicInteger 来计数
没有基础的方法来解决吗?我不懂啊
qq_15915835 2016-07-01
  • 打赏
  • 举报
回复
用 AtomicInteger 来计数
dodomila_ 2016-07-01
  • 打赏
  • 举报
回复
引用 2 楼 u011619071 的回复:
最好的办法是使用 原子操作,
我把num定义成volatile的输出的还是21条数据啊
X元素 2016-07-01
  • 打赏
  • 举报
回复
最好的办法是使用 原子操作,
X元素 2016-07-01
  • 打赏
  • 举报
回复
private int num=20; 试着使用volatile

62,614

社区成员

发帖
与我相关
我的任务
社区描述
Java 2 Standard Edition
社区管理员
  • Java SE
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧