前台页面展示效果
最终效果
两张表,住宿申请表,退宿申请表
- 住宿审批表A:
-
主键id,人员id,宿舍地址,宿舍号,补贴开始日期,实际入住日期,申请日期。
- 退宿审批表B:
-
主键id,人员id,宿舍地址,宿舍号,补贴开始日期,退宿日期,申请表。
业务需求:
根据选择的年份,季度。得出此人的补贴情况
业务逻辑
-
有退宿的情况下
这个人 if (退宿日期 <= 15号){ 补贴175元 } else if (退宿日期 > 15号 ) { 补贴350元 }
-
没有退宿情况下
这个人 if (补贴开始日期 <= 15号) { 补贴350元 } else if (补贴开始日期 > 15号) { 补贴减半 175元 }
前台页面 如果要在先页面上显示每季度三个月的数据 应该在实体类建三个字段 分别存 每季度
第一个月,第二个月,第三个月 的数据虚拟字段。
oneMothStandard,twoMothStandard,threeMothStandard
你可能会想,一个月对应一个虚拟字段。不是应该12个虚拟字段吗。天呢12个虚拟字段处理起来是多么的麻烦。接着往下分析你就会明白了。
查询条件
(根据选择年份,选择季度查询数据(第一,二,三,四季度 传的值分别是 3,6,9,12)) sql 中用补贴开始日期格式化出年,月 与选择条件做判断。你可能会问,季度为什么要传 3,6,9,12 呢,下面来分下数据。
后台 处理数据遇到情况:如果当前月份是五月
数据分析
1.如果这个人 补贴开始日期是一月份15号之前的。那么他的补贴情况分别是
第一季度,一月份350,二月份350 三月份350。第二季度,四月份350元,五月份350元,六月份0元。
2.如果这个人 补贴开始日期是二月份15号之前的。
那么他的补贴情况分别是 第一季度,一月份0元,二月份350 三月份350。第二季度,四月份350元,五月份350元,六月份0元。
3.如果这个人 补贴开始日期是四月份15号之前的。
那么他的补贴情况分别是 第一季度,一月份0元,二月份0, 三月份0。第二季度,四月份350元,五月份350元,六月份0元。
4.如果这个人 补贴开始日期是四月份15号之前的。
那么他的补贴情况分别是 第一季度,一月份0元,二月份0, 三月份0。第二季度,四月份0元,五月份350元,六月份0元。
假如理想情况下没有人员退宿。
要查第二季度补贴报表 如果用 in(4,5,6) 是不是有问题。
原因:
如果一,二,三月申请人员信息没有查出来,这样他们4,5月补贴就没有了。
也就是说 如果要查二季度的补贴报表 应该把 <= 6 月份的申请人员信息全查出来,
那么要查一季度的补贴报表 应该把 <= 3 月份的申请人员信息全查出来。 现在明白为什么要用 3,6,9,12 分别代表 第一,二,三,四季度了吧。
最难的逻辑分析来了。只有这 oneMothStandard,twoMothStandard,threeMothStandard三个字段
该怎么赋值呢 又分别准确代表月份补贴的数据呢。因为这个逻辑我也是思索了很长的时间。
其实可以这样分析,前台展示的页面只有三个月的数据,而且每季度都有三个月。那么结合上面的图。
让oneMothStandard 代表每季度第一个月份的补贴数据。
同理twoMothStandard,threeMothStandard 分别代表每季度第二个,第个三月份的补贴数据。
前台传过来的季度 分别是 3,6,9,12. 开始赋值逻辑判断
进行逻辑处理
```java
// 分开一个人 一个人的去处理。循环这个集合 根据人员id 前台选择年份,季度 作为条件查询数据 得到一个新集合
//根据前台选择的年份 季度查询数据得到集合
List<DormSubsidyPage> dormSubsidyPages = dormSubsidyPageMapper.queryDormSubsidyPageList(page, subsidyPage);
for (DormSubsidyPage dormSubsidyPage : dormSubsidyPages) {
// 根据人员id 前台选择的年份 季度查询数据得到集合
List<DormSubsidyPage> dsubsidyList = queryDormSubsidyList(dormSubsidyPage);
//季度计算
for (DormSubsidyPage dorm : dsubsidyList) {
// 退宿年,月,日
int tsyear = dorm.getTzrq()==null?0:Integer.valueOf(year.format(dorm.getTzrq()));
int tsmoth = dorm.getTzrq()==null?0:Integer.valueOf(tmoth.format(dorm.getTzrq()));
int tsday = dorm.getTzrq()==null?0:Integer.valueOf(tday.format(dorm.getTzrq()));
//dorm.getMonths(),dorm.getDays(),subsidyPage.getMonths() 分别为补贴开始月份 补贴开始日,前台传季度参数
// 先判断有没有退宿的人员
if (tsmoth > 0) {
if (tsmoth - dorm.getMonths() >= 1){
// 申请月份在当前查询季度第一个月份 || 申请的月份在当前查询季度的 前一季度 (例如查询 第二季度的数据 有在第一季度申请的人员)
if (tsmoth - dorm.getMonths() >=2 ){
// 如果在当前查询季度一个月 15号之后前 补贴减半 例如查询第二季度 4 月份的数据
if (tsmoth - dorm.getMonths() ==2 && dorm.getDays() > 15){
dormSubsidyPage.setOneMothStandard(175);
} esle {
dormSubsidyPage.setOneMothStandard(350);
}
dormSubsidyPage.setTwoMothStandard(300);
dormSubsidyPage.setThreeMothStandard(300);
}
// 申请的月份在当前查询季度第二个月 例如查询第二季度 5 月份的数据
if (tsmoth - dorm.getMonths() == 1 ) {
if (dorm.getDays() > 15) {
dormSubsidyPage.setTwoMothStandard(175);
} else {
dormSubsidyPage.setTwoMothStandard(300);
}
// 退宿日
if (tsday < 15) {
dormSubsidyPage.setThreeMothStandard(175);
} else {
dormSubsidyPage.setThreeMothStandard(300);
}
dormSubsidyPage.setThreeMothStandard(300)
}
// 季度第三月份退宿
if (tsmoth - subsidyPage.getMonths() == 0 ) {
if (tsday < 15) {
dormSubsidyPage.setThreeMothStandard(divide);
} else {
dormSubsidyPage.setThreeMothStandard(dormSubsidyPage.getLodging());
}
}
}
}
// 没有退宿的情况
if (tsmoth <= 0) {
// 如果补贴开始的月份在 比查询的季度参数小 (例如查询第二季度 1,2,3,4,5,6月份的数据处理逻辑)
if (subsidyPage.getMonths() - dorm.getMonths() >= 1) {
// 当前查询季度第一月份 || 或者当前查询季度 前一季度申请 (例如查询第二季度 1,2,3 月份申请人员数据处理)
if (subsidyPage.getMonths() - dorm.getMonths() >= 2) {
// 当前查询季度第一月份申请 (例如查询第二季度 4月份申请人员数据处理)
if (subsidyPage.getMonths() - dorm.getMonths() == 2 && dorm.getDays() > 15) {
dormSubsidyPage.setOneMothStandard(divide);
} else {
dormSubsidyPage.setOneMothStandard(dormSubsidyPage.getLodging());
}
dormSubsidyPage.setTwoMothStandard(dormSubsidyPage.getLodging());
dormSubsidyPage.setThreeMothStandard(dormSubsidyPage.getLodging());
}
// 当前查询季度第二月份申请 (例如查询第二季度 5月份申请人员数据处理)
if (subsidyPage.getMonths() - dorm.getMonths() == 1) {
if (dorm.getDays() > 15) {
dormSubsidyPage.setTwoMothStandard(divide);
} else {
dormSubsidyPage.setTwoMothStandard(dormSubsidyPage.getLodging());
}
dormSubsidyPage.setThreeMothStandard(dormSubsidyPage.getLodging());
}
// 季度第三月份申请的
} else if (subsidyPage.getMonths() - dorm.getMonths() == 0) {
if (dorm.getDays() > 15) {
dormSubsidyPage.setThreeMothStandard(divide);
} else {
dormSubsidyPage.setThreeMothStandard(dormSubsidyPage.getLodging());
}
}
}
}
}
//然后去除超过当前系统日期的数据 (例如当前月份是五月份 查询第二季度的时候 六月份的补贴数据应该还没有 通过上面的计算逻辑 是有的 )
代码省略****
//最后根据申请人员id 去除重复的数据
代码省略****
// 上面两步执行完 把集合返回前台`
代码省略****
有一个直接致命的问题。
当时这样只考虑的本年的数据,如果这个人是 2019 申请的补贴并且没有退宿 那么查询2020年的数据 就把2019年申请补贴人员信息给漏掉 造成统计的数据不准确。当前后台查询数据sql 可以改下 改成 <= 当前查询的月份 在假如系统有很多30年申请补贴 并且没有退宿的人员这样处理起来的数据太lo了 。
真心希望各位前辈多给些建议。总感觉我写的逻辑太复杂了。