一、书接上回:

https://www.cnblogs.com/mindzone/p/17749725.html

这个效果被否决了,产品要求一定要UI的来,UI效果如图:

按人为主体的时候,固定有4个类型,点击每个类型的下拉,展示该类型的权重分排名记录

二、实现思路:

最终实现了,麻烦点多

后端的问题:

1、一次查询,调用3段SQL,先按车辆分组查询,再查询对应的4个类型权重分最高的,最后按每个类型查询排名

2、因为类型固定是4个,所以记录数被影响了,每页必须除以4,而返回的总记录又乘以4,第一个分组的SQL 要做好分页计算处理

3、查询条件的兼容性问题,这里我对排名的记录不设置查询条件,因为内嵌的SQL做逻辑不处理,可以做,麻烦就是

前端问题:

1、表格组件,不使用树表格属性,改用了展开行,树表格只能在首列点击下拉

2、不能合并单元格,因为点击查看排名记录,单元格行数动态的,合并计算会出BUG

3、内嵌的排名表格不能展示表头字段名称,并且和主表格的展示要一致

三、实现步骤:

编写SQL

1、主查询SQL即对车牌号分组,这里GROUP BY 语句用Wrapper对象写的

/**
* @author OnCloud9
* @date 2023/10/10 19:49
* @description 以车牌分组排序进行查询
* @params [page, query]
* @return com.baomidou.mybatisplus.core.metadata.IPage<cn.ymcd.perception.basedata.statistic.dto.AcaBeLpresultDTO>
*/
@Select(
"SELECT license_plate, COUNT(1) AS count, MAX( update_date ) AS ud " +
"FROM aca_be_lpresult " +
" ${ew.customSqlSegment} "
)
IPage<AcaBeLpresultDTO> getBleCarBasicPageLpPrimary(IPage<AcaBeLpresultDTO> page, @Param(Constants.WRAPPER) QueryWrapper<AcaBeLpresultDTO> query);

2、对每个车牌查询4种蓝牙类型权重分最高的记录:

先从简单的具体某个蓝牙类型来查询,指定车牌号和类型,对权重分降序,取第一个即可

SELECT * FROM aca_be_lpresult WHERE license_plate = '赣AK16M5' AND type IN(2, 66)
ORDER BY score DESC LIMIT 1

有可能在这个类型下,没有这个蓝牙类型的记录,但是要求固定有个类型的展示,所以一定需要一个记录展示

先写一个车牌号作为临时表,这个临时表本身做一条记录填充

(SELECT '赣AK16M5' AS license_plate) AS temp2

以临时表为主表,连接上面的类型的权重分最高记录,就可以保证有一条记录存在

如果记录为空,则填充默认值

SELECT
IFNULL(type2.id, '') AS id,
IFNULL(type2.mac, '') AS mac,
'手表蓝牙' AS typeName2,
IFNULL(type2.ble_name, '') AS ble_name,
temp2.license_plate,
IFNULL(type2.car_type, NULL) AS car_type,
IFNULL(type2.times, 0) AS times,
IFNULL(type2.days_count, 0) AS days_count,
IFNULL(type2.station_count, 0) AS station_count,
IFNULL(type2.adjoint_count, 0) AS adjoint_count,
IFNULL(type2.mac_law_count, 0) AS mac_law_count,
IFNULL(type2.score, 0) AS score,
IFNULL(type2.create_date, NULL) AS create_date,
IFNULL(type2.update_date, NULL) AS update_date,
IFNULL(type2.timeline, NULL) AS timeline
FROM (SELECT '赣AK16M5' AS license_plate) AS temp2 LEFT JOIN
(SELECT id, mac, type, ble_name, license_plate, car_type, times, days_count, station_count, adjoint_count, mac_law_count, score, create_date, update_date, timeline
FROM aca_be_lpresult WHERE license_plate = '赣AK16M5' AND type = 7
ORDER BY score DESC LIMIT 1) AS type2 ON temp2.license_plate = type2.license_plate;

为空的查询结果:

+----+-----+-----------+----------+---------------+----------+-------+------------+---------------+---------------+---------------+-------+-------------+-------------+----------+
| id | mac | typeName2 | ble_name | license_plate | car_type | times | days_count | station_count | adjoint_count | mac_law_count | score | create_date | update_date | timeline |
+----+-----+-----------+----------+---------------+----------+-------+------------+---------------+---------------+---------------+-------+-------------+-------------+----------+
| | | 手表蓝牙 | | 赣AK16M5 | NULL | 0 | 0 | 0 | 0 | 0 | 0.00 | NULL | NULL | NULL |
+----+-----+-----------+----------+---------------+----------+-------+------------+---------------+---------------+---------------+-------+-------------+-------------+----------+
1 row in set (0.08 sec)

使用UNION 关键字对4个类型的查询合并成一个结果

