給大家介紹一個servlet、jsp和mysql之間簡單的相互轉換(就是使用頁面訪問數據庫),以數據庫中table表格為例。
1、建立一個servlet,命名為Check,把數據庫中數據掉取出來
Connection con = Connect.get();//之前分裝好類(上個博客說過)
try {
Statement st = con.createStatement();
ResultSet rs = st.executeQuery("select * from dvd1");//存放數據庫中的數據
ResultSetMetaData rm = rs.getMetaData();//獲取數據庫中字段的名稱、字段的值和屬性
List<Map<String, Object>> list = new ArrayList<Map<String, Object>>();//存放數據庫中的數據
while (rs.next()) {//一個遍歷數據中的數據,直到字段對應的值為null為止
Map<String, Object> m = new HashMap<String, Object>();//使用Map的鍵值對,來對數據庫中的字段和字段對應的值進行存儲
for (int i = 1; i <= rm.getColumnCount(); i++) {//rm.getColumnCount()是字段的個數
m.put(rm.getColumnName(i), rs.getObject(i));//rm.getColumnName(i)遍歷的是字段的名稱,rs.getObject(i)遍歷是字段對應的值
}
list.add(m);//把Map集合的鍵值存放到List集合中
}
rs.close();//對用的完的資源進行關閉
st.close();
con.close();
request.setAttribute("lists", list);//把List集合中數據放到request的域中
request.getRequestDispatcher("/check.jsp").forward(request,response);//把上面的request域的輸送到check.jsp中
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
這是把數據庫中數據讀取出來,注意點:1、request.setAttribute("lists", list);中list是是存放到request域中的變量(List集合中的變量),而lists是要傳送的變量,用在jsp中接受;2、request.getRequestDispatcher("/check.jsp")中getRequestDispatcher中存放是相對地址,“/”表示當前Web項目,"/check.jsp"也就是在當前的Web項目中的check.jsp。(在jsp和servlet之間的跳轉就是靠這些地址,把這個理清楚,基本就是沒有問題了)
2、建立一個jsp,命名為check,接受Check.java中發送過來的數據
<%
List<Map<String, Object>> list = (List<Map<String, Object>>) request.getAttribute("lists");//對servlet中的數據的接收
if (list == null || list.size() < 1) {//判斷數據庫中有沒有數據
out.print("數據庫中沒有數據");
} else {
%>
<div class="head">所有圖書信息</div>
<table align="center">使用的是table表格打印到頁面上
<thead>
<tr align="center">
<td><b>選擇</b></td>
<td><b>ID</b></td>
<td><b>DVD名稱</b></td>
<td><b>狀態</b></td>
<td><b>日期</b></td>
<td><b>次數</b></td>
</tr>
</thead>
<%
for (int i = 0; i < list.size(); i++) {//對接收的數據進行遍歷打印
%>
<tr align="center">
<td><input type="checkbox" value="<%=list.get(i).get("id")%>"></td>//第二get是字段,第一get是第二get對應的值
<td><%=list.get(i).get("id")%></td>
<td><%=list.get(i).get("name")%></td>
<td><%=list.get(i).get("state1")%></td>
<td><%=list.get(i).get("date1")%></td>
<td><%=list.get(i).get("count1")%></td>
</tr>
<%
}
%>
</table>
這個是之前寫個一個列子,注意點:1、request.getAttribute("lists")這就是接收servlet發送過來數據的語句,lists是對應request.setAttribute("lists", list)中的第一個參數;2、if (list == null || list.size() < 1),這里的兩個條件為了避免“”、“ ”,有不是空時,但是它沒有長度;3、<%= %>這是在頁面顯示的語句,而<% %>是jsp中的寫java代碼
這樣就可以把數據庫中的數據再頁面上顯示了。
越往后面的學習中可以發現的servlet中java是可以優化的,當然就一個功能優化了也不是能明顯;同樣的功能實現,代碼越簡潔越來了,給人的感覺也好。
List<Map<String, Object>> list=Mysql.mysql( "select * from teachers");
request.setAttribute("lists", list);
request.getRequestDispatcher("/teacherCheck.jsp").forward(request, response);
這就是servlet中代碼優化之后的代碼,但是上面的代碼都放到了Mysql.mysql方法中,如果有其他的功能需要也就可以直接調用了;這樣就減少了代碼量。
代碼的封裝
static Connection con =null;
static Statement st = null;
static ResultSet rs = null;
public static List<Map<String, Object>> mysql(String sql) {
con = get();//數據庫的連接
List<Map<String, Object>> list = new ArrayList<Map<String, Object>>();
try {
st = con.createStatement();
rs = st.executeQuery(sql);
ResultSetMetaData rsd = rs.getMetaData();//獲取數據庫中字段的名稱和其值
while (rs.next()) {
Map<String, Object> map = new HashMap<String, Object>();
for (int i = 1; i <= rsd.getColumnCount(); i++) {
map.put(rsd.getColumnName(i), rs.getObject(i));
}
list.add(map);
}
return list;
} catch (SQLException e) {
e.printStackTrace();
return null;
} finally {
close(rs, st, null, con);
}
}
這代碼和之前的代碼也是不一樣的,就是對資源用完之后的關閉
public static void close(ResultSet rs, Statement st, PreparedStatement ps,Connection con) {
try {
if (rs != null)
rs.close();
if (st != null)
st.close();
if (ps != null)
ps.close();
if (con != null)
con.close();
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
定義了四個常用的接口,要進行關閉時直接調用就可以了,注意點:當需要關閉的資源沒有四個的時候,把沒有用的輸入null就可以了,在這個方法中有對其的判斷,而這個判斷主要的判斷就是有這個接口的代碼,而沒有執行的情況,進行的判斷:比如說st = con.createStatement();rs = st.executeQuery(sql);如果st這行代碼出現了錯誤,下面st這行代碼就不執行了,拋出了異常,1)封裝的代碼中如果沒有if的判斷就會出現空指針的錯誤,因為rs沒有執行,rs的值為null;2)沒有封裝的代碼,st資源會一直開着,等待java垃圾回收,這樣效率低。
其實這樣也是不合適,這里出現線程安全的問題,下次再給大家分享。
