第15天 web练习和分页技术

复习day14内容:

学习新技术的思路?

分析功能的思路?

使用queryRunner操作数据库的步骤?

ResultSetHandler接口常用实现类(三个重点)?

今日任务

  1. 用户的联系人增删改查
  2. 联系人的条件查询、
  3. 分页技术实现
  1. 案例—添加联系人

    1. 画图分析

    添加联系人功能:

    回顾联系人管理系统需求:

    1)使用添加联系人功能,必须要用户登录(session中必须要有loginUser),如果,没有登陆,让用户返回登陆页面。

    2)不同用户,可以有同样的联系人,同一个用户,联系人不能重复

    3)联系人不重复的情况下,数据库添加一条联系人的记录

    画图分析:

    1. 代码实现

    Jsp:

    Servlet代码:

    package cn.itcast.web;

    import java.io.IOException;

    import java.lang.reflect.InvocationTargetException;

    import javax.servlet.ServletException;

    import javax.servlet.http.HttpServlet;

    import javax.servlet.http.HttpServletRequest;

    import javax.servlet.http.HttpServletResponse;

    import org.apache.commons.beanutils.BeanUtils;

    import cn.itcast.domain.Contact;

    import cn.itcast.domain.User;

    import cn.itcast.service.ContactService;

    import cn.itcast.service.impl.ContactServiceImpl;

    public class AddContactServlet extends HttpServlet {

    public void doGet(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    request.setCharacterEncoding("utf-8");

    //第一步:校验登录

    User loginUser = (User)request.getSession().getAttribute("loginUser");

    if(loginUser == null){

    response.sendRedirect(request.getContextPath()+"/login.jsp");

    return;

    }

    //第二步:封装数据

    Contact con = new Contact();

    try {

    BeanUtils.populate(con, request.getParameterMap());

    } catch (Exception e) {

    //抓取异常的时候,根据需求去抓,不同的异常,不同处理

    e.printStackTrace();

    }

    //单独封装了u_id数据,这个数据是,表示当前联系人是哪个用户的

    con.setU_id(loginUser.getId());

    //第三步:调用service,添加联系人

    ContactService contactService = new ContactServiceImpl();

    int info = contactService.addContact(con);

    //第四步:根据返回值,处理

    if(info == 1){

    //添加成功,请求一个Servlet,获取所有当前用户的联系人数据

    //response.sendRedirect(request.getContextPath()+"/welcome.jsp");

    response.sendRedirect(request.getContextPath()+"/findAllContact");

    return;

    }else if(info == -1){

    //联系人重复

    request.setAttribute("msg", "联系人重复");

    request.getRequestDispatcher("/addContect.jsp").forward(request, response);

    return;

    }else{

    //服务器忙,请稍候再

    request.setAttribute("msg", "服务器忙,请稍候再试");

    request.getRequestDispatcher("/addContect.jsp").forward(request, response);

    return;

    }

    }

    public void doPost(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    doGet(request, response);

    }

    }

    Service代码:

    接口:

    /**

    * 添加联系人方法

    * @param con

    * @return

    */

    int addContact(Contact con);

    实现类:

    private ContactDao contactDao = new ContactDaoImpl();

    @Override

    public int addContact(Contact con) {

    //查询数据库,联系人是否重复

    int info = contactDao.findContactByNameAndUid(con.getName(),con.getU_id());

    if(info == 1){

    //不重复,可以添加

    contactDao.addContact(con);

    return 1;

    }else{

    return -1;

    }

    }

    Dao代码:

    接口:

    /**

    * 根据用户id和联系人名称查询数据的方法

    * @param name

    * @param u_id

    * @return

    */

    int findContactByNameAndUid(String name, int u_id);

    /**

    * 添加联系人的方法

    * @param con

    */

    void addContact(Contact con);

    实现类:

    private QueryRunner qr = new QueryRunner(JDBCUtils.getDataSource());

    @Override

    public int findContactByNameAndUid(String name, int u_id) {

    String sql = "select * from contact where name = ? and u_id = ?";

    try {

    Contact contact = qr.query(sql, new BeanHandler<Contact>(Contact.class), name,u_id);

    if(contact == null){

    return 1;

    }else{

    return -1;

    }

    } catch (SQLException e) {

    //e.printStackTrace();打印堆栈信息,包括了错误信息。后期需要写入日志,数据一定要保留起来

    e.printStackTrace();

    throw new RuntimeException("查询联系人异常");

    }

    }

    @Override

    public void addContact(Contact con) {

    String sql = "insert into contact values(null,?,?,?,?,?)";

    try {

    qr.update(sql,con.getU_id() ,con.getName(),con.getSex(),con.getAddress(),con.getTel());

    } catch (SQLException e) {

    e.printStackTrace();

    throw new RuntimeException("添加联系人异常");

    }

    }

  2. 案例—查询当前用户的全部联系人实现

    查询全部联系人(当前登录用户的全部联系人)

    查询全部联系人功能什么时候被调用?

    1. 用户登录之后,查询全部联系人功能被调用

      获取到所有联系人数据之后将数据转发到welcome.jsp,显示所有联系人的数据。

    2. 添加联系人完成之后,查询全部联系人功能被调用

      添加联系人完成之后,要看到添加的数据。

      需要重新获取全部联系人数据,转发welcome.jsp页显示

    1. 修改联系人完成之后,查询全部联系人功能被调用

      修改联系人完成之后,看到修改后的数据。

    1. 删除联系人完成之后,查询全部联系人功能被调用

      同上

    1. 画图分析

    1. 代码实现

    loginServlet:

    findAllContactServlet:

    package cn.itcast.web;

    import java.io.IOException;

    import java.util.List;

    import javax.servlet.ServletException;

    import javax.servlet.http.HttpServlet;

    import javax.servlet.http.HttpServletRequest;

    import javax.servlet.http.HttpServletResponse;

    import cn.itcast.domain.Contact;

    import cn.itcast.domain.User;

    import cn.itcast.service.ContactService;

    import cn.itcast.service.impl.ContactServiceImpl;

    public class FindAllContactServlet extends HttpServlet {

    public void doGet(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    //校验登录

    User loginUser = (User)request.getSession().getAttribute("loginUser");

    if(loginUser == null){

    response.sendRedirect(request.getContextPath()+"/login.jsp");

    return;

    }

    //获取数据(u_id)

    int u_id = loginUser.getId();

    //调用service方法

    ContactService contactService = new ContactServiceImpl();

    List<Contact> data = contactService.findAll(u_id);

    //将数据存入request,转发到welcome.jsp页面

    request.setAttribute("data", data);

    request.getRequestDispatcher("/welcome.jsp").forward(request, response);

    }

    public void doPost(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    doGet(request, response);

    }

    }

    Service:

    接口:

    /**

    * 查询指定用户的所有联系人

    * @param u_id

    * @return

    */

    List<Contact> findAll(int u_id);

    实现类:

    public List<Contact> findAll(int u_id) {

    return contactDao.findAll(u_id);

    }

    Dao:

    接口:

    /**

    * 获取指定用户联系人的方法

    * @param u_id

    * @return

    */

    List<Contact> findAll(int u_id);

    实现类:

    public List<Contact> findAll(int u_id) {

    String sql = "select * from contact where u_id = ?";

    try {

    return qr.query(sql, new BeanListHandler<Contact>(Contact.class), u_id);

    } catch (SQLException e) {

    e.printStackTrace();

    throw new RuntimeException("获取指定的用户所有联系人失败");

    }

    }

    添加联系人servlet修改:

  3. 案例--修改联系人分析(分两次请求)

    效果是什么?

    1. 点击修改连接(第一次请求),在页面(upadateContact.jsp)上看到原来的数据
    2. 点击修改联系人按钮提交数据(第二次请求)
    3. 在welcome.jsp页面看到修改后的数据,通过调用findAllContactServlet,servlet获取所有的联系人,看到修改后的结果
    1. 画图分析

    修改联系人流程一:

    修改联系人流程二:

    1. 代码实现

    修改welcome.jsp页面:

    显示了当前联系人数据的id:

    修改updateContact.jsp页面:

    FindContactByIdServlet:

    package cn.itcast.web;

    import java.io.IOException;

    import javax.servlet.ServletException;

    import javax.servlet.http.HttpServlet;

    import javax.servlet.http.HttpServletRequest;

    import javax.servlet.http.HttpServletResponse;

    import cn.itcast.domain.Contact;

    import cn.itcast.domain.User;

    import cn.itcast.service.ContactService;

    import cn.itcast.service.impl.ContactServiceImpl;

    public class FindByIDServlet extends HttpServlet {

    public void doGet(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    //校验登录

    User loginUser = (User)request.getSession().getAttribute("loginUser");

    if(loginUser == null){

    response.sendRedirect(request.getContextPath()+"/login.jsp");

    return;

    }

    //获取参数联系人id

    String parameter = request.getParameter("id");

    int id = Integer.parseInt(parameter);

    //调用service方法获取数据

    ContactService contactService = new ContactServiceImpl();

    Contact con = contactService.findById(id);

    //将数据转发到updateContact.jsp页面

    request.setAttribute("con", con);

    request.getRequestDispatcher("/updateContact.jsp").forward(request, response);

    }

    public void doPost(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    doGet(request, response);

    }

    }

    Service:

    接口:

    /**

    * 根据id查询数据

    * @param id

    * @return

    */

    Contact findById(int id);

    实现类:

    public Contact findById(int id) {

    return contactDao.findById(id);

    }

    Dao:

    接口:

    /**

    * 根据id查询数据

    * @param id

    * @return

    */

    Contact findById(int id);

    实现类:

    public Contact findById(int id) {

    String sql = "select * from contact where id = ?";

    try {

    return qr.query(sql, new BeanHandler<Contact>(Contact.class), id);

    } catch (SQLException e) {

    e.printStackTrace();

    throw new RuntimeException("获取指定的联系人数据失败");

    }

    }

    修改操作UpdateContactServlet:

    package cn.itcast.web;

    import java.io.IOException;

    import java.lang.reflect.InvocationTargetException;

    import javax.servlet.ServletException;

    import javax.servlet.http.HttpServlet;

    import javax.servlet.http.HttpServletRequest;

    import javax.servlet.http.HttpServletResponse;

    import org.apache.commons.beanutils.BeanUtils;

    import cn.itcast.domain.Contact;

    import cn.itcast.domain.User;

    import cn.itcast.service.ContactService;

    import cn.itcast.service.impl.ContactServiceImpl;

    public class UpdateContactServlet extends HttpServlet {

    public void doGet(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    request.setCharacterEncoding("utf-8");

    //校验登录

    User loginUser = (User)request.getSession().getAttribute("loginUser");

    if(loginUser == null){

    response.sendRedirect(request.getContextPath()+"/login.jsp");

    return;

    }

    //封装数据

    Contact con = new Contact();

    try {

    BeanUtils.populate(con, request.getParameterMap());

    } catch (Exception e) {

    e.printStackTrace();

    }

    //调用service

    ContactService contactService = new ContactServiceImpl();

    contactService.updateContact(con);

    //调用findAllContact查看效果

    response.sendRedirect(request.getContextPath()+"/findAllContact");

    }

    public void doPost(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    doGet(request, response);

    }

    }

    Service:

    接口:

    /**

    * 修改联系人

    * @param con

    */

    void updateContact(Contact con);

    实现类:

    public void updateContact(Contact con) {

    contactDao.updateContact(con);

    }

    Dao:

    接口:

    /**

    * 修噶联系人

    * @param con

    */

    void updateContact(Contact con);

    实现类:

    public void updateContact(Contact con) {

    String sql = "update contact set name = ? , sex = ? , tel = ? , address = ? where id = ?";

    try {

    qr.update(sql, con.getName(),con.getSex(),con.getTel(),con.getAddress(),con.getId());

    } catch (SQLException e) {

    e.printStackTrace();

    throw new RuntimeException("修改指定的联系人数据失败");

    }

    }

  4. 案例--删除联系人实现

    注意:一般来说,公司在做删除功能时候,不是真实的物理删除(执行delete语句),只会设置标记,标记这条数据失效。

    为什么不删除数据?

    数据是公司最宝贵的财富,根据数据可以做大数据分析

    例子:根据订单的下单时间,下单金额,订单的地址,订单商品的信息——这个人什么时候发工资,薪资水平,去哪里偷东西,偷哪些贵重物品

    智能推荐:确定推荐的时间,你需要的品牌,你附近的商家

    传智播客:名字,上海地址,老家地址,专业,学历,年龄,来源,有无工作经验,是否在校

    老家地址:下一个分校应该在哪里

    专业:分析出,当前培训的市场扩张程度

    学历:给就业部老师,指定相应的就业方案

    年龄:招生的部门,主要的招生的年龄段

    来源:老学员介绍,广告,优酷视频看到的,通过百度查询——下一个推广的主要方向

    是否在校:第一,是否要开辟高校市场。第二,就业指导老师,准备相应的就业方案

    功能的效果:

    1. 画图分析

    注意:相关money的功能(加 减 乘 除 ,显示),相关用户的功能,一定要把用户当作小白,把用户的体验,能做多好就做多好

    1. 代码实现

    Welcome.jsp修改:

    Servlet代码:

    package cn.itcast.web;

    import java.io.IOException;

    import javax.servlet.ServletException;

    import javax.servlet.http.HttpServlet;

    import javax.servlet.http.HttpServletRequest;

    import javax.servlet.http.HttpServletResponse;

    import cn.itcast.domain.User;

    import cn.itcast.service.ContactService;

    import cn.itcast.service.impl.ContactServiceImpl;

    public class DeleteServlet extends HttpServlet {

    public void doGet(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    //校验登录

    User loginUser = (User)request.getSession().getAttribute("loginUser");

    if(loginUser == null){

    response.sendRedirect(request.getContextPath()+"/login.jsp");

    return;

    }

    //获取数据 id

    int id = Integer.parseInt(request.getParameter("id"));

    //调用service方法删除数据

    ContactService contactService = new ContactServiceImpl();

    contactService.delete(id);

    //调用findAllContact查看删除效果

    response.sendRedirect(request.getContextPath()+"/findAllContact");

    }

    public void doPost(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    doGet(request, response);

    }

    }

    Service代码:

    接口:

    /**

    * 删除操作

    * @param id

    */

    void delete(int id);

    实现类:

    public void delete(int id) {

    contactDao.delete(id);

    }

    Dao代码:

    接口:

    /**删除操作

    * @param id

    */

    void delete(int id);

    实现类:

    public void delete(int id) {

    String sql = "delete from contact where id = ?";

    try {

    qr.update(sql, id);

    } catch (SQLException e) {

    e.printStackTrace();

    throw new RuntimeException("删除指定的联系人数据失败");

    }

    }

  5. 案例--根据条件查询联系人实现

    页面分析:

    条件查询sql语句实现:

    select * from contact where key like '%用户输入的查询内容(value)%';

    要查询的数据库字段:是页面下拉框选择的内容(key)

    用户输入的查询条件:是input输入框中用户输入的内容(value)

    1. 画图分析

    1. 代码实现

    Servlet:

    package cn.itcast.web;

    import java.io.IOException;

    import java.util.List;

    import javax.servlet.ServletException;

    import javax.servlet.http.HttpServlet;

    import javax.servlet.http.HttpServletRequest;

    import javax.servlet.http.HttpServletResponse;

    import cn.itcast.domain.Contact;

    import cn.itcast.domain.User;

    import cn.itcast.service.ContactService;

    import cn.itcast.service.impl.ContactServiceImpl;

    public class FindByKeyServlet extends HttpServlet {

    public void doGet(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    request.setCharacterEncoding("utf-8");

    //校验登录

    User loginUser = (User)request.getSession().getAttribute("loginUser");

    if(loginUser == null){

    response.sendRedirect(request.getContextPath()+"/login.jsp");

    return;

    }

    //获取数据(key :查询字段name tel address || value :用户输入的模糊查询的条件 || u_id 当前用户)

    String key = request.getParameter("key");

    String value = request.getParameter("value");

    int u_id = loginUser.getId();

    //调用service方法获取数据

    ContactService contactService = new ContactServiceImpl();

    List<Contact> data = contactService.findByKey(key ,value, u_id);

    //将数据转发到welcome.jsp页面

    request.setAttribute("data", data);

    request.getRequestDispatcher("/welcome.jsp").forward(request, response);

    }

    public void doPost(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    doGet(request, response);

    }

    }

    Service:

    接口:

    /**

    * 条件查询方法

    * @param key :查询字段

    * @param value :用户输入的查询内容

    * @param u_id :当前用户id

    * @return

    */

    List<Contact> findByKey(String key, String value, int u_id);

    实现类:

    public List<Contact> findByKey(String key, String value, int u_id) {

    return contactDao.findByKey(key,value,u_id);

    }

    Dao:

    接口:

    /**

    * 条件查询的方法

    * @param key

    * @param value

    * @param u_id

    * @return

    */

    List<Contact> findByKey(String key, String value, int u_id);

    实现类:

    public List<Contact> findByKey(String key, String value, int u_id) {

    String sql = "select * from contact where "+ key +" like ? and u_id = ?";

    try {

    return qr.query(sql, new BeanListHandler<Contact>(Contact.class), "%"+value+"%",u_id);

    } catch (SQLException e) {

    e.printStackTrace();

    throw new RuntimeException("条件查询联系人数据失败");

    }

    }

  6. 案例--大结果集分页实现

    1. 分页介绍

    大结果集: 一次性,从,数据库中,获取,大量(上万的数量)的,数据。

    分页: 将数据分批次展示给用户

    大结果集分页的技术需求(它因为什么原因诞生的):

    1)物理计算机的瓶颈(内存瓶颈),如果给一个只有1千万数据内存的机器,给了2千万数据。数据溢出。

    一个水桶,只能装1L水,现在我给他灌2L的水,肯定有1L的水溢出,浪费了。

    2)封装数据到对象,过程十分慢长(这个漫长是数据量太大),这样的用户体验非常差

    假设:有一个超级机器,内存无限的,1个数据要1秒钟,1千万数据,一千万秒。

    补充:用户等待一个功能响应,一般只会等多久?

    跟据不同的信息内容,不同。

    查看商品,用户不喜欢等待,而且有代替方案,一般5到15秒。

    支付,等30秒左右

    抢票,不要动我的手机,我正在抢票,等待时间3分钟。

    分页技术的实现:数据库实现,内存实现(redis数据库)

    数据库实现:通过关键字,限制一次性从数据库中获取数据的起始位置和长度。

    起始位置:数据从哪一行开始获取。

    长度:一次性获取数据的量。

    MySql关键字:limit

    Select * from contact where key =? limit ?,?

    第一个问号:起始位置

    第二个问号:长度

    代码测试:

    //测试数据库分页

    //测试数据库分页

    @Test

    public void test1(){

    QueryRunner qr = new QueryRunner(JDBCUtils.getDataSource());

    //第一个?:起始位置第二个?:长度

    String sql = "select * from contact limit ?,?";

    try {

    List<Contact> list = qr.query(sql, new BeanListHandler<Contact>(Contact.class), 10,10);

    System.out.println(list);

    } catch (SQLException e) {

    e.printStackTrace();

    }

    }

    效果截图:

    内存分页实现:

    先将数据从数据库中获取出来,将数据存入缓存(list集合)中,将数据分批次展示给用户。

    缓存:内存中开辟的空间,专门用来存储数据的

    代码测试:

    //测试内存分页

    @Test

    public void test2(){

    QueryRunner qr = new QueryRunner(JDBCUtils.getDataSource());

    //第一个?:起始位置第二个?:长度

    String sql = "select * from contact";

    try {

    List<Contact> list = qr.query(sql, new BeanListHandler<Contact>(Contact.class));

    //将list集合中的数据分批次展示给用户

    List<Contact> subList = list.subList(3, 6);

    System.out.println(subList);

    } catch (SQLException e) {

    e.printStackTrace();

    }

    }

    代码执行效果:

    1. 页面修改(功能展示)

    页面修改结果:

    分析——使用数据库分页技术实现分页效果,需要那些数据?

    1. 用户需要看到的数据的页码(pageNum)
    2. 当前联系人总数(total)
    3. 一页多少行(长度size)
    4. 尾页(end)
    5. 当前分页查询的结果(联系人数据data:List<Contact>)
    1. Page类(封装分页数据的对象)书写

    将复杂的数据,我们封装一个对象中,这个对象,我们取名字叫Page

    符合面向对象思想,封装。

    1. 画图分析

    1. 代码实现

    Servlet:

    package cn.itcast.web;

    import java.io.IOException;

    import javax.servlet.ServletException;

    import javax.servlet.http.HttpServlet;

    import javax.servlet.http.HttpServletRequest;

    import javax.servlet.http.HttpServletResponse;

    import cn.itcast.domain.Page;

    import cn.itcast.domain.User;

    import cn.itcast.service.ContactService;

    import cn.itcast.service.impl.ContactServiceImpl;

    public class QueryPageServlet extends HttpServlet {

    public void doGet(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    //校验登录

    User loginUser = (User)request.getSession().getAttribute("loginUser");

    if(loginUser == null){

    response.sendRedirect(request.getContextPath()+"/login.jsp");

    return;

    }

    //获取数据

    int pageNum = Integer.parseInt(request.getParameter("pageNum"));

    int u_id = loginUser.getId();

    //调用service方法获取数据

    ContactService contactService = new ContactServiceImpl();

    Page page = contactService.queryPage(u_id,pageNum);

    //将数据转发到welcome.jsp页面

    request.setAttribute("page", page);

    request.getRequestDispatcher("/welcome.jsp").forward(request, response);

    }

    public void doPost(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    doGet(request, response);

    }

    }

    Service:

    接口:

    /**

    * 分页查询的方法

    * @param u_id

    * @param pageNum

    * @return

    */

    Page queryPage(int u_id, int pageNum);

    实现类:

    public Page queryPage(int u_id, int pageNum) {

    //获取总记录数据

    int total = contactDao.count(u_id);

    //定义长度

    int size = 10;

    //计算尾页

    //total size end %

    //100 10 10 0

    //101 10 11 1

    int end = total % size == 0 ? (total / size) :(total / size)+1;

    //计算起始位置

    int startIndex = (pageNum - 1) * size;

    //获取联系人数据

    List<Contact> data = contactDao.queryPage(u_id ,startIndex,size);

    //封装数据到page对象

    Page page = new Page();

    page.setData(data);

    page.setEnd(end);

    page.setPageNum(pageNum);

    page.setSize(size);

    page.setTotal(total);

    //返回page

    return page;

    }

    Dao:

    接口:

    /**

    * 获取总记录数

    * @param u_id

    * @return

    */

    int count(int u_id);

    /**

    * 获取联系人数据

    * @param u_id

    * @param startIndex

    * @param size

    * @return

    */

    List<Contact> queryPage(int u_id, int startIndex, int size);

    实现类:

    public int count(int u_id) {

    String sql = "select count(*) from contact where u_id = ? ";

    //ScalarHandler:封装count avg max min 。。。。函数执行结果

    try {

    //Long:一般数据的总数,使用int 类型存不下的

    Long long1 = qr.query(sql, new ScalarHandler<Long>(), u_id);

    return long1.intValue();

    } catch (SQLException e) {

    e.printStackTrace();

    throw new RuntimeException("分页总数获取失败");

    }

    }

    @Override

    public List<Contact> queryPage(int u_id, int startIndex, int size) {

    String sql = "select * from contact where u_id = ? limit ?,?";

    try {

    return qr.query(sql, new BeanListHandler<Contact>(Contact.class), u_id,startIndex,size);

    } catch (SQLException e) {

    e.printStackTrace();

    throw new RuntimeException("分页联系人数据获取失败");

    }

    }

    loginServlet:

    Welcome.jsp修改:

  7. 案例—分页与条件查询组合实现(了解:内容)

    画图分析

    需求:将条件查询的结果,进行分页显示

    1. 页面修改

    1)要分页请求中,必须包含条件请求参数

    2)条件查询的请求中,必须包含分页请求的参数

    1. 组合查询servlet

    package cn.itcast.web;

    import java.io.IOException;

    import javax.servlet.ServletException;

    import javax.servlet.http.HttpServlet;

    import javax.servlet.http.HttpServletRequest;

    import javax.servlet.http.HttpServletResponse;

    import cn.itcast.domain.Page;

    import cn.itcast.domain.User;

    import cn.itcast.service.ContactService;

    import cn.itcast.service.impl.ContactServiceImpl;

    public class QueryPageServlet2 extends HttpServlet {

    public void doGet(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    // 校验登陆

    User loginUser = (User) request.getSession().getAttribute("loginUser");

    if (loginUser == null) {

    response.sendRedirect(request.getContextPath() + "/login.jsp");

    return;

    }

    // 获取数据

    String key = request.getParameter("key");

    String value = request.getParameter("value");

    // 处理中文乱码

    if(value == null){

    value = "";

    }

    value = new String(value.getBytes("iso-8859-1"), "utf-8");

    int pageNum = Integer.parseInt(request.getParameter("pageNum"));

    int u_id = loginUser.getId();

    // 调用service方法

    ContactService contactService = new ContactServiceImpl();

    Page page = contactService.queryPage2(key, value, pageNum, u_id);

    // 展示数据

    // 除了要将分页(page)数据保存到request对象

    // 注意:要将查询key和value都要保存到request对象

    request.setAttribute("page", page);

    request.setAttribute("key", key);

    request.setAttribute("value", value);

    request.getRequestDispatcher("/welcome.jsp").forward(request, response);

    }

    public void doPost(HttpServletRequest request, HttpServletResponse response)

    throws ServletException, IOException {

    // 处理中文乱码

    request.setCharacterEncoding("utf-8");

    // 校验登陆

    User loginUser = (User) request.getSession().getAttribute("loginUser");

    if (loginUser == null) {

    response.sendRedirect(request.getContextPath() + "/login.jsp");

    return;

    }

    // 获取数据

    String key = request.getParameter("key");

    String value = request.getParameter("value");

    int pageNum = Integer.parseInt(request.getParameter("pageNum"));

    int u_id = loginUser.getId();

    // 调用service方法

    ContactService contactService = new ContactServiceImpl();

    Page page = contactService.queryPage2(key, value, pageNum, u_id);

    // 展示数据

    // 除了要将分页(page)数据保存到request对象

    // 注意:要将查询key和value都要保存到request对象

    request.setAttribute("page", page);

    request.setAttribute("key", key);

    request.setAttribute("value", value);

    request.getRequestDispatcher("/welcome.jsp").forward(request, response);

    }

    }

    1. 组合查询service

    接口:

    /**

    * 条件查询和分页方法

    * @param key

    * @param value

    * @param pageNum

    * @param u_id

    * @return

    */

    Page queryPage2(String key, String value, int pageNum, int u_id);

    实现类:

    public Page queryPage2(String key, String value, int pageNum, int u_id) {

    // 获取总记录数

    int total = contactDao.count2(u_id,key,value);

    // 定义长度

    int size = 3;

    // 根据总记录数和长度,计算尾页

    // 不能直接做除法:

    条数据,应该有11页,但是除法运算,结果:10页

    int end = total % size == 0 ? (total / size) : (total / size) + 1;

    // 计算数据库查询的起始位置

    // 第一页:pageNum=1 ,1-1=0 0*size = 0

    // 第二页:pageNum=2 ,2-1=1 1*size = 10

    // 第三页:pageNum=3 ,3-1=2 2*size = 20

    int startIndex = (pageNum - 1) * size;

    // 获取联系人数据

    List<Contact> data = contactDao.queryPage2(u_id,key,value, startIndex, size);

    // 创建对象封装数据(page)

    Page p = new Page();

    p.setData(data);

    p.setEnd(end);

    p.setPageNum(pageNum);

    p.setSize(size);

    p.setTotal(total);

    // 返回page

    return p;

    }

    1. 组合查询dao

    接口:

    /**

    * 条件查询和分页——获取总记录数据

    * @param u_id

    * @param key

    * @param value

    * @return

    */

    int count2(int u_id, String key, String value);

    /**

    * 条件查询和分页——获取联系人数据

    * @param u_id

    * @param key

    * @param value

    * @param startIndex

    * @param size

    * @return

    */

    List<Contact> queryPage2(int u_id, String key, String value,

    int startIndex, int size);

    实现类:

    @Override

    public int count2(int u_id, String key, String value) {

    QueryRunner qr = new QueryRunner(JDBCUtils.getDataSource());

    String sql = "select count(*) from contact where u_id = ?";

    //思考:用户登录之后,默认查询当前用户全部联系人,key value 没有数据

    //所以,我们需要根据key和value的值,判断,应该生成什么样的sql语句

    //定义一个集合用来存储数据,这个集合中的数据,会根据判断,变化

    List<Object> list = new ArrayList<Object>();

    list.add(u_id);

    if(key !=null && !key.equals("")){

    //表示当前key是有数据

    //应该拼接上key和value值

    //思考:因为有判断存在,sql语句的参数,有时候是一个问号,有时是两个问号

    sql = sql + " and "+key+" like ?";

    list.add("%"+value+"%");

    }

    try {

    Long long1 = qr.query(sql, new ScalarHandler<Long>(),list.toArray());

    return long1.intValue();

    } catch (SQLException e) {

    e.printStackTrace();

    throw new RuntimeException("获取联系人总数失败");

    }

    }

    @Override

    public List<Contact> queryPage2(int u_id, String key, String value,

    int startIndex, int size) {

    QueryRunner qr = new QueryRunner(JDBCUtils.getDataSource());

    String sql = "select * from contact where u_id = ?";

    //在用户登录之后,默认查询所有数据,key和value是没有值得,sql语句需要根据key和value进行变化

    List<Object> list = new ArrayList<Object>();

    list.add(u_id);

    if(key !=null && !key.equals("")){

    sql = sql + " and "+key+" like ?";

    list.add("%"+value+"%");

    }

    sql = sql + " limit ?,?";

    list.add(startIndex);

    list.add(size);

    try {

    return qr.query(sql, new BeanListHandler<Contact>(Contact.class), list.toArray());

    } catch (SQLException e) {

    e.printStackTrace();

    throw new RuntimeException("获取联系人分页数据失败");

    }

    }

    1. 修改登录servlet

    作业:参考课堂笔记完成案例功能

    1. 完成添加功能(25点积分)
    2. 完成查询全部联系人的功能(25点积分)
    3. 完成修改联系人的功能(25点积分)
    4. 完成删除联系人的功能(25点积分)
    5. 完成条件查询联系人的功能(25点积分)
    6. 完成大结果集分页功能(25点积分)

    QQ:395793718

    电话:13651825024