SELECT
IFNULL(type2.id, '') AS id,
IFNULL(type2.mac, '') AS mac,
'手机蓝牙' AS typeName2,
IFNULL(type2.ble_name, '') AS ble_name,
temp2.license_plate,
IFNULL(type2.car_type, NULL) AS car_type,
IFNULL(type2.times, 0) AS times,
IFNULL(type2.days_count, 0) AS days_count,
IFNULL(type2.station_count, 0) AS station_count,
IFNULL(type2.adjoint_count, 0) AS adjoint_count,
IFNULL(type2.mac_law_count, 0) AS mac_law_count,
IFNULL(type2.score, 0) AS score,
IFNULL(type2.create_date, NULL) AS create_date,
IFNULL(type2.update_date, NULL) AS update_date,
IFNULL(type2.timeline, NULL) AS timeline
FROM (SELECT '赣AK16M5' AS license_plate) AS temp2 LEFT JOIN
(SELECT id, mac, type, ble_name, license_plate, car_type, times, days_count, station_count, adjoint_count, mac_law_count, score, create_date, update_date, timeline
FROM aca_be_lpresult WHERE license_plate = '赣AK16M5' AND type IN(2, 66)
ORDER BY score DESC LIMIT 1) AS type2 ON temp2.license_plate = type2.license_plate
UNION
SELECT
IFNULL(type2.id, '') AS id,
IFNULL(type2.mac, '') AS mac,
'手表蓝牙' AS typeName2,
IFNULL(type2.ble_name, '') AS ble_name,
temp2.license_plate,
IFNULL(type2.car_type, NULL) AS car_type,
IFNULL(type2.times, 0) AS times,
IFNULL(type2.days_count, 0) AS days_count,
IFNULL(type2.station_count, 0) AS station_count,
IFNULL(type2.adjoint_count, 0) AS adjoint_count,
IFNULL(type2.mac_law_count, 0) AS mac_law_count,
IFNULL(type2.score, 0) AS score,
IFNULL(type2.create_date, NULL) AS create_date,
IFNULL(type2.update_date, NULL) AS update_date,
IFNULL(type2.timeline, NULL) AS timeline
FROM (SELECT '赣AK16M5' AS license_plate) AS temp2 LEFT JOIN
(SELECT id, mac, type, ble_name, license_plate, car_type, times, days_count, station_count, adjoint_count, mac_law_count, score, create_date, update_date, timeline
FROM aca_be_lpresult WHERE license_plate = '赣AK16M5' AND type = 7
ORDER BY score DESC LIMIT 1) AS type2 ON temp2.license_plate = type2.license_plate
UNION
SELECT
IFNULL(type2.id, '') AS id,
IFNULL(type2.mac, '') AS mac,
'电脑蓝牙' AS typeName2,
IFNULL(type2.ble_name, '') AS ble_name,
temp2.license_plate,
IFNULL(type2.car_type, NULL) AS car_type,
IFNULL(type2.times, 0) AS times,
IFNULL(type2.days_count, 0) AS days_count,
IFNULL(type2.station_count, 0) AS station_count,
IFNULL(type2.adjoint_count, 0) AS adjoint_count,
IFNULL(type2.mac_law_count, 0) AS mac_law_count,
IFNULL(type2.score, 0) AS score,
IFNULL(type2.create_date, NULL) AS create_date,
IFNULL(type2.update_date, NULL) AS update_date,
IFNULL(type2.timeline, NULL) AS timeline
FROM (SELECT '赣AK16M5' AS license_plate) AS temp2 LEFT JOIN
(SELECT id, mac, type, ble_name, license_plate, car_type, times, days_count, station_count, adjoint_count, mac_law_count, score, create_date, update_date, timeline
FROM aca_be_lpresult WHERE license_plate = '赣AK16M5' AND type IN(1, 65)
ORDER BY score DESC LIMIT 1) AS type2 ON temp2.license_plate = type2.license_plate
UNION
SELECT
IFNULL(type2.id, '') AS id,
IFNULL(type2.mac, '') AS mac,
'其它蓝牙' AS typeName2,
IFNULL(type2.ble_name, '') AS ble_name,
temp2.license_plate,
IFNULL(type2.car_type, NULL) AS car_type,
IFNULL(type2.times, 0) AS times,
IFNULL(type2.days_count, 0) AS days_count,
IFNULL(type2.station_count, 0) AS station_count,
IFNULL(type2.adjoint_count, 0) AS adjoint_count,
IFNULL(type2.mac_law_count, 0) AS mac_law_count,
IFNULL(type2.score, 0) AS score,
IFNULL(type2.create_date, NULL) AS create_date,
IFNULL(type2.update_date, NULL) AS update_date,
IFNULL(type2.timeline, NULL) AS timeline
FROM (SELECT '赣AK16M5' AS license_plate) AS temp2 LEFT JOIN
(SELECT id, mac, type, ble_name, license_plate, car_type, times, days_count, station_count, adjoint_count, mac_law_count, score, create_date, update_date, timeline
FROM aca_be_lpresult WHERE license_plate = '赣AK16M5' AND type NOT IN(1, 65, 2, 66, 7)
ORDER BY score DESC LIMIT 1) AS type2 ON temp2.license_plate = type2.license_plate

查询结果:

