浏览代码

pms 瑞鹰 设备利用率

zhangcl 9 小时之前
父节点
当前提交
21d725c422

+ 75 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotrydailyreport/IotRyDailyReportController.java

@@ -13,13 +13,16 @@ import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
 import cn.iocoder.yudao.framework.datapermission.core.util.DataPermissionUtils;
 import cn.iocoder.yudao.framework.excel.core.util.ExcelUtils;
 import cn.iocoder.yudao.framework.tenant.core.util.TenantUtils;
+import cn.iocoder.yudao.module.pms.controller.admin.depttype.vo.IotDeptTypePageReqVO;
 import cn.iocoder.yudao.module.pms.controller.admin.iotprojectinfo.vo.IotProjectInfoPageReqVO;
 import cn.iocoder.yudao.module.pms.controller.admin.iotprojecttask.vo.IotProjectTaskPageReqVO;
 import cn.iocoder.yudao.module.pms.controller.admin.iotrydailyreport.vo.*;
+import cn.iocoder.yudao.module.pms.dal.dataobject.depttype.IotDeptTypeDO;
 import cn.iocoder.yudao.module.pms.dal.dataobject.iotprojectinfo.IotProjectInfoDO;
 import cn.iocoder.yudao.module.pms.dal.dataobject.iotprojecttask.IotProjectTaskDO;
 import cn.iocoder.yudao.module.pms.dal.dataobject.iotprojecttaskattrs.IotTaskAttrModelProperty;
 import cn.iocoder.yudao.module.pms.dal.dataobject.iotrydailyreport.IotRyDailyReportDO;
+import cn.iocoder.yudao.module.pms.dal.mysql.depttype.IotDeptTypeMapper;
 import cn.iocoder.yudao.module.pms.dal.mysql.iotrydailyreport.IotRyDailyReportMapper;
 import cn.iocoder.yudao.module.pms.service.iotprojectinfo.IotProjectInfoService;
 import cn.iocoder.yudao.module.pms.service.iotprojecttask.IotProjectTaskService;
@@ -72,6 +75,8 @@ public class IotRyDailyReportController {
     private IotRyDailyReportMapper iotRyDailyReportMapper;
     @Resource
     private DictDataService dictDataService;
+    @Resource
+    private IotDeptTypeMapper iotDeptTypeMapper;
 
     @PostMapping("/create")
     @Operation(summary = "创建瑞鹰日报")
@@ -1428,6 +1433,74 @@ public class IotRyDailyReportController {
                 pageReqVO.setTaskIds(taskIds);
             }
         }
