1:电商如此发达的现在,作为一个web开发程序猿,如果不会写购物车,真是有点不好意思找工作。所以抓紧练习啊,从上篇博客中抽离出如何实现购物车的功能。

2:首先需要理解购物车实现的一些基本步骤。
  2.1:首先考虑我购买的是哪一本书籍或者那一件商品,是不是,这里可以使用id传参确定购买的是那一件商品或者书籍,也可以使用session中取出哪一本书籍,这里采用从session的取出那一件商品或者书籍
       代码如:

      Book book=(Book)session.getAttribute("book");
     2.2:第二考虑如何把书籍放到购物车中
         2.1.1:首先考虑是否有购物车,如果没有,则创建,如果有直接使用
         2.1.2:其次先将购物车从session中拿出来,不存在就创建。
    代码如:

      Map<Integer,CartItem> cart=(Map<Integer,CartItem>)session.getAttribute("cart");
        //如果没有购物车,那么创建,只有第一次访问才会操作
        if(cart==null){
           //new一个购物车
          cart=new HashMap<>();
        }
    2.3:考虑如何把书籍放到购物车中
       2.1.1:第一考虑购物车中是否有该书籍,所以先从购物车中获取该书籍,如果为空,那么没有该书籍
     代码如:

    CartItem item=(CartItem)cart.get(book.getBookid());
       if(item==null){
             //如果购物车中不存在该书籍,那么创建,且数量默认为1
               item=new CartItem();
               //将书籍放到购物车中
              item.setBook(book);
              //将书籍的默认数量为1
              item.setNumber(1);
          }else{
              //如果购物车中以及有该书籍,那么数量加1
              item.setNumber(item.getNumber()+1);
          }
    2.4:考虑如何把购物车项(即挑选的书籍是哪一个和书本的数量)放到购物车中
      代码如:

    cart.put(book.getBookid(),item);
    2.5:将购物车放到session中,方便后面取出来
      代码如:

  session.setAttribute("cart", cart);


3:下面是具体的实现,从创建数据表开始,数据表book字段和数据名称如下所示:

 

4:下面创建实体类book.java;

 package com.bie.po;

 import java.io.Serializable;

 /**
* @author BieHongLi
* @version 创建时间:2017年2月27日 上午10:07:21
* 图书的实体类
*/
public class Book implements Serializable{ //实体类实现序列化,避免后面出现异常
private static final long serialVersionUID = 1L;
private Integer bookid;
private String bookname;
private Double price;
private String author;
private String pic;
private String publish;
public Integer getBookid() {
return bookid;
}
public void setBookid(Integer bookid) {
this.bookid = bookid;
}
public String getBookname() {
return bookname;
}
public void setBookname(String bookname) {
this.bookname = bookname;
}
public Double getPrice() {
return price;
}
public void setPrice(Double price) {
this.price = price;
}
public String getAuthor() {
return author;
}
public void setAuthor(String author) {
this.author = author;
}
public String getPic() {
return pic;
}
public void setPic(String pic) {
this.pic = pic;
}
public String getPublish() {
return publish;
}
public void setPublish(String publish) {
this.publish = publish;
}
@Override
public String toString() {
return "Book [bookid=" + bookid + ", bookname=" + bookname + ", price=" + price + ", author=" + author
+ ", pic=" + pic + ", publish=" + publish + "]";
} }