+------+--------------+-----------+-----------------------+---------------+----------+-------+------------+---------------+---------------+---------------+-------+---------------------+---------------------+---------------------+
| id | mac | typeName2 | ble_name | license_plate | car_type | times | days_count | station_count | adjoint_count | mac_law_count | score | create_date | update_date | timeline |
+------+--------------+-----------+-----------------------+---------------+----------+-------+------------+---------------+---------------+---------------+-------+---------------------+---------------------+---------------------+
| 2134 | 000d18a17fa0 | 手机蓝牙 | BC8-A是北:D??ndroid | 赣AK16M5 | 1 | 4 | 3 | 3 | 0 | 0 | 8.00 | 2023-10-12 19:32:52 | 2023-10-12 19:35:33 | 2023-10-12 19:33:10 |
| | | 手表蓝牙 | | 赣AK16M5 | NULL | 0 | 0 | 0 | 0 | 0 | 0.00 | NULL | NULL | NULL |
| 2183 | 0d1852f820a0 | 电脑蓝牙 | BC8-Android | 赣AK16M5 | 1 | 1 | 1 | 1 | 0 | 0 | 2.50 | 2023-10-12 19:32:58 | 2023-10-12 19:35:32 | 2023-10-12 19:32:58 |
| | | 其它蓝牙 | | 赣AK16M5 | NULL | 0 | 0 | 0 | 0 | 0 | 0.00 | NULL | NULL | NULL |
+------+--------------+-----------+-----------------------+---------------+----------+-------+------------+---------------+---------------+---------------+-------+---------------------+---------------------+---------------------+
4 rows in set (0.16 sec)

  

在这里只传递车牌号作为参数处理,可以追加Wrapper对象补充筛选条件

@Select(
"SELECT " +
" IFNULL(type2.id, '') AS id, " +
" IFNULL(type2.mac, '') AS mac, " +
" 1 AS `type`, " +
" '手机蓝牙' AS typeName2," +
" IFNULL(type2.ble_name, '') AS ble_name," +
" temp2.license_plate," +
" IFNULL(type2.car_type, NULL) AS car_type, " +
" IFNULL(type2.times, 0) AS times, " +
" IFNULL(type2.days_count, 0) AS days_count," +
" IFNULL(type2.station_count, 0) AS station_count," +
" IFNULL(type2.adjoint_count, 0) AS adjoint_count," +
" IFNULL(type2.mac_law_count, 0) AS mac_law_count," +
" IFNULL(type2.score, 0) AS score," +
" IFNULL(type2.create_date, NULL) AS create_date," +
" IFNULL(type2.update_date, NULL) AS update_date," +
" IFNULL(type2.timeline, NULL) AS timeline " +
"FROM (SELECT ${licensePlateStr} AS license_plate) AS temp2 LEFT JOIN " +
"(SELECT id, mac, type, ble_name, license_plate, car_type, times, days_count, station_count, adjoint_count, mac_law_count, score, create_date, update_date, timeline " +
"FROM aca_be_lpresult WHERE license_plate = #{licensePlate} AND type IN(2, 66) " +
"ORDER BY score DESC LIMIT 1) AS type2 ON temp2.license_plate = type2.license_plate " +
"UNION " +
"SELECT " +
" IFNULL(type2.id, '') AS id, " +
" IFNULL(type2.mac, '') AS mac," +
" 2 AS `type`, " +
" '手表蓝牙' AS typeName2," +
" IFNULL(type2.ble_name, '') AS ble_name," +
" temp2.license_plate," +
" IFNULL(type2.car_type, NULL) AS car_type, " +
" IFNULL(type2.times, 0) AS times, " +
" IFNULL(type2.days_count, 0) AS days_count," +
" IFNULL(type2.station_count, 0) AS station_count," +
" IFNULL(type2.adjoint_count, 0) AS adjoint_count," +
" IFNULL(type2.mac_law_count, 0) AS mac_law_count," +
" IFNULL(type2.score, 0) AS score," +
" IFNULL(type2.create_date, NULL) AS create_date," +
" IFNULL(type2.update_date, NULL) AS update_date," +
" IFNULL(type2.timeline, NULL) AS timeline " +
"FROM (SELECT ${licensePlateStr} AS license_plate) AS temp2 LEFT JOIN " +
"(SELECT id, mac, type, ble_name, license_plate, car_type, times, days_count, station_count, adjoint_count, mac_law_count, score, create_date, update_date, timeline " +
"FROM aca_be_lpresult WHERE license_plate = #{licensePlate} AND type = 7 " +
"ORDER BY score DESC LIMIT 1) AS type2 ON temp2.license_plate = type2.license_plate " +
"UNION " +
"SELECT" +
" IFNULL(type2.id, '') AS id, " +
" IFNULL(type2.mac, '') AS mac, " +
" 3 AS `type`, " +
" '电脑蓝牙' AS typeName2," +
" IFNULL(type2.ble_name, '') AS ble_name," +
" temp2.license_plate," +
" IFNULL(type2.car_type, NULL) AS car_type, " +
" IFNULL(type2.times, 0) AS times, " +
" IFNULL(type2.days_count, 0) AS days_count," +
" IFNULL(type2.station_count, 0) AS station_count," +
" IFNULL(type2.adjoint_count, 0) AS adjoint_count," +
" IFNULL(type2.mac_law_count, 0) AS mac_law_count," +
" IFNULL(type2.score, 0) AS score," +
" IFNULL(type2.create_date, NULL) AS create_date," +
" IFNULL(type2.update_date, NULL) AS update_date," +
" IFNULL(type2.timeline, NULL) AS timeline " +
"FROM (SELECT ${licensePlateStr} AS license_plate) AS temp2 LEFT JOIN " +
"(SELECT id, mac, type, ble_name, license_plate, car_type, times, days_count, station_count, adjoint_count, mac_law_count, score, create_date, update_date, timeline " +
"FROM aca_be_lpresult WHERE license_plate = #{licensePlate} AND type IN(1, 65) " +
"ORDER BY score DESC LIMIT 1) AS type2 ON temp2.license_plate = type2.license_plate " +
"UNION " +
"SELECT " +
" IFNULL(type2.id, '') AS id, " +
" IFNULL(type2.mac, '') AS mac, " +
" 4 AS `type`, " +
" '其它蓝牙' AS typeName2," +
" IFNULL(type2.ble_name, '') AS ble_name," +
" temp2.license_plate," +
" IFNULL(type2.car_type, NULL) AS car_type, " +
" IFNULL(type2.times, 0) AS times, " +
" IFNULL(type2.days_count, 0) AS days_count," +
" IFNULL(type2.station_count, 0) AS station_count," +
" IFNULL(type2.adjoint_count, 0) AS adjoint_count," +
" IFNULL(type2.mac_law_count, 0) AS mac_law_count," +
" IFNULL(type2.score, 0) AS score," +
" IFNULL(type2.create_date, NULL) AS create_date," +
" IFNULL(type2.update_date, NULL) AS update_date," +
" IFNULL(type2.timeline, NULL) AS timeline " +
"FROM (SELECT ${licensePlateStr} AS license_plate) AS temp2 LEFT JOIN" +
"(SELECT id, mac, type, ble_name, license_plate, car_type, times, days_count, station_count, adjoint_count, mac_law_count, score, create_date, update_date, timeline " +
"FROM aca_be_lpresult WHERE license_plate = #{licensePlate} AND type NOT IN(1, 65, 2, 66, 7) " +
"ORDER BY score DESC LIMIT 1) AS type2 ON temp2.license_plate = type2.license_plate "
)
List<AcaBeLpresultDTO> getBleCarBasicRankForEachCar(@Param("licensePlate") String licensePlate, @Param("licensePlateStr") String licensePlateStr);

