Image

Imagebanana wrote in Imagejava_dev

Thread question

This is quite a long post...


I went on a Java course from Sun when I was a newbie. The tutor taught the threading part quite well, with one wierd thing. He said that there is a memory leak when threads die, and that you should therefore not let them die, but keep them alive and re-use them. The reason he gave for the memory leak is that you can always query the exit status of a thread, even long after it's gone.


On the assumption that he knew what he was talking about, I have written thread pooling mechanisms, and advised others to do the same. It's not too hard, but is it a waste of time? I had a go at testing this recently.


Below is my test code. The idea is that each thread displays the available memory and (except the 1000th) spawns another thread. If you try this, you'll see the available memory stabilise pretty quickly. If you're really keen, try commenting the first clean (); in the run() method - then you'll see available memory tumble until garbage collection runs automatically, and each time it does, you get back to the same base (and this is why there's a sleep on the last thread).


public class ThreadCycler
		extends Thread
{
	private static int threadCount = 0;

	public static void main ( String [] args )
	{
		System.out.println ( "Starting..." );

		// Start the first thread
		spawn ();

		System.out.println ( "Finished main." );
	}

	public void run()
	{
		// Clean up memory
		clean ();

		// Show memory usage
		show ();

		// Start another thread
		if ( threadCount < 1000 )
		{
			spawn ();
		}
		else
		{
			try
			{
				System.out.println ( "Sleeping..." );
				Thread.sleep ( 10000L );
			}
			catch ( InterruptedException e )
			{
				System.out.println ( "Sleep interrupted!" );
			}

			show ();
			clean ();
			show ();
		}
	}

	private void clean ()
	{
		System.gc ();
		System.runFinalization ();
	}

	private void show ()
	{
		Runtime rt    = Runtime.getRuntime ();
		long    free  = rt.freeMemory ();
		long    total = rt.totalMemory ();
		Thread  t     = Thread.currentThread ();

		System.out.println ( t.getName () + ' ' + t.activeCount () + ' ' + free + ' ' + total + ' '
			 + ( ( double ) free / ( double ) total * 100.0 ) + '%' );
	}

	private static void spawn ()
	{
		ThreadCycler tc = new ThreadCycler ();
		tc.start();
		threadCount++;
	}
}


So...
The question is: does this mean that there's no leak when threads die, or is my test wrong?