5:创建好实体类接下来是写工具类BaseDao.java,用于连接数据库的操作,这些代码就不做多解释了,都已经写烂了。所以工具类一定要熟练书写

 package com.bie.utils;

 import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException; /**
* @author BieHongLi
* @version 创建时间:2017年2月27日 上午10:09:00
* 连接数据库的工具类
*/
public class BaseDao { private static String driver="com.mysql.jdbc.Driver";
private static String url="jdbc:mysql:///test";
private static String user="root";
private static String password="123456"; /***
* 连接数据库的方法
* @return
* @throws ClassNotFoundException
* @throws SQLException
*/
public static Connection getCon() throws ClassNotFoundException, SQLException{
Class.forName(driver);//加载数据库驱动
System.out.println("测试加载数据库成功");
Connection con=DriverManager.getConnection(url, user, password);
System.out.println("测试数据库链接成功");
return con;
} /***
* 关闭数据库的方法
* @param con
* @param ps
* @param rs
*/
public static void close(Connection con,PreparedStatement ps,ResultSet rs){
if(rs!=null){//关闭资源,避免出现异常
try {
rs.close();
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
if(ps!=null){
try {
ps.close();
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
if(con!=null){
try {
con.close();
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
} /***
* 同意增删改的方法
* @param sql
* @param arr
* @return
*/
public static boolean addUpdateDelete(String sql,Object[] arr){
Connection con=null;
PreparedStatement ps=null;
try {
con=BaseDao.getCon();//第一步 :连接数据库的操作
ps=con.prepareStatement(sql);//第二步:预编译
//第三步:设置值
if(arr!=null && arr.length!=0){
for(int i=0;i<arr.length;i++){
ps.setObject(i+1, arr[i]);
}
}
int count=ps.executeUpdate();//第四步:执行sql语句
if(count>0){
return true;
}else{
return false;
}
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return false;
} public static void main(String[] args) {
try {
BaseDao.getCon();
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}

6:写好工具类就可以进行写dao层(数据交互层),service层(业务逻辑层),先写数据交互层dao层,使用先创建接口再实现接口的方法

 package com.bie.dao;

 import java.util.List;

 import com.bie.po.Book;

 /**
* @author BieHongLi
* @version 创建时间:2017年2月27日 上午10:11:21
*
*/
public interface BookDao { /***
* 图书的查询的方法
* @param sql
* @param arr
* @return
*/
public List<Book> select(String sql,Object[] arr); /***
* 按照图书编号进行查询
* @param id
* @return
*/
public Book getBook(Integer id);
}
 package com.bie.dao.impl;

 import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List; import com.bie.dao.BookDao;
import com.bie.po.Book;
import com.bie.utils.BaseDao; /**
* @author BieHongLi
* @version 创建时间:2017年2月27日 上午10:11:34
*
*/
public class BookDaoImpl implements BookDao{ @Override
public List<Book> select(String sql, Object[] arr) {
Connection con=null;
PreparedStatement ps=null;
ResultSet rs=null;
try {
con=BaseDao.getCon();//第一步连接数据库
ps=con.prepareStatement(sql);//第二步:预编译
if(arr!=null){
for(int i=0;i<arr.length;i++){
ps.setObject(i+1, arr[i]);
}
}
//第四步执行sql
rs=ps.executeQuery();
List<Book> list=new ArrayList<Book>();
while(rs.next()){
Book book=new Book();
book.setBookid(rs.getInt("bookid"));
book.setBookname(rs.getString("bookname"));
book.setPrice(rs.getDouble("price"));
book.setAuthor(rs.getString("author"));
book.setPic(rs.getString("pic"));
book.setPublish(rs.getString("publish")); list.add(book);
}
return list;
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}finally{
//关闭资源,避免出现异常
BaseDao.close(con, ps, rs);
} return null;
} @Override
public Book getBook(Integer id) {
Connection con=null;
PreparedStatement ps=null;
ResultSet rs=null;
try {
con=BaseDao.getCon();//第一步连接数据库
String sql="select * from book where bookid = ? ";
ps=con.prepareStatement(sql);//第二步:预编译
ps.setInt(1, id); //第四步执行sql
rs=ps.executeQuery();
while(rs.next()){
Book books=new Book();
books.setBookid(rs.getInt("bookid"));
books.setBookname(rs.getString("bookname"));
books.setPrice(rs.getDouble("price"));
books.setAuthor(rs.getString("author"));
books.setPic(rs.getString("pic"));
books.setPublish(rs.getString("publish")); return books;
}
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}finally{
//关闭资源,避免出现异常
BaseDao.close(con, ps, rs);
} return null;
} }

7:写好dao层(数据交互层),就可以写service层(业务逻辑层),写业务逻辑层service层,也是使用先创建接口再实现接口的方法

 package com.bie.service;

 import java.util.List;

 import com.bie.po.Book;

 /**
* @author BieHongLi
* @version 创建时间:2017年2月27日 上午10:13:38
*
*/
public interface BookService { /***
* 图书信息查询的方法
* @return
*/
public List<Book> select(Book book); /***
* 根据id进行查询
* @param id
* @return
*/
public Book getBook(Book book);
}
 package com.bie.service.impl;

 import java.util.ArrayList;
import java.util.List; import com.bie.dao.BookDao;
import com.bie.dao.impl.BookDaoImpl;
import com.bie.po.Book;
import com.bie.service.BookService; /**
* @author BieHongLi
* @version 创建时间:2017年2月27日 上午10:13:52
*
*/
public class BookServiceImpl implements BookService{ private BookDao dao=new BookDaoImpl(); public List<Book> select(Book book){
//String sql="select * from book ";
StringBuilder sql=new StringBuilder("select * from book where 1=1 ");
//sql语句
List<Object> list=new ArrayList<Object>();
if(book!=null){ if(book.getBookid()!=null && book.getBookid()!=0){
sql.append(" and bookid=? ");
list.add(book.getBookid());
}
/*list.add(book.getBookname());
list.add(book.getPrice());
list.add(book.getAuthor());
list.add(book.getPic());
list.add(book.getPublish());*/
} return dao.select(sql.toString(), list.toArray());
} @Override
public Book getBook(Book book) {
if(book.getBookid()!=null && book.getBookid()!=0){
return dao.getBook(book.getBookid());
}
return null;
} }

8:最后按照正常开发的话就是servlet层,但是这里将servlet层的代码写到了jsp里面。所以下面jsp页面才是大戏

  先创建一个book.jsp页面,用于显示从数据库查询到的图书数据

 <%@page import="java.util.List"%>
<%@page import="com.bie.service.impl.BookServiceImpl"%>
<%@page import="com.bie.po.Book"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>图书列表的页面</title>
</head>
<body>
<%
//图书的实体类创建一个对象
Book book=new Book();
//图书的业务逻辑层层
BookServiceImpl service=new BookServiceImpl();
List<Book> list=service.select(book);
%>
<div style="text-align:right;font-size:36px;">
<a href="docart.jsp">我的购物车</a>
</div>
<table align="center" width="100%">
<tr>
<th>编号</th>
<th>书名</th>
<th>价格</th>
<th>作者</th>
<th>封皮</th>
<th>出版社</th>
</tr>
<%
for(Book b:list){
%>
<tr align="center">
<td><%=b.getBookid() %></td>
<td><a href="dobook.jsp?id=<%=b.getBookid()%>"><%=b.getBookname() %></a></td>
<td><%=b.getPrice() %></td>
<td><%=b.getAuthor() %></td>
<td><%=b.getPic() %></td>
<td><%=b.getPublish() %></td>
</tr>
<%} %>
</table> </body>
</html>

9:当图书显示出来之后就可以根据图书编号查看图书详情了,接着写dobook.jsp页面和detail.jsp页面,这个显示图书的详细的信息的页面

 <%@page import="com.bie.service.impl.BookServiceImpl"%>
<%@page import="com.bie.service.BookService"%>
<%@page import="com.bie.po.Book"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>处理图书详细信息的页面</title>
</head>
<body>
<%
Book book=new Book();
String sid=request.getParameter("id");
Integer id=Integer.parseInt(sid);
BookService service=new BookServiceImpl();
book.setBookid(id);
Book books=service.getBook(book); session.setAttribute("book", books);
response.sendRedirect("detail.jsp");
%>
</body>
</html>
 <%@page import="com.bie.po.Book"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>图书详细信息的页面</title>
</head>
<body>
<%
Book book=(Book)session.getAttribute("book");
%>
<div style="text-align:right;font-size:36px;"> <a href="docart.jsp">我的购物车</a>
</div>
<table align="center" cellpadding="20" cellspacing="20">
<tr>
<td>图书编号</td>
<td>图书名称</td>
<td>图书价格</td>
<td>图书作者</td>
<td>图书封皮</td>
<td>图书出版社</td>
</tr>
<tr>
<td><%=book.getBookid() %></td>
<td><%=book.getBookname() %></td>
<td><%=book.getPrice() %></td>
<td><%=book.getAuthor() %></td>
<td><img src="data:images/<%=book.getPic() %>"></td>
<td><%=book.getPublish() %></td>
</tr>
<tr>
<td colspan="2"></td>
<td><a href="cart.jsp">添加到购物车</a></td>
<td><a href="book.jsp">图书列表</a></td> <td colspan="2"></td>
</tr>
</table>
</body>
</html>

10:写好上面的detail.jsp然后就可以在detail.jsp页面点击添加到购物车,下面实现购物车的功能,也是这个实现购物车的核心部分,参考的话是重点看的内容,当然在写购物车之前还需要创建一个实体类CartItem.java,用于存放图书的信息和购买的数量

 package com.bie.po;

 /**
* @author BieHongLi
* @version 创建时间:2017年2月27日 上午10:40:53
* 购物项
*/
public class CartItem { private Book book;// 图书对象的成员变量
private Integer number;// 购买的数量; public Book getBook() {
return book;
} public void setBook(Book book) {
this.book = book;
} public Integer getNumber() {
return number;
} public void setNumber(Integer number) {
this.number = number;
} }
 <%@page import="java.util.HashMap"%>
<%@page import="com.bie.po.CartItem"%>
<%@page import="java.util.Map"%>
<%@page import="com.bie.po.Book"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>添加到购物车</title>
</head>
<body>
<%
//购物车功能
//1:首先考虑我购买的是哪一本书籍,这里可以使用id确认也可以使用session中取出哪一本书籍
Book book=(Book)session.getAttribute("book"); //2:考虑如何把书籍放到购物车中
//2.1:首先考虑是否有购物车,如果没有,则创建,如果有直接使用
//2.2:其次先将购物车从session中拿出来,不存在就创建。
Map<Integer,CartItem> cart=(Map<Integer,CartItem>)session.getAttribute("cart");
//如果没有购物车,那么创建,只有第一次访问才会操作
if(cart==null){
//new一个购物车
cart=new HashMap<>();
} //3:考虑如何把书籍放到购物车中
//3.1:第一考虑购物车中是否有该书籍,所以先从购物车中获取该书籍,如果为空,那么没有该书籍
CartItem item=(CartItem)cart.get(book.getBookid());
if(item==null){
//如果购物车中不存在该书籍,那么创建,且数量默认为1
item=new CartItem();
//将书籍放到购物车中
item.setBook(book);
//将书籍的默认数量为1
item.setNumber(1);
}else{
//如果购物车中以及有该书籍,那么数量加1
item.setNumber(item.getNumber()+1);
} //4:考虑如何把购物车项(即挑选的书籍是哪一个和书本的数量)放到购物车中
cart.put(book.getBookid(),item); //5:将购物车放到session中,方便后面取出来
session.setAttribute("cart", cart); response.sendRedirect("book.jsp");
%>
</body>
</html>

11:写完上面的就可以查看我的购物车了,在book.jsp页面和detail.jsp页面都有可以点击查看我的购物车的连接,然后就可以查看我的购物车,完成购物车功能。

 <%@page import="com.bie.po.CartItem"%>
<%@page import="java.util.Map"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>我的购物车的页面</title>
</head>
<body>
<table width="100%" align="center" border="1px">
<tr>
<th>书本编号</th>
<th>书本名称</th>
<th>书本单价</th>
<th>书本数量</th>
<th>书本小计</th>
</tr>
<%
//1:将添加到购物车里面的物品显示出来
Map<Integer,CartItem> map=(Map<Integer,CartItem>)session.getAttribute("cart");
//2:将购物车里面的内容遍历出来
double count=0;//显示出总价格
for(Map.Entry<Integer,CartItem> entry : map.entrySet()){
//计算出每一样的书籍一共花了多少钱
double price=entry.getValue().getBook().getPrice() * entry.getValue().getNumber();
//计算出一共花了多少钱
count=count+price;
%>
<tr align="center">
<td><%=entry.getKey() %></td>
<td><%=entry.getValue().getBook().getBookname() %></td>
<td><%=entry.getValue().getBook().getPrice() %></td>
<td><%=entry.getValue().getNumber() %></td>
<td><%=entry.getValue().getBook().getPrice() * entry.getValue().getNumber()%></td> </tr>
<%} %>
<tr>
<td colspan="4" align="right">价格总计</td>
<td><%=count %></td>
</tr>
</table>
<div style="text-align:center;font-size:36px;">
<a href="book.jsp">图书列表</a>
</div>
</body>
</html>

效果如下所示:

虽然简陋,没有完全实现完,还待改善,继续加油!!!

购物车的实现(jsp的session+Java的Map的结合)的更多相关文章

  1. [转]用 Jsp 的 Session 机制编写的购物车程序

    一.构建的商品类 //写一个Goods类,并定义商品的各个属性,返回商品属性的方法,以及商品对象进行比较的方法//Goods.java package com.viita.Shop; public c ...

  2. JSP中嵌入java代码方式以及指令

    JSP中嵌入java代码的三种方式: (1)声明变量或方法 :  <%! 声明; %> :慎重使用,因为此方法定义的是全局变量 (2)java片段(scriptlet):  <% j ...

  3. JSP编译为Java类

    JSP编译为Java类: 注意可以随便写import的内容:可以写类属性.方法.main函数.内部类:可以使用内部类: JSP: <%@ page language="java&quo ...

  4. JSP中的Java代码和内置对象

    一.JSP中的Java代码 (一)JSP页面中有三种方式嵌入java代码: 1.java的表达式 格式:<%= java表达式 %> 2.java的语句 格式:<% java语句&g ...

  5. 【JSP】JSP中的Java脚本

    前言 现代Web开发中,在JSP中嵌入Java脚本不是推荐的做法,因为这样 不利于代码的维护.有很多好的,替代的方法避免在JSP中写Java脚本.本文仅做为JSP体系技术的一个了解.     类成员定 ...

  6. jsp的session完成登陆功能

    login.jsp: <%@ page language="java" import="java.util.*" contentType="te ...

  7. 如何在 js 代码中使用 jsp 标签或 Java 代码

    JSP 标签还是很方便的,比如 Struts.Spring 等提供给我们的 JSP 标签,可以用它们来获取变量或进行一些计算.比如 struts2 的 <s:url value="/a ...

  8. 11 jsp脚本调用java代码

    大多数情况下, jsp 文档的大部分由静态文本(html)构成, 为处理该页面而创建的 servlet 只是将它们原封不动的传递给客户端, 原封不动的传送给客户端有两个小例外: 1. 如果想传送 &l ...

  9. 严重: Servlet.service() for servlet [jsp] threw exception java.lang.NullPointerException

    五月 04, 2018 11:53:24 上午 org.apache.catalina.core.ApplicationDispatcher invoke 严重: Servlet.service() ...

随机推荐

  1. Linux 命令详解(九)轻易删除OpenSSL 的后果

    警告自己,不要轻易的去删除系统的软件 1.composer自动更新出现错误 www@TinywanAliYun:~/web/go-study-line$ composer self-update Ke ...

  2. centos7 memcached+magent+keepalived集群

    111,222均部署keepalived,magent,memcached keepalived 111为主机,222为备机 其中,111上magent以本地memcache为主,222为备用 222 ...

  3. currentColor

    http://www.zhangxinxu.com/wordpress/2014/10/currentcolor-css3-powerful-css-keyword/

  4. 求幂运算、多项式乘法及Horner法则的应用

    一,两种不同的求幂运算 求解x^n(x 的 n 次方) ①使用递归,代码如下: private static long pow(int x, int n){ if(n == 0) return 1; ...

  5. Python HTML操作(HTMLParser)

    HTML操作是编程中很重要的一块,下面用Python3.x中的html.parser中的HTMLParser类来进行HTML的解析. HTMLParser类定义及常用方法 标准库中的定义 class ...

  6. Java EE 之Hibernate异常总结【1】org.hibernate.LazyInitializationException: could not initialize proxy - no Session

    字面意义就是不能被初始化. 简单理解就是因为,你使用了lazy=true,这样hibernate在从数据库中调数据的时候是不会把关联的对象查出来的,而是保存一个获取值得方法,在你使用getXXX()调 ...

  7. d2-admin中那些不错的技巧

    d2-admin基于vue-cli3 路由相关 刷新路由,参照官方  组件内的守卫 但是搞不明白为何加了句 render:h => h() { path: 'refresh', name: 'r ...

  8. Broadcast的类型

    两种发送方法 1.无序广播 对于多个接收者来说是完全异步的,通常每个接收者都无需等待即可以接收到广播,接收者相互之间不会有影响.对于这种广播,接收者无法终止广播,即无法阻止其他接收者的 接收动作. 消 ...

  9. 重新看halcon模板匹配

    工业中模板匹配有很多需求. 代码如下: read_image (Image, 'J:/测试图片/test1/1.bmp') get_image_size (Image, Width, Height) ...

  10. js数组的操作push,pop,shift,unshift

    push(args)可以每次压入多个元素,并返回更新后的数组长度. var oldArr=[1,2,3]; alert(oldArr.push(4,[5,6]))–>5(这里只会将[5,6]当做 ...