最后获取该类型下的排名记录SQL

SELECT * FROM aca_be_lpresult WHERE license_plate = '赣AK16M5' AND type IN(2, 66)
ORDER BY score DESC LIMIT 11

因为第一条已经在上面的SQL里面存在了,所以SQL查出来用Java去掉第一个元素即可

业务逻辑层

这里就不单独贴了,因为区分了蓝牙和人的主体,就看下面以车牌分组的部分

蓝牙部分没有要求类型的筛选,所以分组查询之后只需要查询排名放入即可

以车辆查询的部分则麻烦一点,还需要设置翻页的参数变化,每页数量先除4,提供实际的分组翻页查询

得到的总记录需要乘4再把实际可以翻页的记录数补回来

因为动态表格和扩展行的影响,不能合并单元格,妥协的处理是,只在每组记录的第一行展示关键信息(车辆信息 + 蓝牙信息)

可以看到我只在类型排名的集合里对第一个元素设置displayFlag变量为true

@SuppressWarnings("all")
@Override
public IPage<AcaBeLpresultDTO> getBleCarBasicPage(AcaBeLpresultDTO dto) {
boolean hasMacType = Objects.nonNull(dto.getType());
List<String> collect = null; QueryWrapper<AcaBeLpresultDTO> query = Wrappers.<AcaBeLpresultDTO>query()
.like(StringUtils.isNotBlank(dto.getMac()), "mac", StringUtils.isNotBlank(dto.getMac()) ? dto.getMac().replaceAll("-", "").toLowerCase() : "")
.like(StringUtils.isNotBlank(dto.getBleName()), "ble_name", dto.getBleName())
.like(StringUtils.isNotBlank(dto.getLicensePlate()), "license_plate", dto.getLicensePlate())
.between(StringUtils.isNotBlank(dto.getStartUpdateDate()) && StringUtils.isNotBlank(dto.getEndUpdateDate()), "update_date", dto.getStartUpdateDate(), dto.getEndUpdateDate())
.orderByDesc("ud"); if (hasMacType) {
List<Dict> macTypeList = dictService.dicts("MAC_TYPE");
/* 检查是否匹配字典值 */
Optional<Dict> optionalDict = macTypeList.stream().filter(x -> x.getDmbh().equals(dto.getType().toString())).findFirst();
if (optionalDict.isPresent()) {
/* 如果匹配则查找同名的集合值 */
Dict dict = optionalDict.get();
String dmmc = dict.getDmmc();
collect = macTypeList.stream().filter(x -> x.getDmmc().equals(dmmc)).map(Dict::getDmbh).collect(Collectors.toList());
query.in(collect.size() > 1, "type", collect);
query.eq(collect.size() == 1, "type", collect.get(0));
} else {
/* 如果不匹配,则查找(未知) */
collect = macTypeList.stream().map(Dict::getDmbh).collect(Collectors.toList());
query.notIn("type", collect);
}
} IPage<AcaBeLpresultDTO> page = dto.getPage();
Integer option = dto.getOption();
if (new Integer(1).equals(option)) {
query.groupBy("mac");
page = baseMapper.getBleCarBasicPageMacPrimary(dto.getPage(), query);
List<AcaBeLpresultDTO> newRecords = new ArrayList<>();
for (AcaBeLpresultDTO beLpresultDTO : page.getRecords()) {
List<AcaBeLpresultDTO> rankList = lambdaQuery()
.eq(AcaBeLpresultDTO::getMac, beLpresultDTO.getMac())
.in(hasMacType, AcaBeLpresultDTO::getType, collect)
.like(StringUtils.isNotBlank(dto.getLicensePlate()), AcaBeLpresultDTO::getLicensePlate, dto.getLicensePlate())
.between(StringUtils.isNotBlank(dto.getStartUpdateDate()) && StringUtils.isNotBlank(dto.getEndUpdateDate()), AcaBeLpresultDTO::getUpdateDate, dto.getStartUpdateDate(), dto.getEndUpdateDate())
.orderByDesc(AcaBeLpresultDTO::getScore)
.last("LIMIT 11").list();
rankList.forEach(this::convert);
AcaBeLpresultDTO removed = rankList.remove(0);
removed.setChildren(rankList);
newRecords.add(removed);
}
page.setRecords(newRecords);
} else {
query.groupBy("license_plate");
page.setSize(page.getSize() / 4);
page = baseMapper.getBleCarBasicPageLpPrimary(page, query);
page.setTotal(page.getTotal() * 4);
List<AcaBeLpresultDTO> newRecords = new ArrayList<>();
for (AcaBeLpresultDTO beLpresultDTO : page.getRecords()) {
String licensePlate = beLpresultDTO.getLicensePlate();
String licensPlateStr = "'" + licensePlate + "'";
List<AcaBeLpresultDTO> eachCar = baseMapper.getBleCarBasicRankForEachCar(licensePlate, licensPlateStr);
eachCar.forEach(row -> {
convert(row);
List<AcaBeLpresultDTO> rank = getBleCarBasicPageRank(row);
row.setChildren(rank);
});
eachCar.get(0).setDisplayFlag(true);
newRecords.addAll(eachCar);
}
page.setRecords(newRecords);
}
return page;
}

 

