Java Performance Tuning
Java(TM) - see bottom of page
Our valued sponsors who help make this site possible
JProfiler: Get rid of your performance problems and memory leaks!
Training online: Concurrency, Threading, GC, Advanced Java and more ...
Tips April 2006
JProfiler
|
Get rid of your performance problems and memory leaks!
|
JProfiler
|
Get rid of your performance problems and memory leaks!
|
|
|
Back to newsletter 065 contents
http://jboss.org/jbossBlog/blog/acoliver/2006/03/21/If_you_dont_do_this_JBoss_will_run_really_slowly.txt
Speeding default JBoss (Page last updated March 2006, Added 2006-04-27, Author Andrew Oliver, Publisher JBoss). Tips:
- By default, the RMI subsystem forces a full garbage collection once per minute.
- To reduce the frequency of RMI distributed garbage collection to once per hour, use -Dsun.rmi.dgc.client.gcInterval=3600000 -Dsun.rmi.dgc.server.gcInterval=3600000
- You can add XX:+DisableExplicitGC to make sure that explicit calls to System.gc() doesn't do anything.
- If you do a lot of remote object calls (EJBs) and don't cache your Home or Remote objects then MAYBE once per hour of distributed garbage collection won't be enough.
- The -server changes various settings, like the thread stack size. It maye then be using too much memory for your app - you may need to reset thread stack size with e.g. -XX:ThreadStackSize=128 or -Xss128k
http://www-128.ibm.com/developerworks/java/library/j-jtp03216.html
Good housekeeping practices (Page last updated March 2006, Added 2006-04-27, Author Brian Goetz, Publisher IBM). Tips:
- Non-memory resources like file handles and socket handles must be explicitly released by the program.
- Waiting until finalization to release some resources is not an option: Locks and Semaphores are not likely to get garbage collected until it is too late; you would run out of database connections if you waited for finalization.
- Exceptions being thrown can prevent resources being released. Code should ensure that releases occur irrespective of possible exceptions, typically in finally blocks.
- It may be necessary to nest finallys if closing multiple resources - ugly but necessary. Bear in mind that nearly anything can throw an Exception.
- Resources acquired on a per-user basis (including the socket connection) must be released when the user logs out.
- Maintaining an ownership hierarchy, where each resource owns the resources it acquires and is responsible for releasing them, helps keep the resource complexity from getting out of control.
- Don't rely on finalizers as the primary means of releasing resources.
- Finalizers are very easy to write incorrectly.
- The timing of finalization is not deterministic, and there is no guarantee that finalizers will ever even run.
- Finalization adds overhead to instantiation and garbage collection of finalizable objects.
http://java.sys-con.com/read/204711.htm
Concurrent Programming and Locking in J2SE 5.0 (Page last updated April 2006, Added 2006-04-27, Author Craig Caulfield, Publisher JDJ). Tips:
- The synchronized keyword has limitations: it can't be interrupted or timed-out; only a single condition can be tested using the wait() and notify() methods.
- The Lock interface (implementations, the ReentrantLock and ReentrantReadWriteLock) is more flexible than the synchronized keyword.
- With the Lock interface threads can poll objects for existing locks held by other threads before trying to acquire a lock themselves. Locks can also specify timeouts, during which they can be interrupted.
- As an object, a Lock can be stored, passed around, or discarded, meaning multiple objects can share the same lock, or one object can have multiple locks.
- A Lock object can have multiple condition objects.
- The synchronized keyword causes an execution block to block until the monitor's lock becomes available. The lock is released on normal or exception termination of the execution block.
- The synchronized keyword imposes a modest performance hit in the case of uncontended locks.
- The synchronized keyword provides implicit locking, whereas the Lock interface makes locking explicit.
- A lock is called re-entrant because a thread can repeatedly acquire a lock that it already owns. The lock keeps track of these acquisitions and the thread must call unlock() each time it has been locked to release the lock fully.
- When a synchronized method or block exits normally or by exception, any locks are automatically released. With an explicit lock of the Lock implementations, locks are only released explicitly - typically by following the call to lock() with a try/finally block, with the lock being released in the finally clause.
- ReentrantLock and ReentrantReadWriteLock constructors can take an optional fairness parameter. When this parameter is set to true and there's contention for an object's lock, the lock will be granted to the thread that's been waiting the longest.
- Fair locks don't have the same throughput as unfair locks - the fairness parameter should always be set to false
- Where there's a requirement that threads be served in a first-created, first-out (fair) order, there are dedicated data structures that can do this better than using fair Locks.
- A call to await() should always be inside a while-loop there's no guarantee that the condition will be true when the thread is next notified.
- It is good practice to put the await() while-loop immediately after the call to lock().
- A deadlock is where a thread acquires resource A and then tries to acquire resource B and another thread may already be holding resource B and is, in turn, trying to acquire resource A.
- A deadlock only can form if: only one process or thread may use a resource at a time (Mutual exclusion), and a process or thread may hold allocated resources while waiting to acquire others (Hold-and-wait), and no resource can be forcibly removed from a process or thread that holds it (No pre-emption).
- The usual way of preventing a circular wait is to design a lock hierarchy and make sure that all threads acquire their locks in the same sequence.
- The lockInterruptibly() method from the Lock interface: If the interrupt() method is called on a thread while it's waiting to acquire a lock, an InterruptedException is thrown and the attempt to acquire the lock is abandoned.
- Typical use of lockInterruptibly():
try {lock.lockInterruptibly(); try { ... } finally {lock.unlock(); } } catch (InterruptedException e) { ... }
- You can also try to acquire a lock rather than block trying:
if (lock.tryLock()) try { ... } finally { lock.unlock(); } else ...
- tryLock() can be called with a timeout parameter:
if (lock.tryLock(100, TimeUnit.MILLISECONDS))...
- await() can be called with a timeout parameter:
condition.await(100, TimeUnit.MILLISECONDS))
- Acquiring a contended lock causes a bigger performance hit than acquiring an uncontended lock.
- As little work as possible is done under locking: obtain a lock, do whatever is necessary, and then release the lock quickly.
- ReentrantReadWriteLock is more flexible than ReentrantLock: a write lock is still mutually exclusive, but if none of these is active, then a read lock can be held by more than one reader thread at once.
- The ReentrantReadWriteLock works best in situations where there will be more reader threads than writer threads.
- The synchronized keyword produces code that is simpler and more concise; the new Lock utilities rely on the idiom of explicitly acquiring a lock and then releasing it inside a finally block so are more complex but more flexible.
http://cretesoft.com/archive/newsletter.do?issue=124&locale=en_US
Copying Arrays Fast (Page last updated March 2006, Added 2006-04-27, Author Heinz Kabutz, Publisher JavaSpecialists). Tips:
- clone() is apparently slower than creating a new byte[] and copying the values into it using System.arraycopy. But this is true only for small arrays.
- clone() checks whether an instance is normal object or array, and whether the array is of primitives or objects. For small arrays, the cost of the two ifs dominates the cost of creating the arrays.
- [Article provides a PerformanceChecker class to run performance tests on a class].
- [Article provides an Average class which provides average and stddev statistics for a set of values].
- The point at which an object is put into Old Space is when it is larger than 512kb [for default heap values of the Sun JVM].
http://www.devx.com/Java/Article/31228
Clustering at the JVM Level (Page last updated April 2006, Added 2006-04-27, Author Ari Zilka, Publisher DevX). Tips:
- A solution that uses the network or database to replicate changes will be bottlenecked on network bandwidth or database scalability.
- Any tool based on serialization suffers from a "copy-on-change" issue - a change effectively makes a new object in other JVMs.
- JMS and JGroups provide high availability by sharing critical information across machines and JVMs. However, they send all information to all JVMs and will bottleneck on the network.
- A database provides high availability by storing data in a highly available database server. However, it sends all information to the database and will bottleneck on the DB server.
- Application servers provide load balanced clustering but require the application to be architected appropriately to deliver the full scalability and high availability benefits.
- A clustered JVM (like Terracotta) distributes a Java application transparently to the application.
http://www.onjava.com/pub/a/onjava/2006/04/19/database-connection-pooling-with-tomcat.html
Database Connection Pooling (Page last updated April 2006, Added 2006-04-27, Author Kunal Jaggi, Publisher OnJava). Tips:
- Connection pooling is a technique used for sharing a cached set of open database connections among several requesting clients. It doesn't require you to modify your code significantly while still providing enhanced performance benefits.
- Creating new connections for data access, maintaining them, and tearing down the open connection can lead to massive load on the server.
- Connection pooling reduces JDBC overhead.
- A connection pool typically can configure; a maximum or unlimited number of connections in the pool; a maximum or unlimited number of idle database connections to be retained in the pool; maximum time to wait for a database connection to become available (after which an exception is thrown).
- Optimal performance is attained when a connection pool in its steady state contains just enough connections to service all concurrent connection requests, without having to create new physical database connections at runtime.
http://java.sun.com/developer/technicalArticles/J2EE/AJAX/RealtimeValidation/
Realtime Form Validation Using AJAX (Page last updated April 2006, Added 2006-04-27, Author Greg Murray, Publisher Sun). Tips:
- Traditional web applications require that the form data be posted to the server for validation of all fields. However, this strategy can be distracting to the end user, especially in cases where a single form field is invalid. Using AJAX, data can be validated by the server in near real-time as the user types the data in an HTML form.
- [Article runs through an example of an AJAX client validating a field using a Servlet without having the full form posted to the server].
Jack Shirazi
Back to newsletter 065 contents
Last Updated: 2025-01-27
Copyright © 2000-2025 Fasterj.com. All Rights Reserved.
All trademarks and registered trademarks appearing on JavaPerformanceTuning.com are the property of their respective owners.
Java is a trademark or registered trademark of Oracle Corporation in the United States and other countries. JavaPerformanceTuning.com is not connected to Oracle Corporation and is not sponsored by Oracle Corporation.
URL: http://www.JavaPerformanceTuning.com/news/newtips065.shtml
RSS Feed: http://www.JavaPerformanceTuning.com/newsletters.rss
Trouble with this page? Please contact us