1.判断字符串是否为空
StringUtils.isBlank()或者 StringUtils.isNotBlank()
2.判断数字是否为空
NumberUtils.isCreatable()
BigDecimalUtil.isZeroOrNull()
3.Integer和int区别
Integer 默认值是null,int默认值是0
如果定义某实体参数类型为Integer类型,ibatis 判断条件是 <if test="age != null">
如果定义某实体参数类型为int类型,ibatis判断条件是 <if test="age!=0">
如果实体不传递任何参数,Integer 默认是空。int默认是0
4.数据库设置默认值
当数据库设置默认值后,做新增操作后(在ibatis中的insert),数据库插入的不是默认值,只需要去掉该字段就可以。如果不去掉那么自己在插入前设置值
5.LocalDateTime使用
LocalDateTime为jdk1.8新特新 以前用date
LocalDateTime.now().plusDays(1).format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")); //当前时间加1天
LocalDateTime.now().plusYears(10).format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")); //给当前时间加10年
列子2:
DateTimeFormatter df = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
LocalDateTime currentTime = LocalDateTime.parse("2018-01-29 01:00:00",df);
currentTime = currentTime.plusDays(1);
当指定日期加一天
6.List中数据筛选以及排序
streams为jdk1.8新特性
筛选
使用jdk1.8特性排序
List<AirportCodeDTO> resultList = airportCodeDTOList.stream().filter(o -> o.getCityName().contains("海南")).collect(Collectors.toList()); --筛选出城市名称包含海南的关键字的所有集合
18,25,29,30,35,40
List<BigDecimal> list1 = ageList.stream().filter(o -> o.compareTo(BigDecimal.valueOf(0)) >0 && o.compareTo(BigDecimal.valueOf(18)) <0).collect(Collectors.toList());
未使用jdk1.8特性的排序
Collections.sort(flightDOList, new Comparator<FlightDO>() {
@Override
public int compare(FlightDO o1, FlightDO o2) {
return o2.getTakeOffTime().compareTo(o1.getTakeOffTime());
}
});
7.如何将特殊表情或者微信昵称存入数据库
一般mysql表字符集设置为UTF-8,就无法把表情昵称存储到表中,那么需要设置表字符集:utf8mb4
8.BigDecimal和BigDecimalUtil使用
该类提供加减乘除等方法,解决了其他操作类型乘除运算错误问题
BigDecimal.ZERO 设置为0
BigDecimal bigDecimal = new BigDecimal("11"); 将字符串转化为对象
BigDecimalUtil.to2Point() 保留两位小数
BigDecimal dt = new BigDecimal("1");
BigDecimal dt1 = new BigDecimal("3");
BigDecimal dt2 = dt.divide(dt1, 4, BigDecimal.ROUND_HALF_UP);
System.out.println("----除法(保留四位小数)---"+dt2);
System.out.println("----乘法(保留二位小数)---"+dt2.multiply(BigDecimal.valueOf(100l)).setScale(2));
BigDecimal对象取余运算 [0] 是商 [1] 是余
BigDecimal dt1 = BigDecimal.valueOf (6);
BigDecimal dt2 = BigDecimal.valueOf (5);
BigDecimal str = dt1.divideAndRemainder(dt2)[1];
//当int运算方法 int除法误区 当两个int或者BigDecimal都为0时,除法结果是NaN,解决方案是判断两个值是否为0
int a=1;
int b=2;
DecimalFormat df=new DecimalFormat("0.00");
System.out.println(df.format((float)a/b)); System.out.println(df.format(a*1.0/b));
9.String数组和List相互转化
String转化为数组
/准备一个String数组
String[] strs = {"aa","bb","cc"};
//String数组转List
List<String> strsToList1= Arrays.asList(strs);
数组转化为List
//先准备一个List
List<String> testList=new ArrayList<>();
testList.add("a");
testList.add("b");
testList.add("c");
//List转String
String[] strs1=testList.toArray(new String[testList.size()]);
10.mysql建表
1.sort 排序字段 2.remark 标记/备注字段
11.删除list数据
一定要使用Iterator进行遍历删除,其他会报错
if(list != null && !list.isEmpty()){
Iterator<ProductInfoBean> iter = list.iterator();
while(iter.hasNext()){
ProductInfoBean productInfoBean = iter.next();
if(StringUtils.isNotBlank(productInfoBean.getName())){
productInfoBean.setId(UF.getRandomUUID());
productInfoBean.setProductId(productId);
}else{
iter.remove();
}
}
}
12.mysql去重
统计出交易总会员数量
SELECT COUNT(DISTINCT member_id)
FROM table
13.使用jdk1.8 stream 进行分页
场景:比如出现数据统计,全部数据统计到一个List当中
List<String> list = new ArrayList<String>();
list.add("1");
list.add("2");
list.add("3");
list.add("4");
list.add("5");
list.add("6");
list.add("7");
list.add("8");
list.add("9");
list.add("10");
list.add("11");
list = list.stream().skip(5).collect(Collectors.toList());
List<String> pagingData = list.stream().limit(5).collect(Collectors.toList());
System.out.println(pagingData);
结果是:
[6, 7, 8, 9, 10]
14.list倒序
Collections.reverse(list);
15.mysql集锦
(1).当平台发布公告,获取公告,并且知道公告用户是否已读状态
SELECT mn.id,
mn.title,
mn.remark,
mn.content,
mn.author,
IFNULL(mnmm.status,1) AS STATUS,
FROM msg_notice AS mn
LEFT JOIN (SELECT id,notice_id,member_id,status FROM msg_notice_member_mapping WHERE member_id = #{memberId}) AS mnmm
ON mn.id = mnmm.notice_id
order by modify_time desc
最后想得到结果是:公告表有10条数据,用户已读2条,那么返回10条数据,并且两条数据显示可读状态
重点介绍:红色字体标注起来的语句,为啥用这种写法,如果直接用关联表那么根据条件只会查询出2条数据,这种写法会查询出10条数据
(2).类似子查询用法集锦
SELECT DAY,
COUNT(member_id) as number
FROM (
SELECT DATE_FORMAT(pb.add_time, '%Y-%m-%d') AS DAY,
pb.member_id
FROM pay_bill as pb
left join member_user as mu
on pb.member_id = mu.id
GROUP BY DATE_FORMAT(pb.add_time, '%Y-%m-%d'),pb.member_id
) AS a
GROUP BY a.day
(3).查询用户7天内没有绑卡的用户数量
SELECT SUM(IF (mse.add_time IS NULL OR mse.add_time = '' OR DATE_ADD(DATE_FORMAT(mae.add_time, '%Y-%m-%d'),INTERVAL 7 DAY) < DATE_FORMAT(mse.add_time, '%Y-%m-%d'), 1 , 0)) unbind
FROM member_analyse mae
LEFT JOIN (SELECT * FROM member_analyse WHERE TYPE = 2) mse ON mse.member_id = mae.member_id
WHERE mae.type = 1
//本sql重点是IF语句以及LEFT JOIN (子查询)
16.ibatis使用技巧
1.多参数传递
mapper定义方法(在参数较少的情况下使用非常便利)
List<ChannelAnalyseBean> findList(@Param("channelId") String channelId,
@Param("startTime") String startTime,
@Param("endTime") String endTime);
xml中不用配置请求参数类型
<!-- 获取某个渠道下用户统计 -->
<select id="findList" resultType="cn.ug.analyse.bean.response.ChannelAnalyseBean">
SELECT channel_id as channelId,
name AS channelName
FROM member_analyse
where mchannel_id = #{channelId}
<if test="startTime != null and startTime !=''">
and day >= #{startTime}
</if>
<if test="endTime != null and endTime != ''">
<![CDATA[ and day <= #{endTime}]]>
</if>
</select>
2.数组、List传递数据遍历
/** 渠道id **/
private String channelIds []; //实体定义
int findNoBindingBankCardTotal(DormancyMemberParamBean entity); //mapper定义
//xml使用方法
<select id="findNoBindingBankCardTotal" parameterType="cn.ug.analyse.bean.request.DormancyMemberParamBean" resultType="Integer">
SELECT IFNULL(count(1), 0) as total
FROM member_user AS mu
<if test="channelIds != null">
channel_id in
<foreach collection="channelIds" item="channelId" index="index" open="(" separator="," close=")">
#{channelId}
</foreach>
</if>
</select>
17.mysql优化方案(都是我的经验)
(1).当多个表之间数据有限情况下,可以使用join,多表查询。比如用户、权限、角色之类数据有限的查询
(2).当多个表之间数据查询,一定要使用单表查询,不要使用关联查询。比如:当主表有100万数据,关联10万条数据,
多表查询不但效率底下,而且后期如果做分库分表业务,维护性大
(3).对表中的关键字段加索引,提高查询效率。比如在订单表中的会员Id上加索引
(4).对数据库经常查询不是经常变化的数据,在业务层使用缓存机制(redis可以实现)。比如产品表。
(5).对表中的某些重要字段进行设置唯一索引,防止业务层并发导致插入相同数据。比如订单表中的订单号
(6).不使用Select *,只查询需要的字段
(7).开启数据库慢日志功能(可以查询出数据库那些sql查询比较慢)
18.mysql中IF函数用法(类似三元表达式)
(1).第一种用法:
select name,if(sex=0,'女','男') as sex from student;
+-------+-----+
| name | sex |
+-------+-----+
| name1 | 女 |
| name2 | 女 |
| name3 | 男 |
| name4 | 女 |
+-------+-----+
4 rows in set (0.00 sec)
(2).第二种用法(比如各种排序)
order by is_stop ASC, IF (is_stop = 1, add_time, stop_time) DESC
//首先按照is_stop升序排列,如果is_stop是1那么按照add_time倒序排列,如果is_stop是2那么按照stop_time倒序排列
(3).第三种用法
19.mysql将获取到的数据插入到表中(insert into select from的使用)
INSERT INTO db1_name(field1,field2) SELECT field1,field2 FROM db2_name
INSERT INTO a(field1,field2) SELECT * FROM(SELECT f1,f2 FROM b JOIN c) AS tb
20.mysql常用函数集锦
and (pbc.status IS NULL OR pbc.status !=2) //or用法
name like concat('%', #{name}, '%') //like使用
IFNULL(sum(amount),0) //如果为空就返回0
DATE_FORMAT(NOW(), '%Y-%m-%d') //时间格式化
DATE_SUB(DATE_FORMAT(NOW(), '%Y-%m-%d'), INTERVAL 1 DAY) //给当前时间-1天 DATE_ADD给当前时间加1天或者一个月等等
ALTER TABLE info ADD label VARCHAR(20); //新增字段
ALTER TABLE info ADD status int NOT NULL DEFAULT '0'; //新增字段设置默认值
ALTER TABLE INFO modify column label varchar(30); //修改字段类型
ALTER TABLE pay_account_finance_bill CHANGE income_amount recharge_amount DECIMAL(10,2) NOT NULL //修改字段
ALTER TABLE table_name ADD UNIQUE (column) //添加唯一索引
ALTER TABLE table_name ADD INDEX index_name (column) //添加普通索引
SELECT CURDATE(); //获取当前日期 2018-06-15
SELECT NOW(); //获取当前时间 2018-06-15 11:46:35
SELECT CONCAT('11','22','33'); //字符串连接