getBleCarBasicPageRank 方法:

convert方法就是对字段的一些翻译,蓝牙mac格式化,翻译蓝牙名称之类的

private List<AcaBeLpresultDTO> getBleCarBasicPageRank(AcaBeLpresultDTO dto) {
List<AcaBeLpresultDTO> list = lambdaQuery().eq(AcaBeLpresultDTO::getLicensePlate, dto.getLicensePlate())
.in(new Integer(1).equals(dto.getType()), AcaBeLpresultDTO::getType, phoneMacTypes)
.in(new Integer(2).equals(dto.getType()), AcaBeLpresultDTO::getType, watchMacTypes)
.in(new Integer(3).equals(dto.getType()), AcaBeLpresultDTO::getType, pcMacTypes)
.notIn(new Integer(4).equals(dto.getType()), AcaBeLpresultDTO::getType, Stream.concat(phoneMacTypes.stream(), Stream.concat(watchMacTypes.stream(), pcMacTypes.stream())).collect(Collectors.toList()))
.orderByDesc(AcaBeLpresultDTO::getScore)
.last("LIMIT 11")
.list()
;
if (CollectionUtils.isNotEmpty(list)) {
list.remove(0);
list.forEach(this::convert);
}
return list;
}

 

页面部分的处理:

首先是查询切换的支持

<el-row style="padding: 0 20px 10px 15px;">
<el-col :span="6">
<el-radio-group v-model="queryForm.option" @change="onOptionChange">
<el-radio :label="1">以蓝牙为主体</el-radio>
<el-radio :label="2">以车辆为主体</el-radio>
</el-radio-group>
</el-col>
<el-col :span="18" style="float: right;" />
</el-row>

切换事件:

因为车辆主体查询不适用蓝牙的查询条件,做清空处理后再查询

onOptionChange(val) {
if (val === 2) {
this.queryForm.type = ''
this.queryForm.mac = ''
this.queryForm.bleName = ''
}
this.searchPage()
}

首次翻页查询方法:

因为只有在切换的时候调用,车辆和蓝牙的翻页选项不一样

searchPage() {
this.page.current = 1
if (this.queryForm.option === 2) {
this.page.size = 20
this.sizeList = [20, 40, 60, 100, 200]
} else {
this.page.size = 10
this.sizeList = [10, 20, 30, 100, 200]
}
this.page.total = 0
this.getPageData()
}

查询接口:

分组类型排名的结果可能没有id,所以按下标赋值:

async getPageData() {
this.loadingFlag = true
this.spanArr = []
this.spanIdx = 0
const postData = { ... this.queryForm, page: this.page }
const { data: tableData, total } = await getBleCarBasicPage(postData)
if (this.queryForm.option === 2) tableData.forEach((el, idx) => (el.id = idx))
this.tableData = tableData
this.page.total = total
this.loadingFlag = false
},

查询条件项:

以车辆为主体的查询项,蓝牙的部分都做隐藏控制

<el-row>
<el-col :span="24" style="padding: 15px 20px 0 15px; height: 100%; background: none;">
<div class="grid-content bg-purple-dark">
<el-form :inline="true" :model="queryForm" class="demo-form-inline" size="small">
<el-form-item v-show="queryForm.option === 1" label="蓝牙MAC地址">
<el-input v-model="queryForm.mac" clearable filterable placeholder="请输入蓝牙MAC地址" size="small" />
</el-form-item>
<el-form-item v-show="queryForm.option === 1" label="蓝牙名称">
<el-input v-model="queryForm.bleName" clearable filterable placeholder="请输入蓝牙名称" size="small" />
</el-form-item>
<el-form-item v-show="queryForm.option === 1" label="蓝牙类型">
<el-select v-model="queryForm.type" placeholder="请选择" clearable>
<el-option v-for="item in macTypeList" :key="item.dmbh" :label="item.dmmc" :value="item.dmbh" />
</el-select>
</el-form-item>
<el-form-item label="关联车辆信息" style="margin-left: 5px;">
<el-input v-model="queryForm.licensePlate" clearable filterable placeholder="请输入关联车辆信息" size="small" />
</el-form-item>
<el-form-item>
<el-button type="primary" size="small" @click="searchPage">查询</el-button>
<el-button size="small" @click="resetInput">重置</el-button>
</el-form-item>
</el-form>
</div>
</el-col>
</el-row>

  