Javaweb 第15天 web练习和分页技术的更多相关文章

  1. ] 解决myeclipse中新建javaweb工程,无法使用Web App Libraries问题

    ] 解决myeclipse中新建javaweb工程,无法使用Web App Libraries问题 标签: myeclipsejavawebWeb App Libraries 2013-10-16 1 ...

  2. 1、javaweb学习之配置文件web.xml

    今天这里主要讲述javaweb中的配置文件web.xml中的内容及其作用,都是基础部分,对于初学者需要好好掌握理解. 简单配置: <servlet>    <servlet-name ...

  3. JavaWeb基本概念及web服务器

    1.基本概念 1.1.前言 web开发: web,网页的意思,www.baidu.com 静态web html,css 提供给所有人看的数据始终不会发生变化! 动态web 淘宝,几乎是所有的网站: 提 ...

  4. JDBC 学习笔记(一)—— 基础知识 + 分页技术

    本文目录:  1.JDBC简介       2.使用JDBC的步骤——第一个JDBC程序       3.DriverManager ——加载数据库驱动       4.数据库URL ——标识数据库的 ...

  5. 关于Ajax无刷新分页技术的一些研究 c#

    关于Ajax无刷新分页技术的一些研究 c# 小弟新手,求大神有更好的解决方案,指教下~ 以前做项目,用过GridView的刷新分页,也用过EasyUI的封装好的分页技术,最近在老项目的基础上加新功能, ...

  6. Web端即时通讯技术盘点:短轮询、Comet、Websocket、SSE

    1. 前言 Web端即时通讯技术因受限于浏览器的设计限制,一直以来实现起来并不容易,主流的Web端即时通讯方案大致有4种:传统Ajax短轮询.Comet技术.WebSocket技术.SSE(Serve ...

  7. 新手入门:史上最全Web端即时通讯技术原理详解

    前言 有关IM(InstantMessaging)聊天应用(如:微信,QQ).消息推送技术(如:现今移动端APP标配的消息推送模块)等即时通讯应用场景下,大多数都是桌面应用程序或者native应用较为 ...

  8. Web端即时通讯技术原理详解

    前言 有关IM(InstantMessaging)聊天应用(如:微信,QQ).消息推送技术(如:现今移动端APP标配的消息推送模块)等即时通讯应用场景下,大多数都是桌面应用程序或者native应用较为 ...

  9. 改进Spring中的分页技术

    Spring中有一个PagedListHolder,能够实现分页. 但此类有几个缺点: 1. 使用此类的代码比較繁琐 2. 此类存放的数据源是全部的记录集,即对于记录数为1000条的数据,即使我们仅仅 ...

随机推荐

  1. headfirst设计模式(1)—策略模式

    什么是策略模式 策略模式定义了一系列的算法,并将每一个算法封装起来,而且使它们还可以相互替换.策略模式让算法独立于使用它的客户而独立变化(摘自百度百科) 关键字:算法封装,相互替换,独立变化 算法封装 ...

  2. [翻译]Webpack解惑

    本文译自Webpack - The Confusing Parts,原文需FQ. Webpack现在是React应用程序标配的模块打包器,我估计Angular2和其他框架的用户也在大规模使用.我第一次 ...

  3. C#调用百度地图API

    1.打开链接http://developer.baidu.com/map/jshome.htm这里有很多DEMO,或者你直接百度搜索"百度地图API",第一个就是.进入后有很多方向 ...

  4. [大山中学dp常练-4 Rounds]

    Round#1 2016.9.28 这次晚练十分sb 有点浪费时间 全是dp题 先说过程 3分钟草了第一题之后感觉好像有点水 然后翻了翻题目 看了看第一第四题两颗星 其他三颗星 然后一下子第二题题目太 ...

  5. python学习——DAY1

    日期:20170113 一.个人体会: 零基础学python,是艰辛的,需要付出和坚持. 关于流程图.我最开始画的是从上到下,再从左到右,画了很多重复的内容,单线程的流程图,看起来很容易理解,但是自己 ...

  6. vs 插件

    Visual Assist 代码提示 Indent Guides

  7. Freeplane中的自动边线颜色功能

    今天我将电脑上的Freeplane从1.3.11升级到了1.5.18.发现新版本已经没有了1.3.11中的菜单选项Format → “Automatic edge color”.搜索了一下才发现,该功 ...

  8. Vultr新加坡机房速度怎么样?值得购买吗?最新评测!

    2016年9月,Vultr vps开通了新加坡Singapore机房线路.与知名的竞争对手Digitalocean和Linode一样,新加坡机房对亚洲速度友好,是讨用户欢心的一个进步. 但是,vult ...

  9. C# Where

    判断一个字符串中是否包含字符串数组里的字符,恶意字符限制提交,一般人,包括最初的我,会这样写 public bool ValidateStr(string[] parms) { bool result ...

  10. ios开发设置不同字体

    最近项目开发中遇到需要设置指定字体的需求,研究了一下字体设置,最后附有我写的一个小demo,先来看一下效果: 开始上网搜了一下,普遍说到以下方法 for(NSString *fontfamilynam ...