+
+        // 统计设备利用率
+        Long deptId = pageReqVO.getDeptId();
+        // 钻井或修井部门 队伍
+        List<Long> zjOrXjDeptIds = new ArrayList<>();
+        if (ObjUtil.isNotEmpty(deptId)) {
+            // 查询指定部门下所有子部门
+            Set<Long> childDeptIds = deptService.getChildDeptIdListFromCache(deptId);
+            Map<Long, DeptDO> allDeptPair = deptService.getDeptMap(childDeptIds);
+            // 钻井日报汇总 分母为 钻井施工队伍  修井日报汇总分母分母为修井施工队伍
+            // 1钻井  2修井
+            String projectClassification = pageReqVO.getProjectClassification();
+            // 查询钻井部门 修井 部门
+            IotDeptTypePageReqVO reqVO = new IotDeptTypePageReqVO();
+            if ("1".equals(projectClassification)) {
+                reqVO.setType("zj");
+            } else {
+                reqVO.setType("xj");
+            }
+            List<IotDeptTypeDO> deptTypes = iotDeptTypeMapper.selectList(reqVO);
+            if (CollUtil.isNotEmpty(deptTypes)) {
+                deptTypes.forEach(dept -> {
+                    zjOrXjDeptIds.add(dept.getDeptId());
+                });
+            }
+        }
+
+        // 统计设备利用率 查询非 dt zx 状态的日报
+        // 钻井:日报状态 过滤掉 ‘等停dt’    修井:日报状态过滤掉 ‘等停dt’、‘整修zx’
+        List<String> statuses = new ArrayList<>();
+        statuses.add("dt");
+        statuses.add("zx");
+        pageReqVO.setStatuses(statuses);
+        double rate = 0.0;
+        Integer reportCount = 0;
+        List<IotRyDailyReportDO> dailyReports = iotRyDailyReportMapper.dailyReports(pageReqVO);
+        if (CollUtil.isNotEmpty(dailyReports)) {
+            for (IotRyDailyReportDO dailyReport : dailyReports) {
+                if (zjOrXjDeptIds.contains(dailyReport.getDeptId())) {
+                    ++reportCount;
+                }
+            }
+        }
+
+        // 计算筛选时间范围内 指定部门的设备利用率
+        long daysCount = 0l;
+        if (ObjUtil.isNotEmpty(pageReqVO.getCreateTime()) && pageReqVO.getCreateTime().length >= 2) {
+            LocalDateTime start = pageReqVO.getCreateTime()[0];
+            LocalDateTime end = pageReqVO.getCreateTime()[1];
+            if (ObjUtil.isNotEmpty(start) && ObjUtil.isNotEmpty(end) && !end.isBefore(start)) {
+                // 使用ChronoUnit.DAYS.between计算天数差,并+1包含首尾两天
+                daysCount = ChronoUnit.DAYS.between(
+                        start.toLocalDate(),
+                        end.toLocalDate()
+                ) + 1;
+            }
+        }
+
+        // 所有项目部包含的队伍数量>0 并且 指定时间区间天数大于0
+        if (daysCount > 0 && zjOrXjDeptIds.size() > 0) {
+            // 当前项目部 设备利用率 公式 reportCount/(currentTeamNum*daysCount)
+            // 计算设备利用率(处理除数为0的情况)
+            rate = new BigDecimal((double) reportCount / (zjOrXjDeptIds.size() * daysCount))
+                    .setScale(4, RoundingMode.HALF_UP)  // 保留4位小数,四舍五入
+                    .doubleValue();
+        }
+
+        // 查询指定部门 指定时间范围内的日报
         List<IotRyDailyReportDO> list = iotRyDailyReportService.getIotRyDailyReportPage(pageReqVO).getList();
         Map<String, BigDecimal> result = new HashMap<>();
         // 总进尺
@@ -1521,6 +1594,8 @@ public class IotRyDailyReportController {
                 result.put("completedWells", completedWells);
             }
         }
+        // 设备利用率
+        result.put("utilizationRate", BigDecimal.valueOf(rate));
         return success(result);
     }
 

+ 2 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/iotrydailyreport/vo/IotRyDailyReportStatisticsRespVO.java

@@ -79,4 +79,6 @@ public class IotRyDailyReportStatisticsRespVO {
     @ExcelProperty("非生产时效")
     private String nonProductiveTimeStr;
 
+    @Schema(description = "设备利用率")
+    private BigDecimal utilizationRate;
 }

+ 1 - 1
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/controller/admin/stat/IotStaticController.java

