Executing Two Threads (Write to File)

Hello,

My understanding of threads: JVM Thread Scheduler has the sole authority over scheduling of threads and if two threads are started (Thread1.start and Thread2.start) they will be scheduled and run in not a fixed order, if the same program were to be executed more than once. As JVM Thread scheduler depends on the version of JDK installed, the order could also be dependent on the version. May I be corrected, if I am misinterpreting?

Here is a program that I'm trying to run:

import java.util.*;

import java.io.*;

public class TwoThreads implements Runnable {

Thread tt, ss;

public static void main(String args[]){

TwoThreads runner = new TwoThreads();

Thread tt = new Thread(runner);

Thread ss = new Thread(runner);

tt.setName("Alpha");

ss.setName("Beta");

ss.start();

tt.start();

}

public void run(){

try{

FileWriter fs1 = new FileWriter("/home/crito/tt.txt");

FileWriter fs2 = new FileWriter("/home/crito/ss.txt");

BufferedWriter bw1 = new BufferedWriter(fs1);

BufferedWriter bw2 = new BufferedWriter(fs2);

for (int tk = 0; tk<=1000; tk++)

{double m = Math.sqrt(tk);

if (Thread.currentThread().getName() == "Alpha")

{

bw1.write("Square root of "+tk+" = "+m);

bw1.newLine();

}

else

{

bw2.write("Square root of "+tk+" = "+m);

bw2.newLine();

}

}

bw1.close();

bw2.close();

} catch(Exception ex) {ex.printStackTrace();}

}

}

The output creates two files, ss.txt (with all square-roots from o to 1000) and tt.txt (blank file). Shouldn't the above logic provide turns for the threads and populate square-roots in both files? If not, then how should the code be modified to achieve almost concurrent population of records.

Thanks for bearing with me.

[1909 byte] By [Javajockeya] at [2007-11-26 18:37:57]
# 1
Do you want two files to be written to concurrently, or do you want two files to be written to in lock-step (a record for you, a record for me...)?
DrLaszloJamfa at 2007-7-9 6:12:01 > top of Java-index,Java Essentials,Java Programming...
# 2
Can you suggest how we could do it in both cases? Thanks for your reply.
Javajockeya at 2007-7-9 6:12:01 > top of Java-index,Java Essentials,Java Programming...
# 3
Write to two files concurrently: create two threads, with separate runnables. Each runnable opens and write to one file -- no tricks!Lock-step: don't use threads.
DrLaszloJamfa at 2007-7-9 6:12:01 > top of Java-index,Java Essentials,Java Programming...
# 4

> Write to two files concurrently: create two threads,

> with separate runnables. Each runnable opens and

> write to one file

One file each, that is. Two separate files. Else you'll likely end up with a jumble of intermixed ****--and not necessarily line by line, but within a given line.

jverda at 2007-7-9 6:12:01 > top of Java-index,Java Essentials,Java Programming...
# 5

> Shouldn't the above logic provide turns for the

> threads and populate square-roots in both files?

No. You're creating two threads, each of which tries to do tha majority of the code in your run method.

If you were expecting them to take turns to write different values, then no this isn't going to happen. If you were expecting them both to write the same set of values to both files, then that's closer, but you open BOTH files within BOTH threads, and whichever thread executes first will get a lock on the files (preventing the other thread from writing).

Two additional points. Firstly, PLEASE use code formatting (the "code" button - and read the [url http://forum.java.sun.com/help.jspa?sec=formatting]Formatting tips[/url] link)

Secondly it's a dreadful idea to try to control the thread behaviour on the basis of its name. Write your Runnable class to take appropriate parameters in the constructor, and use those to determine filenames and the like.

(Edit: man am I slow today...)

dcmintera at 2007-7-9 6:12:01 > top of Java-index,Java Essentials,Java Programming...
# 6

Thanks. I'm sorry about the code format.

This is a book example from Head First Java:

public class HeadFirst implements Runnable{

public static void main(String args[]){

HeadFirst runner = new HeadFirst();

Thread a = new Thread(runner);

Thread b = new Thread(runner);

a.setName("a");

b.setName("b");

a.start();

b.start();

}

public void run(){

for (int i=0; i<25; i++){

String tk = Thread.currentThread().getName();

System.out.println(tk+"is running");

}

}

}

The book says the threads will alternate though not with a fixed frequency of occurrence. It also says the order of occurrences would differ from one run to other. I am using JDK 6 and for me (always) thread a executes 25 times followed by thread b which executes 25 times. Is the execution JVM-specific?

Thanks.

Javajockeya at 2007-7-9 6:12:01 > top of Java-index,Java Essentials,Java Programming...
# 7

Here is the output 1 get:

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

bis running

ais running

java.vm.version=1.5.0_10-b03

DrLaszloJamfa at 2007-7-9 6:12:01 > top of Java-index,Java Essentials,Java Programming...
# 8

> other. I am using JDK 6 and for me (always) thread a

> executes 25 times followed by thread b which executes

> 25 times.

The time to execute 25 printlns is very, very small, and not worth a context switch. And most likely neither thread has to block, so there's no reason to switch one out and let the other one do work.

A more realistic test would be to have them write large blocks to two different pysical disks--maybe one local and one a network share.

> Is the execution JVM-specific?

Yes. The two competing concerns to balance are:

* Giving each thread some CPU cycles reasonably frequently, so none of them starve. (Context switch based on a time slice.)

* Not switching contexts more often than necessary, as that incurs overhead. (Context switch when a thread blocks, say on I/O.)

The rules of how those concerns are balanced depends on the hardware, the VM, possibly startup args to the VM. The effects of those rules depend on what other processes are running, how much memory they're using, disk load, network load, user activity... all kinds of stuff.

jverda at 2007-7-9 6:12:01 > top of Java-index,Java Essentials,Java Programming...
# 9

With respect to the solution of having two separate classes (Runnables) for two threads to write same data into two files:

If I have a scenario where multiple slave computers run the same logic and turn in their results (results differ because each slave uses Math.random() function) in form of a file to a single master computer, does that main I will need as many runnable class files as the number of slaves computers?

Javajockeya at 2007-7-9 6:12:01 > top of Java-index,Java Essentials,Java Programming...
# 10
It sounds like the same Runnable class would work everywhere. If your class needs specific parameters, why not pass them in the constructor?
DrLaszloJamfa at 2007-7-9 6:12:01 > top of Java-index,Java Essentials,Java Programming...
# 11

In the first program, I had tried to use the same Runnable class and write the data to two files. Data was populated only in one file. As per your suggestion, when I used two separate Runnable classes, I was able to achieve the desired result (data written into two separate files). Wouldn't using one Runnable class file then cause the same problem in the client server scenario?

Also, in my case each slave needs to do the same thing, take exactly same patterns but results would differ because each slave would take different random number streams.

Thanks.

Javajockeya at 2007-7-9 6:12:01 > top of Java-index,Java Essentials,Java Programming...
# 12
I think you answered your own question.
DrLaszloJamfa at 2007-7-9 6:12:01 > top of Java-index,Java Essentials,Java Programming...