表格部分:

1、这里涉及了一个scope-slot作用域问题,内嵌表格不能和主表格使用解构语法读取变量

  所以可以看到我这里没有一直使用同样的变量名,主表格用的是直接解构的对象,到了内嵌表格用的是scope,而内嵌中还有内嵌的列,则用scope2替代

  如果都使用解构或者同名的变量,会导致vue报错,这里是一个注意点

2、关闭内嵌的表格表头,这个使用组件自带的show-header属性即可搞定

3、让内嵌的表格和外部主表格保持一致,我用空列进行填充的,宽度参数和外部保持一致,就是不声明prop属性和label属性

4、表格扩展行的样式问题,因为这个是自定义的样式,我用浏览器调试找的

/deep/ td.el-table__cell.el-table__expanded-cell {
background: #1b203c!important;
}

完整代码:

    <el-row v-loading="loadingFlag" :element-loading-text="loadingText" class="row-talbe">
<el-table
v-show="queryForm.option === 1"
:data="tableData"
size="mini"
style="width: 100%"
stripe
row-key="id"
:tree-props="{ children: 'children', hasChildren: 'hasChildren' }"
max-height="calc(100vh - 350px)"
:header-cell-style="{ 'text-align': 'center' }"
highlight-current-row
tooltip-effect="light"
>
<el-table-column label="蓝牙MAC地址" prop="macCode" show-overflow-tooltip>
<template slot-scope="{ row }">
<more-info-drop-down
text-field="macCode"
keyword-field="macCode"
:info-object="row"
style="display: inline-block;"
/>
</template>
</el-table-column>
<el-table-column label="蓝牙名称" prop="bleName" align="center" show-overflow-tooltip />
<el-table-column label="蓝牙类型" prop="typeName" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
{{ row['typeName'] !== '0' ? row['typeName'] : '未知' }}
</template>
</el-table-column>
<el-table-column label="关联车辆信息" prop="licensePlate" align="left" min-width="160" show-overflow-tooltip>
<template slot-scope="{ row }">
<div>
<p>车牌号码:<more-info-drop-down text-field="licensePlate" keyword-field="licensePlate" :info-object="row" style="display: inline-block;" /></p>
<p>行车记录仪:{{ row.apName }} <more-info-drop-down text-field="usrMacCode" keyword-field="usrMacCode" :info-object="row" style="display: inline-block;" /></p>
<p>车载蓝牙:{{ row['bleName2'] }} <more-info-drop-down text-field="bleMacCode" keyword-field="bleMacCode" :info-object="row" style="display: inline-block;" /></p>
</div>
</template>
</el-table-column>
<el-table-column label="关联车辆次数" prop="times" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
<span class="link-color" @click="timesDetail(row)">
{{ row.times ? `${row.times}次` : '0次' }}
</span>
</template>
</el-table-column>
<el-table-column label="关联车辆天数" prop="daysCount" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
<span class="link-color" @click="dayDetail(row)">
{{ row['daysCount'] ? `${row['daysCount']}天` : '0天' }}
</span>
</template>
</el-table-column>
<el-table-column label="关联车辆点位数" prop="stationCount" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
<span class="link-color" @click="staDetail(row)">
{{ row['stationCount'] ? `${row['stationCount']}个` : '0个' }}
</span>
</template>
</el-table-column>
<el-table-column label="关联车辆伴随记录" prop="adjointCount" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
{{ row['adjointCount'] ? `${row['adjointCount']}条` : '0条' }}
</template>
</el-table-column>
<el-table-column label="关联车辆规律" prop="macLawCount" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
{{ row['macLawCount'] ? `${row['macLawCount']}条` : '0条' }}
</template>
</el-table-column>
<el-table-column label="权重计算详情" prop="score" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
<span class="link-color" @click="scoreDetail(row)">
{{ row['score'] ? `${row['score']}分` : '0分' }}
</span>
</template>
</el-table-column>
<el-table-column label="更新时间" prop="updateDate" min-width="120px" align="center" show-overflow-tooltip />
</el-table> <!-- 以关联车辆信息为主体 -->
<el-table
v-show="queryForm.option === 2"
:data="tableData"
size="mini"
style="width: 100%"
stripe
max-height="calc(100vh - 350px)"
highlight-current-row
tooltip-effect="light"
>
<el-table-column label="关联车辆信息" prop="licensePlate" align="left" min-width="160" show-overflow-tooltip>
<template slot-scope="{ row }">
<div v-show="row['displayFlag']" style="display: inline-block;">
<p>车牌号码:<more-info-drop-down text-field="licensePlate" keyword-field="licensePlate" :info-object="row" style="display: inline-block;" /></p>
<p>行车记录仪:{{ row.apName }} <more-info-drop-down text-field="usrMacCode" keyword-field="usrMacCode" :info-object="row" style="display: inline-block;" /></p>
<p>车载蓝牙:{{ row['bleName2'] }} <more-info-drop-down text-field="bleMacCode" keyword-field="bleMacCode" :info-object="row" style="display: inline-block;" /></p>
</div>
</template>
</el-table-column>
<el-table-column type="expand" width="40" align="center">
<template slot-scope="scope">
<el-table :show-header="false" :data="scope.row.children" size="mini" stripe>
<el-table-column label="" prop="" align="center" min-width="160" />
<el-table-column label="" prop="" align="center" width="40" />
<el-table-column label="" prop="" align="center" width="80" />
<el-table-column label="蓝牙名称" prop="bleName" align="center" show-overflow-tooltip />
<el-table-column label="蓝牙MAC地址" prop="macCode" align="center" show-overflow-tooltip>
<template slot-scope="scope2">
<more-info-drop-down
text-field="macCode"
keyword-field="macCode"
:info-object="scope2.row"
/>
</template>
</el-table-column>
<el-table-column label="关联车辆次数" prop="times" align="center" show-overflow-tooltip>
<template slot-scope="scope2">
<span class="link-color" @click="timesDetail(scope2.row)">
{{ scope2.row.times ? `${scope2.row.times}次` : '0次' }}
</span>
</template>
</el-table-column>
<el-table-column label="关联天数" prop="daysCount" align="center" show-overflow-tooltip>
<template slot-scope="scope2">
<span class="link-color" @click="dayDetail(scope2.row)">
{{ scope2.row['daysCount'] ? `${scope2.row['daysCount']}天` : '0天' }}
</span>
</template>
</el-table-column>
<el-table-column label="关联点位数" prop="stationCount" align="center" show-overflow-tooltip>
<template slot-scope="scope2">
<span class="link-color" @click="staDetail(scope2.row)">
{{ scope2.row['stationCount'] ? `${scope2.row['stationCount']}个` : '0个' }}
</span>
</template>
</el-table-column>
<el-table-column label="伴随点位数" prop="adjointCount" align="center" show-overflow-tooltip>
<template slot-scope="scope2">
{{ scope2.row['adjointCount'] ? `${scope2.row['adjointCount']}条` : '0条' }}
</template>
</el-table-column>
<el-table-column label="关联规律" prop="macLawCount" align="center" show-overflow-tooltip>
<template slot-scope="scope2">
{{ scope2.row['macLawCount'] ? `${scope2.row['macLawCount']}条` : '0条' }}
</template>
</el-table-column>
<el-table-column label="权重分数" prop="score" align="center" show-overflow-tooltip>
<template slot-scope="scope2">
<span class="link-color" @click="scoreDetail(scope2.row)">
{{ scope2.row['score'] ? `${scope2.row['score']}分` : '0分' }}
</span>
</template>
</el-table-column>
<el-table-column label="更新时间" prop="updateDate" min-width="120px" align="center" show-overflow-tooltip />
</el-table>
</template>
</el-table-column>
<el-table-column label="蓝牙类型" width="80" prop="typeName2" align="center" />
<el-table-column label="蓝牙名称" prop="bleName" align="center" show-overflow-tooltip />
<el-table-column label="蓝牙MAC地址" prop="macCode" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
<more-info-drop-down
text-field="macCode"
keyword-field="macCode"
:info-object="row"
/>
</template>
</el-table-column>
<el-table-column label="关联车辆次数" prop="times" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
<span class="link-color" @click="timesDetail(row)">
{{ row.times ? `${row.times}次` : '0次' }}
</span>
</template>
</el-table-column>
<el-table-column label="关联天数" prop="daysCount" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
<span class="link-color" @click="dayDetail(row)">
{{ row['daysCount'] ? `${row['daysCount']}天` : '0天' }}
</span>
</template>
</el-table-column>
<el-table-column label="关联点位数" prop="stationCount" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
<span class="link-color" @click="staDetail(row)">
{{ row['stationCount'] ? `${row['stationCount']}个` : '0个' }}
</span>
</template>
</el-table-column>
<el-table-column label="伴随点位数" prop="adjointCount" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
{{ row['adjointCount'] ? `${row['adjointCount']}条` : '0条' }}
</template>
</el-table-column>
<el-table-column label="关联规律" prop="macLawCount" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
{{ row['macLawCount'] ? `${row['macLawCount']}条` : '0条' }}
</template>
</el-table-column>
<el-table-column label="权重分数" prop="score" align="center" show-overflow-tooltip>
<template slot-scope="{ row }">
<span class="link-color" @click="scoreDetail(row)">
{{ row['score'] ? `${row['score']}分` : '0分' }}
</span>
</template>
</el-table-column>
<el-table-column label="更新时间" prop="updateDate" min-width="120px" align="center" show-overflow-tooltip />
</el-table> <el-pagination
style="text-align: right;margin-top: 10px;"
layout="total, sizes, prev, pager, next"
:page-size="page.size"
:current-page.sync="page.current"
:page-sizes="sizeList"
:total="page.total"
@size-change="handleSizeChange"
@current-change="handleCurrentChange"
/>
</el-row>

  

