JSP default is multithreaded, this is the JSP and Asp,php,perl script language is not the same place, but also one of its advantages, but if you do not pay attention to the synchronization problem in multiple threads, will make the written JSP program has difficult to find errors. The following is an example of the multithreading problem in JSP and how to solve it.
One, JSP in the existence of multithreading problems:
When a client requests a JSP file for the first time, the server compiles the JSP into a class file, creates an instance of the class, and then creates a thread to handle the client-side request. If more than one client requests the JSP file at the same time, the server creates multiple threads. Each client request corresponds to a thread. Implementing multithreading can greatly reduce the resource requirements of the system and increase the concurrency and response time of the system. The variables that might be used in a JSP are described below:
Instance variables
Instance variables are allocated in the heap and are shared by all threads belonging to that instance, so they are not thread-safe.
JSP system provides 8 class variables, JSP used in the OUT,REQUEST,RESPONSE,SESSION,CONFIG,PAGE,PAGECONXT is thread-safe, application is used throughout the system, so is not thread-safe.
Local variables
Local variables are allocated on the stack, because each thread has its own stack space, so it is thread-safe.
Static class
Static classes can be used directly, and are not thread-safe, without being instantiated.
External resources:
There may be multiple threads or processes in your program that simultaneously manipulate the same resource (for example, multiple threads or processes writing to a file at the same time). Be aware of synchronization issues at this point.
Second, the following examples of multithreading problems:
<%@ page import=
javax.naming.*,
java.util.*,
java.sql.*,
weblogic.common.*
"%>
<%
Stri ng name
String product;
Long quantity
Name=request.getparameter ("name");
product= Request.getparameter ("Product");
Quantity=request.getparameter ("Quantity");/* (1) */
Savebuy ();
%>
<%!
public void Savebuy ()
{
/* Perform database operations, save data to table */
try {
Properties props = new properties ();
Props.put ("User", "Scott");
Props.put ("Password", "Tiger");
Props.put ("Server", "DEMO");
Driver mydriver = (Driver) Iver "). newinstance ();
conn = Mydriver.connect ("jdbc:weblogic:oracle", props);
stmt = Conn.createstatement ();
String inssql = "INSERT into buy (empid, name, dept) VALUES (?,?,?,?)";
stmt = conn.preparestatement (Inssql);
Stmt.setstring (1, name);
Stmt.setstring (2, procuct);
Stmt.setint (3, quantity);
Stmt.execute ();
}
catch (Exception e)
{
System.out.println ("SQLException was THrown: "+ e.getmessage ());
}
Finally//close connections and {
try {
if (stmt!= null)
Stmt.close ();
if (conn!= null)
Con N.close ();
} catch (SQLException Sqle) {
System.out.println ("SQLException was thrown:" + sqle.getmessage ());
}
}
}
%>
The above program simulates a part of online shopping and saves the user name, the name of the item purchased, and the number of items you enter in the browser to the table. An instance variable is used in the Savebuy () function, so it is not thread safe. Because: Each statement in the program is not an atomic operation, such as Name=request.getparameter ("name"), the execution of which will correspond to multiple machine instructions, at any time may be scheduled by the system to sleep state, so that other threads to continue to execute. If thread a goes to sleep when it executes to (1), thread B starts executing and changes the value of the quantity, then when it executes, it starts executing from the call Savebuy () function, so that the quantity that it saves to the table is the value that was changed by thread B. It is a serious problem that thread a corresponds to the number of users actually buying that is inconsistent with the data kept in the table.
Third, the solution
Using single thread
In the JSP file, add: To make it run single-threaded, there is still only one instance, and all client requests are executed serially. This can degrade the performance of the system.
Thread Synchronization of Function savebuy () plus synchronized, which is still performed in multithreading, but can also degrade system performance:
Public synchronized void Savebuy ()
{
......
}
Using local variables instead of instance variables, the function savebuy () is declared as follows:
Because the parameters that are passed to him in Savebuy () are allocated in the stack, they are thread-safe.
public void Savebuy (String name,string product, int quantity)
{
......
}
The method of invocation should read:
<%
String Name
String product;
Long quantity;
Name=request.getparameter ("name");
Product=request.getparameter ("Product");
Quantity=request.getparameter ("Quantity");
Savebuy (name,product,quantity)
%>
If you have a lot of savebuy parameters, or if the data is used in many places, you can declare a class and use it as a parameter, such as:
public class Buyinfo
{
String name;
String product;
Long quantity;
}
public void Savebuy (Buyinfo info)
{
......
}
The method of invocation should read:
<%
Buyinfo userbuy = new Buyinfo ();
Userbuy.name=request.getparameter ("name");
Userbuy.product=request.getparameter ("Product");
Userbuy.quantity=request.getparameter ("Quantity");
Savebuy (userbuy);
%>
So it's best to use 3 because 1,2 can degrade the performance of the system.
Multithreading problems are generally only possible in the case of large concurrent volume access, and are difficult to repeat, so you should always be aware of programming.