java项目干货(SpringBoot+Mysql)(三)

第三个项目:HMS(宾馆管理系统)

一.在使用REPLACE可以同时实现INSERT和UPDATE的功能,不过有以下需要注意的地方

 

REPLACE=INSERT+UPDATE(有点像)

 

关于REPLACE和INSERT的区别,REPLACE要求主键只能够有一条

根据应用情况可以使用replace 语句代替insert/update语句。例如:如果一个表在一个字段上建立了唯一索引,当向这个表中使用已经存在的键值插入一条记录,将会抛出一个主键冲突的错误。如果我们想用新记录的值来覆盖原来的记录值时,就可以使用REPLACE语句。

         使用REPLACE插入记录时,如果记录不重复(或往表里插新记录),REPLACE功能与INSERT一样,如果存在重复记录,REPLACE就使用新记录的值来替换原来的记录值。使用REPLACE的最大好处就是可以将DELETE和INSERT合二为一,形成一个原子操作。这样就可以不必考虑同时使用DELETE和INSERT时添加事务等复杂操作了。

       在使用REPLACE时,表中必须有唯一有一个PRIMARY KEY或UNIQUE索引,否则,使用一个REPLACE语句没有意义。

 

      注意:UPDATE和REPLACE的区别:

      1)UPDATE在没有匹配记录时什么都不做,而REPLACE在有重复记录时更新,在没有重复记录时插入。

      2)UPDATE可以选择性地更新记录的一部分字段。而REPLACE在发现有重复记录时就将这条记录彻底删除,再插入新的记录。也就是说,将所有的字段都更新了。

 

还有一点,如果表的字段中比较多的话,更新操作就最好使用UPDATE,精确的更新,如果使用REPLACE来更新的话,会将原先的记录删除,全部的字段更新,比较影响性能,还有,使用REPLACE的时候,需要前端传原先的全部数据(那前端该怎么获取原先的全部数据呢),所以还是需要根据实际情况来操作,

 

综上所述,对于选择使用REPLACE或UPDATE进行更新操作的建议:

  1. 如果字段比较多,使用REPLACE

  2. 如果数据更新的时候,非主键的其他属性需要全部更新的话,可以考虑使用REPLACE

  3. 如果数据更新的时候,主键也需要更新,使用REPLACE

  4. 实际上,更新操作的时候,其实还是主要是用UPDATE,因为使用REPLACE实现更新操作有一个致命的缺点:如果不想出现脏数据,那么更新时需要全部未修改的字段的原始数据,否则更新的时候,会导致无需修改的属性全部为NULL,部分数据将会被擦除,造成脏数据

 

 

其实REPLACE看起来像是万金油,但是其实使用的时候需要特别的注意,一不小心就有可能造成脏数据,所以使用的时候需要格外注意,能使用UPDATE的时候就尽量使用UPDATE,但是使用INSERT和REPLACE的话其实没有需要特别注意的地方

 

 

二.数据库中的一张表是否需要设置主键:看业务需求

  1. 如果涉及到了多表联合的时候,那每一张表都需要主键

  2. 如果只是简单的单表操作,每条数据可以重复,那么就不一定需要主键

 

三.Mybatis使用注解实现动态SQL

 

脚本实现

/**

* description:添加客房类型

*/

@Insert("<script>"

        + "UPDATE room_type "

        + "SET "

        + "<if test=\"type!=null and type!=\'\' \"> "

        + "type=#{type}, "

        + "</if> "

        + "<if test=\"price!=null\"> "

        + "price=#{price} "

        + "</if> "

        + "WHERE code=#{code} "

        + "</script> ")

boolean updateRoomType(RoomType roomType);

 

 

使用@SelectProvider、@InsertProvider、@UpdateProvider、@DeleteProvider

结构化实现SQL

但是这种自动生成的SQL和HIBERNATE一样,在实现一些复杂语句的SQL时会束手无策。所以需要根据现实场景,来考虑使用哪一种动态SQL

 

四.前后端时间戳传递机制

 

Long beginTime = MyNumberTranformUtil.getLong(dataCenterService.

        getParamValueFromParamOfRequestParamJsonByParamName("beginTime"));

Long endTime = MyNumberTranformUtil.getLong(dataCenterService.

        getParamValueFromParamOfRequestParamJsonByParamName("endTime"));

Date partBeginTime = null;

Date partEndTime = null;

if (beginTime != null) {

    partBeginTime = new Date(beginTime.longValue());

}

if (endTime != null) {

    partEndTime = new Date(endTime.longValue());

}

 

五.分页信息的传递机制

 

Integer pageNum = MyNumberTranformUtil.getInteger(dataCenterService.

        getParamValueFromParamOfRequestParamJsonByParamName("pageNum"));

Integer pageSize = MyNumberTranformUtil.getInteger(dataCenterService.

        getParamValueFromParamOfRequestParamJsonByParamName("pageSize"));

 

//检查分页信息

if (CheckVariableUtil.integerParamLessZero(pageNum) || CheckVariableUtil.integerParamLessZero(pageSize)

) {

    ExceptionUtil.setFailureMsgAndThrow(ReasonOfFailure.PAGEINFO_ERROR);

    return;

}

 

六.进行模糊查询的时候,最好将查询条件封装成一个类,使用JSON传递给后端,这样后端将会比较方便

 

 

七.尽量不要使用多层if-else嵌套

 

原代码,使用了多次的ifelse嵌套

//检查房间号是否为空

if (MyCheckUtil.isStringLegal(roomCode)) {

    //检查客房信息是否存在

    if (roomManagementDao.isRoomInfoExisted(roomCode)) {

 

        //检查客房是否已预订

 

        //检查客房是否已入住

 

        dataCenterService.setData("roomCode",roomCode);

    } else {

        ExceptionUtil.setFailureMsgAndThrow(ReasonOfFailure.ROOM_IS_NOT_EXIST);

        return;

    }

} else {

    ExceptionUtil.setFailureMsgAndThrow(ReasonOfFailure.ROOMCODE_IS_NULL);

    return;

}

 

八.检查参数合法性工具类中,非法返回True,这样就可以避免使用的时候多做一次取反运算

 

 

 

 

 

 

 

 

 

 

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值