@@ -2003,7 +2003,7 @@ public class IotStaticController {
         Map<Long, Set<Long>> projectTeamPair = new HashMap<>();
         if (CollUtil.isNotEmpty(allDeptPair)) {
             allDeptPair.forEach((deptId, dept) -> {
-                if (dept.getName().contains("项目部") ) {
+                if ("2".equals(dept.getType())) {
                     projectDeptIds.add(deptId);
                     projectDeptNames.add(dept.getName());
                     projectPair.put(deptId, dept.getName());

+ 0 - 44
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/mysql/iotrddailyreport/IotRdDailyReportMapper.java

@@ -24,50 +24,6 @@ import java.util.List;
 @Mapper
 public interface IotRdDailyReportMapper extends BaseMapperX<IotRdDailyReportDO> {
 
-    /* default PageResult<IotRdDailyReportDO> selectPage(IotRdDailyReportPageReqVO reqVO) {
-        return selectPage(reqVO, new LambdaQueryWrapperX<IotRdDailyReportDO>()
-                .eqIfPresent(IotRdDailyReportDO::getDeptId, reqVO.getDeptId())
-                .eqIfPresent(IotRdDailyReportDO::getProjectId, reqVO.getProjectId())
-                .eqIfPresent(IotRdDailyReportDO::getTaskId, reqVO.getTaskId())
-                .eqIfPresent(IotRdDailyReportDO::getProjectClassification, reqVO.getProjectClassification())
-                .eqIfPresent(IotRdDailyReportDO::getTechniqueIds, reqVO.getTechniqueIds())
-                .eqIfPresent(IotRdDailyReportDO::getDeviceIds, reqVO.getDeviceIds())
-                .betweenIfPresent(IotRdDailyReportDO::getStartTime, reqVO.getStartTime())
-                .betweenIfPresent(IotRdDailyReportDO::getEndTime, reqVO.getEndTime())
-                .eqIfPresent(IotRdDailyReportDO::getCumulativeWorkingWell, reqVO.getCumulativeWorkingWell())
-                .eqIfPresent(IotRdDailyReportDO::getCumulativeWorkingLayers, reqVO.getCumulativeWorkingLayers())
-                .eqIfPresent(IotRdDailyReportDO::getDailyPumpTrips, reqVO.getDailyPumpTrips())
-                .eqIfPresent(IotRdDailyReportDO::getDailyToolsSand, reqVO.getDailyToolsSand())
-                .eqIfPresent(IotRdDailyReportDO::getRunCount, reqVO.getRunCount())
-                .eqIfPresent(IotRdDailyReportDO::getBridgePlug, reqVO.getBridgePlug())
-                .eqIfPresent(IotRdDailyReportDO::getWaterVolume, reqVO.getWaterVolume())
-                .eqIfPresent(IotRdDailyReportDO::getHourCount, reqVO.getHourCount())
-                .eqIfPresent(IotRdDailyReportDO::getDailyFuel, reqVO.getDailyFuel())
-                .eqIfPresent(IotRdDailyReportDO::getDailyPowerUsage, reqVO.getDailyPowerUsage())
-                .betweenIfPresent(IotRdDailyReportDO::getProductionTime, reqVO.getProductionTime())
-                .betweenIfPresent(IotRdDailyReportDO::getNonProductionTime, reqVO.getNonProductionTime())
-                .eqIfPresent(IotRdDailyReportDO::getRdNptReason, reqVO.getRdNptReason())
-                .betweenIfPresent(IotRdDailyReportDO::getConstructionStartDate, reqVO.getConstructionStartDate())
-                .betweenIfPresent(IotRdDailyReportDO::getConstructionEndDate, reqVO.getConstructionEndDate())
-                .eqIfPresent(IotRdDailyReportDO::getProductionStatus, reqVO.getProductionStatus())
-                .eqIfPresent(IotRdDailyReportDO::getExternalRental, reqVO.getExternalRental())
-                .eqIfPresent(IotRdDailyReportDO::getNextPlan, reqVO.getNextPlan())
-                .eqIfPresent(IotRdDailyReportDO::getRdStatus, reqVO.getRdStatus())
-                .eqIfPresent(IotRdDailyReportDO::getMalfunction, reqVO.getMalfunction())
-                .betweenIfPresent(IotRdDailyReportDO::getFaultDowntime, reqVO.getFaultDowntime())
-                .eqIfPresent(IotRdDailyReportDO::getPersonnel, reqVO.getPersonnel())
-                .eqIfPresent(IotRdDailyReportDO::getTotalStaffNum, reqVO.getTotalStaffNum())
-                .eqIfPresent(IotRdDailyReportDO::getLeaveStaffNum, reqVO.getLeaveStaffNum())
-                .eqIfPresent(IotRdDailyReportDO::getExtProperty, reqVO.getExtProperty())
-                .eqIfPresent(IotRdDailyReportDO::getSort, reqVO.getSort())
-                .eqIfPresent(IotRdDailyReportDO::getRemark, reqVO.getRemark())
-                .eqIfPresent(IotRdDailyReportDO::getStatus, reqVO.getStatus())
-                .eqIfPresent(IotRdDailyReportDO::getProcessInstanceId, reqVO.getProcessInstanceId())
-                .eqIfPresent(IotRdDailyReportDO::getAuditStatus, reqVO.getAuditStatus())
-                .betweenIfPresent(IotRdDailyReportDO::getCreateTime, reqVO.getCreateTime())
-                .orderByDesc(IotRdDailyReportDO::getId));
-    } */
-
     default PageResult<IotRdDailyReportDO> selectPage(IotRdDailyReportPageReqVO reqVO) {
         LambdaQueryWrapperX<IotRdDailyReportDO> wrapper = buildCommonQuery(reqVO)
                 .eqIfPresent(IotRdDailyReportDO::getProjectId, reqVO.getProjectId());

+ 10 - 0
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/dal/mysql/iotrydailyreport/IotRyDailyReportMapper.java

@@ -77,6 +77,16 @@ public interface IotRyDailyReportMapper extends BaseMapperX<IotRyDailyReportDO>
                 .orderByDesc(IotRyDailyReportDO::getCreateTime)
                 .orderByAsc(IotRyDailyReportDO::getId);
 
+        // 处理 statuses 条件:当 statuses 有值时,查询 rigStatus 或 repairStatus 不在 statuses 中的数据
+        Collection<String> statuses = reqVO.getStatuses();
+        if (CollUtil.isNotEmpty(statuses)) { // 判断集合非空
+            queryWrapper.and(wrapper -> wrapper
+                    .notIn(IotRyDailyReportDO::getRigStatus, statuses) // rigStatus 不在集合中
+                    .or() // 或
+                    .notIn(IotRyDailyReportDO::getRepairStatus, statuses) // repairStatus 不在集合中
+            );
+        }
+
         // 单独处理 projectClassification 条件
         if ("1".equals(projectClassification)) {
             // 当值为 "1" 时,查询 project_classification 为 "1" 或空字符串的记录

+ 141 - 15
yudao-module-pms/yudao-module-pms-biz/src/main/java/cn/iocoder/yudao/module/pms/service/iotrydailyreport/IotRyDailyReportServiceImpl.java

@@ -488,10 +488,10 @@ public class IotRyDailyReportServiceImpl implements IotRyDailyReportService {
                 result = statisticsByProjectDept(pageReqVO, dailyReports, pageReqVO.getDeptId());
             } else if ("2".equals(selectedDept.getType())) {
                 // 以队伍为维度汇总数据
-                result = statisticsByProjectDepartment(pageReqVO, dailyReports, pageReqVO.getDeptId());
+                result = statisticsByProjectDepartment(pageReqVO, dailyReports);
             } else if ("3".equals(selectedDept.getType())) {
                 // 显示单个队伍的汇总数据
-                result = statisticsByProjectDepartment(pageReqVO, dailyReports, pageReqVO.getDeptId());
+                result = statisticsByProjectDepartment(pageReqVO, dailyReports);
             } else {
                 // 点击的部门没有类型 判断部门下的是否包含 项目部类型部门 新疆分公司
                 // 以项目部为维度汇总数据
@@ -1018,15 +1018,28 @@ public class IotRyDailyReportServiceImpl implements IotRyDailyReportService {
         Map<Long, List<BigDecimal>> cumulativeNonProductionTimePair = new HashMap<>();
         // key队伍id/项目部id   value非生产时效
         Map<Long, BigDecimal> cumulativeNonProductionPair = new HashMap<>();
+        // key队伍id/项目部id   value设备利用率
+        Map<Long, BigDecimal> deviceUtilizationPair = new HashMap<>();
 
-        // key部门id-任务id
-        Set<String> deptTaskConstrcts = new HashSet<>();
-        // key部门id-任务id
-        Set<String> deptTaskFinishes = new HashSet<>();
+        // 钻井或修井部门 队伍
+        List<Long> zjOrXjDeptIds = new ArrayList<>();
+        // 1钻井  2修井
+        String projectClassification = pageReqVO.getProjectClassification();
+        // 查询钻井部门 修井 部门
+        IotDeptTypePageReqVO deptTypeReqVO = new IotDeptTypePageReqVO();
+        if ("1".equals(projectClassification)) {
+            deptTypeReqVO.setType("zj");
+        } else {
+            deptTypeReqVO.setType("xj");
+        }
+        List<IotDeptTypeDO> deptTypes = iotDeptTypeMapper.selectList(deptTypeReqVO);
+        if (CollUtil.isNotEmpty(deptTypes)) {
+            deptTypes.forEach(dept -> {
+                zjOrXjDeptIds.add(dept.getDeptId());
+            });
+        }
 
-        // 以项目部为维度统计数据
-        // 找到所有项目部与队伍的对应关系
-        // 查询指定根部门下的所有子部门
+        // 以项目部为维度统计数据 找到所有项目部与队伍的对应关系 查询指定根部门下的所有子部门
         Set<Long> allRhChildDeptIds = deptService.getChildDeptIdListFromCache(rootDeptId);
         DeptListReqVO reqVO = new DeptListReqVO();
         reqVO.setDeptIds(allRhChildDeptIds);
@@ -1042,12 +1055,38 @@ public class IotRyDailyReportServiceImpl implements IotRyDailyReportService {
             teamProjectIdPair.put(dept.getId(), dept.getParentId());
         });
 
+        // key项目部id   value项目部包含的钻井or修井队伍id集合
+        Map<Long, Set<Long>> projectTeamPair = new HashMap<>();
+        // 筛选项目部下包含的队伍
+        depts.forEach(dept -> {
+            Long deptId = dept.getId();
+            Long parentId = dept.getParentId();
+            if (projectDeptIds.contains(parentId)) {
+                // 获得当前部门的上级项目部
+                projectDeptIds.forEach(projectDeptId -> {
+                    // 统计各钻井或修井项目部下队伍数量
+                    if (projectDeptId.equals(parentId) && zjOrXjDeptIds.contains(deptId)) {
+                        if (projectTeamPair.containsKey(projectDeptId)) {
+                            Set<Long> tempTeamIds = projectTeamPair.get(projectDeptId);
+                            tempTeamIds.add(deptId);
+                            projectTeamPair.put(projectDeptId, tempTeamIds);
+                        } else {
+                            Set<Long> tempTeamIds = new HashSet<>();
+                            tempTeamIds.add(deptId);
+                            projectTeamPair.put(projectDeptId, tempTeamIds);
+                        }
+                    }
+                });
+            }
+        });
+
         // key施工队伍id    value施工井数量
         Map<Long, Integer> totalTasksPair = new HashMap<>();
         // key施工队伍id    value完工井数量
         Map<Long, Integer> completedTasksPair = new HashMap<>();
         // key任务id   value额定生产时间
         Map<Long, BigDecimal> taskRatedProductionTimePair = new HashMap<>();
+
         if ("2".equals(pageReqVO.getProjectClassification())) {
             // 查询修井 累计施工井数 累计完工井数
             if (ObjUtil.isNotEmpty(pageReqVO.getCreateTime())) {
@@ -1081,9 +1120,28 @@ public class IotRyDailyReportServiceImpl implements IotRyDailyReportService {
             }
         }
 
+        // 统计各项目部的设备利用率
+        // key项目部id     value项目部包含的队伍指定时间区域内日报数量
+        Map<Long, Integer> projectReportPair = new HashMap<>();
+
         // 累计计算各项指标
         if (CollUtil.isNotEmpty(dailyReports)) {
             dailyReports.forEach(report -> {
+                // 统计各项目部的日报数量
+                if (CollUtil.isNotEmpty(projectTeamPair)) {
+                    projectTeamPair.forEach((projectDeptId, teamDeptIds) -> {
+                        if (teamDeptIds.contains(report.getDeptId())) {
+                            // 项目部日报数量
+                            if (projectReportPair.containsKey(projectDeptId)) {
+                                Integer tempCount = projectReportPair.get(projectDeptId);
+                                projectReportPair.put(projectDeptId, ++tempCount);
+                            } else {
+                                projectReportPair.put(projectDeptId, 1);
+                            }
+                        }
+                    });
+                }
+
                 if (ObjUtil.isNotEmpty(report.getDeptId()) && teamProjectIdPair.containsKey(report.getDeptId())) {
                     Long projectDeptId = teamProjectIdPair.get(report.getDeptId());
                     if (ObjUtil.isNotEmpty(projectDeptId) && projectDeptPair.containsKey(projectDeptId)) {
@@ -1201,7 +1259,6 @@ public class IotRyDailyReportServiceImpl implements IotRyDailyReportService {
                     cumulativeNonProductionPair.put(projectDeptId, nonProductionEfficiency);
                 });
             }
-
         }
 
         Long days;
@@ -1219,6 +1276,25 @@ public class IotRyDailyReportServiceImpl implements IotRyDailyReportService {
             days = 0l;
         }
 
+        // 计算各项目部的平均设备利用率
+        if (CollUtil.isNotEmpty(projectTeamPair)) {
+            projectTeamPair.forEach((projectDeptId, resultTeamIds) -> {
+                double rate = 0.0;
+                Integer currentTeamNum = resultTeamIds.size();
+                if (projectReportPair.containsKey(projectDeptId)) {
+                    Integer reportCount = projectReportPair.getOrDefault(projectDeptId, 0);
+                    // 当前项目部 设备利用率 公式 reportCount/(currentTeamNum * daysCount)
+                    // 计算设备利用率(处理除数为0的情况)
+                    if (currentTeamNum > 0 && days > 0) {
+                        rate = new BigDecimal((double) reportCount / (currentTeamNum * days))
+                                .setScale(4, RoundingMode.HALF_UP)  // 保留4位小数,四舍五入
+                                .doubleValue();
+                        deviceUtilizationPair.put(projectDeptId, BigDecimal.valueOf(rate));
+                    }
+                }
+            });
+        }
+
         // 生成返回的数据列表集合
         projectDeptPair.forEach((deptId, dept) -> {
             IotRyDailyReportStatisticsRespVO statistics = new IotRyDailyReportStatisticsRespVO();
@@ -1226,6 +1302,7 @@ public class IotRyDailyReportServiceImpl implements IotRyDailyReportService {
             statistics.setProjectDeptName(dept.getName());
             statistics.setSort(dept.getSort());
             statistics.setType("2");
+            statistics.setUtilizationRate(deviceUtilizationPair.get(deptId));
             statistics.setCumulativeFootage(cumulativeFootagePair.get(deptId));
             statistics.setCumulativeConstructWells(cumulativeConstructWellsPair.get(deptId));
             statistics.setCumulativeCompletedWells(cumulativeCompletedWellsPair.get(deptId));
@@ -1451,11 +1528,11 @@ public class IotRyDailyReportServiceImpl implements IotRyDailyReportService {
      * 按 队伍 维度统计数据
      * @param pageReqVO 日报数据请求对象
      * @param dailyReports 日报数据列表
-     * @param deptId 项目部ID 或 队伍id(塔河项目部 HY-A1)
+     * @param pageReqVO.deptId 项目部ID 或 队伍id(塔河项目部 HY-A1)
      * @return 队伍 维度统计结果列表
      */
     private List<IotRyDailyReportStatisticsRespVO> statisticsByProjectDepartment(IotRyDailyReportPageReqVO pageReqVO,
-                                                                                 List<IotRyDailyReportDO> dailyReports, Long deptId) {
+                                                                                 List<IotRyDailyReportDO> dailyReports) {
         List<IotRyDailyReportStatisticsRespVO> result = new ArrayList<>();
 
         Set<Long> projectDeptIds = new HashSet<>();
@@ -1482,13 +1559,33 @@ public class IotRyDailyReportServiceImpl implements IotRyDailyReportService {
         Map<Long, BigDecimal> cumulativeRatedTimePair = new HashMap<>();
         // key队伍id   value累计运行时效
         Map<Long, BigDecimal> cumulativeTransitTimePair = new HashMap<>();
+        // key队伍id/项目部id   value设备利用率
+        Map<Long, BigDecimal> deviceUtilizationPair = new HashMap<>();
+
+        // 钻井或修井部门 队伍
+        List<Long> zjOrXjDeptIds = new ArrayList<>();
+        // 1钻井  2修井
+        String projectClassification = pageReqVO.getProjectClassification();
+        // 查询钻井部门 修井 部门
+        IotDeptTypePageReqVO deptTypeReqVO = new IotDeptTypePageReqVO();
+        if ("1".equals(projectClassification)) {
+            deptTypeReqVO.setType("zj");
+        } else {
+            deptTypeReqVO.setType("xj");
+        }
+        List<IotDeptTypeDO> deptTypes = iotDeptTypeMapper.selectList(deptTypeReqVO);
+        if (CollUtil.isNotEmpty(deptTypes)) {
+            deptTypes.forEach(dept -> {
+                zjOrXjDeptIds.add(dept.getDeptId());
+            });
+        }
 
         // 以 队伍 为维度统计数据
         // 找到所有项目部与队伍的对应关系
         // 查询指定根部门下的所有子部门
-        Set<Long> allRhChildDeptIds = deptService.getChildDeptIdListFromCache(deptId);
+        Set<Long> allRhChildDeptIds = deptService.getChildDeptIdListFromCache(pageReqVO.getDeptId());
         DeptListReqVO reqVO = new DeptListReqVO();
-        allRhChildDeptIds.add(deptId);  // 查询某支队伍
+        allRhChildDeptIds.add(pageReqVO.getDeptId());  // 查询某支队伍
         reqVO.setDeptIds(allRhChildDeptIds);
         List<DeptDO> depts = deptService.getDeptList(reqVO);
 
@@ -1539,10 +1636,22 @@ public class IotRyDailyReportServiceImpl implements IotRyDailyReportService {
             }
         }
 
+        // 统计各队伍的设备利用率
+        // key队伍id     value队伍指定时间区域内日报数量
+        Map<Long, Integer> teamReportPair = new HashMap<>();
+
         // 累计计算各项指标
         if (CollUtil.isNotEmpty(dailyReports)) {
             dailyReports.forEach(report -> {
-                if (ObjUtil.isNotEmpty(report.getDeptId())) {
+                if (ObjUtil.isNotEmpty(report.getDeptId()) && zjOrXjDeptIds.contains(report.getDeptId())) {
+                    // 统计各个队伍的日报数量
+                    if (teamReportPair.containsKey(report.getDeptId())) {
+                        Integer tempCount = teamReportPair.get(report.getDeptId());
+                        teamReportPair.put(report.getDeptId(), ++tempCount);
+                    } else {
+                        teamReportPair.put(report.getDeptId(), 1);
+                    }
+
                     // 累计进尺
                     cumulativeFootagePair.merge(report.getDeptId(), report.getDailyFootage(), BigDecimal::add);
                     // 累计油耗
@@ -1597,6 +1706,22 @@ public class IotRyDailyReportServiceImpl implements IotRyDailyReportService {
             days = 0l;
         }
 
+        // 计算各队伍的平均设备利用率
+        if (CollUtil.isNotEmpty(teamReportPair)) {
+            teamReportPair.forEach((teamDeptId, reportCount) -> {
+                double rate = 0.0;
+                Integer currentTeamNum = 1;
+                // 当前项目部 设备利用率 公式 reportCount/(currentTeamNum * daysCount)
+                // 计算设备利用率(处理除数为0的情况)
+                if (currentTeamNum > 0 && days > 0) {
+                    rate = new BigDecimal((double) reportCount / (currentTeamNum * days))
+                            .setScale(4, RoundingMode.HALF_UP)  // 保留4位小数,四舍五入
+                            .doubleValue();
+                    deviceUtilizationPair.put(teamDeptId, BigDecimal.valueOf(rate));
+                }
+            });
+        }
+
         // 生成返回的数据列表集合
         teamDeptPair.forEach((teamDeptId, dept) -> {
             IotRyDailyReportStatisticsRespVO statistics = new IotRyDailyReportStatisticsRespVO();
@@ -1604,6 +1729,7 @@ public class IotRyDailyReportServiceImpl implements IotRyDailyReportService {
             statistics.setTeamName(dept.getName());
             statistics.setSort(dept.getSort());
             statistics.setType("3");
+            statistics.setUtilizationRate(deviceUtilizationPair.get(teamDeptId));
             statistics.setCumulativeFootage(cumulativeFootagePair.get(teamDeptId));
             statistics.setCumulativeConstructWells(totalTasksPair.get(teamDeptId));
             statistics.setCumulativeCompletedWells(completedTasksPair.get(teamDeptId));