别的部分应该不需要强调啥了。。。

【Vue】分组类型排名查询功能的更多相关文章

  1. Springboot+Vue实现仿百度搜索自动提示框匹配查询功能

    案例功能效果图 前端初始页面 输入搜索信息页面 点击查询结果页面 环境介绍 前端:vue 后端:springboot jdk:1.8及以上 数据库:mysql 核心代码介绍 TypeCtrler .j ...

  2. vue 对象提供的属性功能、通过axio请求数据(2)

    1 Vue对象提供的属性功能 1.1 过滤器 过滤器,就是vue允许开发者自定义的文本格式化函数,可以使用在两个地方:输出内容和操作数据中. 1.1.1 使用Vue.filter()进行全局定义(全局 ...

  3. mysql查询优化之四:优化特定类型的查询

    本文将介绍如何优化特定类型的查询. 1.优化count()查询count()聚合函数,以及如何优化使用了该函数的查询,很可能是mysql中最容易被误解的前10个话题之一 count() 是一个特殊的函 ...

  4. VUE+Element 前端应用开发框架功能介绍

    前面介绍了很多ABP系列的文章<ABP框架使用>,一步一步的把我们日常开发中涉及到的Web API服务构建.登录日志和操作审计日志.字典管理模块.省份城市的信息维护.权限管理模块中的组织机 ...

  5. 创建ASP.NET Core MVC应用程序(5)-添加查询功能 & 新字段

    创建ASP.NET Core MVC应用程序(5)-添加查询功能 & 新字段 添加查询功能 本文将实现通过Name查询用户信息. 首先更新GetAll方法以启用查询: public async ...

  6. [Architecture Pattern] Repository实作查询功能

    [Architecture Pattern] Repository实作查询功能 范例下载 范例程序代码:点此下载 问题情景 在系统的BLL与DAL之间,加入Repository Pattern的设计, ...

  7. 【百度地图API】小学生找哥哥——小学生没钱打车,所以此为公交查询功能

    原文:[百度地图API]小学生找哥哥--小学生没钱打车,所以此为公交查询功能 任务描述: 有位在魏公村附近上小学的小朋友,要去北京邮电大学找哥哥.他身上钱很少,只够坐公交的.所以,百度地图API快帮帮 ...

  8. FreeSql 新查询功能介绍

    FreeSql FreeSql 是一个功能强大的 NETStandard 库,用于对象关系映射程序(O/RM),提供了 CodeFirst/DbFirst/CURD/表达式函数/读写分离 等基础封装. ...

  9. Vc数据库编程基础MySql数据库的表查询功能

    Vc数据库编程基础MySql数据库的表查询功能 一丶简介 不管是任何数据库.都会有查询功能.而且是很重要的功能.上一讲知识简单的讲解了表的查询所有. 那么这次我们需要掌握的则是. 1.使用select ...

  10. 一步一步学SpringDataJpa——JpaRepository查询功能

    原文地址: https://blog.csdn.net/ming070423/article/details/22086169 1.JpaRepository支持接口规范方法名查询.意思是如果在接口中 ...

随机推荐

  1. itest(爱测试) 开源接口测试,敏捷测试管理平台10.1.4发布

    一:itest work 简介 itest work 开源敏捷测试管理,包含极简的任务管理,测试管理,缺陷管理,测试环境管理,接口测试,接口Mock,还有压测 ,又有丰富的统计分析,8合1工作站.可按 ...

  2. FlashDuty Changelog 2023-10-30 | 告警路由与 Slack 应用

    FlashDuty:一站式告警响应平台,前往此地址免费体验! 告警路由 什么是告警路由? FlashDuty已经与Zabbix.Prometheus等监控系统实现无缝集成,通过一个简单的webhook ...

  3. k8s数据持久化

    前面的学习,我们已经基本完成了在k8s中部署一个web服务,运行pod.创建service.创建ingress对外提供域名的七层代理. 下一个环境就得去关注应用部署后的数据存储问题,容器化如何管理,k ...

  4. 企业快速落地IT服务管理体系的六大关键步骤

    许多企业在实施信息化战略时,一味地追求"技术高消费"而忽视了对信息技术的管理和内部业务流程的变革,侧重点仍然只是事后的技术支持和故障解决方面,随着企业对于信息技术的依赖程度的加重, ...

  5. Interceptor拦截器demo

    Interceptor拦截器demo ##接口测试类 @RestController public class TestController { @RequestMapping(value = &qu ...

  6. SpringBoot 3.x 结合 Swagger3 (Knife4j )踩坑实录

    SpringBoot 3.x + Swagger3 踩坑实录 我的是springboot 版本是:3.2.2 <parent> <groupId>org.springframe ...

  7. js-对象创建

    哥被逼得要当全栈工程师,今天练习了下各种对象的创建方式.代码较多参考了https://www.cnblogs.com/ImmortalWang/p/10517091.html 为了方便测试,整合了一个 ...

  8. 17-Docker镜像和容器操作

    镜像 拉取镜像(下载镜像) 镜像是层次型的,拉取的时候会按照各层分别拉取. 每一个镜像都有自己的散列值,用来唯一标记一层镜像,可以用来判断本地是否已经拉取过此镜像层,如果已经拉取,则直接使用. doc ...

  9. Python str 转 b’二进制串

    用raw_unique_escape来编码无义意的二进制串 bytes(strtext, encoding='raw_unique_escape')

  10. “进口”双核A53@1.4GHz仅188元起,超高性价比!“邮票孔”AM62x工业核心板,正式发布!

    创龙科技作为TI官方合作伙伴,在2022年9月即推出搭载TI最新明星处理器AM62x的工业核心板-SOM-TL62x(B2B版本).为了让工业客户进一步降低产品成本,并提高产品连接的可靠性,我们再次推 ...