From c9f05d722f649726e5661e90e129757f55eb4c68 Mon Sep 17 00:00:00 2001 From: ll <1079863556@qq.com> Date: Wed, 13 Aug 2025 18:55:55 +0800 Subject: [PATCH] =?UTF-8?q?=E5=A5=B6=E4=BA=A7=E9=87=8F=E5=88=86=E6=9E=90?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../NpSheepMilkAnalysisController.java | 51 +--- .../domain/NpSheepMilkAnalysis.java | 42 ++- .../mapper/NpSheepMilkAnalysisMapper.java | 29 +- .../service/INpSheepMilkAnalysisService.java | 10 +- .../impl/NpSheepMilkAnalysisServiceImpl.java | 277 ++++++++++++++++-- .../NpSheepMilkAnalysisMapper.xml | 180 +++--------- 6 files changed, 380 insertions(+), 209 deletions(-) diff --git a/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/controller/NpSheepMilkAnalysisController.java b/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/controller/NpSheepMilkAnalysisController.java index 0c2955d..3e4f07a 100644 --- a/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/controller/NpSheepMilkAnalysisController.java +++ b/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/controller/NpSheepMilkAnalysisController.java @@ -8,12 +8,14 @@ import com.zhyc.common.enums.BusinessType; import com.zhyc.common.utils.poi.ExcelUtil; import com.zhyc.module.dairyProducts.domain.NpSheepMilkAnalysis; import com.zhyc.module.dairyProducts.service.INpSheepMilkAnalysisService; - import org.springframework.beans.factory.annotation.Autowired; import org.springframework.web.bind.annotation.*; import java.util.List; +/** + * 只保留:分页列表(只读) + 单条查询 + 导出 + */ @RestController @RequestMapping("/dairyProducts/sheepMilkAnalysis") public class NpSheepMilkAnalysisController extends BaseController { @@ -22,58 +24,33 @@ public class NpSheepMilkAnalysisController extends BaseController { private INpSheepMilkAnalysisService npSheepMilkAnalysisService; /** - * 查询奶产量分析列表 + * 查询奶产量分析列表(只读,分页) + * 支持参数 manageEarTag(耳号模糊) 和 screenDays(筛选天数) */ @GetMapping("/list") public TableDataInfo list(NpSheepMilkAnalysis analysis) { - startPage(); + startPage(); // 使用 PageHelper 分页(注意 service 中第一个 DB 调用是 distinct sheep id) List list = npSheepMilkAnalysisService.selectNpSheepMilkAnalysisList(analysis); return getDataTable(list); } /** - * 获取单个分析记录详细信息 + * 获取单个分析记录详细信息(按 sheepId) */ - @GetMapping(value = "/{id}") - public AjaxResult getInfo(@PathVariable("id") Long id) { - return AjaxResult.success(npSheepMilkAnalysisService.selectNpSheepMilkAnalysisById(id)); - } - /** - * 新增奶产量分析记录 - */ - @Log(title = "奶产量分析", businessType = BusinessType.INSERT) - @PostMapping - public AjaxResult add(@RequestBody NpSheepMilkAnalysis analysis) { - return toAjax(npSheepMilkAnalysisService.insertNpSheepMilkAnalysis(analysis)); + @GetMapping(value = "/{sheepId}") + public AjaxResult getInfo(@PathVariable("sheepId") String sheepId) { + return AjaxResult.success(npSheepMilkAnalysisService.selectNpSheepMilkAnalysisBySheepId(sheepId)); } /** - * 修改奶产量分析记录 + * 导出奶产量分析记录(Excel) + * 支持 manageEarTag 与 screenDays 两个查询条件 */ - @Log(title = "奶产量分析", businessType = BusinessType.UPDATE) - @PutMapping - public AjaxResult edit(@RequestBody NpSheepMilkAnalysis analysis) { - return toAjax(npSheepMilkAnalysisService.updateNpSheepMilkAnalysis(analysis)); - } - - /** - * 删除奶产量分析记录 - */ - @Log(title = "奶产量分析", businessType = BusinessType.DELETE) - @DeleteMapping("/{ids}") - public AjaxResult remove(@PathVariable Long[] ids) { - return toAjax(npSheepMilkAnalysisService.deleteNpSheepMilkAnalysisByIds(ids)); - } - - /** - * 导出奶产量分析记录 - */ - @Log(title = "奶产量分析", businessType = BusinessType.EXPORT) + @Log(title = "奶产量分析 导出", businessType = BusinessType.EXPORT) @GetMapping("/export") public AjaxResult export(NpSheepMilkAnalysis analysis) { List list = npSheepMilkAnalysisService.selectNpSheepMilkAnalysisList(analysis); ExcelUtil util = new ExcelUtil<>(NpSheepMilkAnalysis.class); - return util.exportExcel(list, "奶产量分析数据"); + return util.exportExcel(list, "羊奶产量分析数据"); } } - diff --git a/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/domain/NpSheepMilkAnalysis.java b/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/domain/NpSheepMilkAnalysis.java index 05972f6..0573a0d 100644 --- a/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/domain/NpSheepMilkAnalysis.java +++ b/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/domain/NpSheepMilkAnalysis.java @@ -1,34 +1,64 @@ package com.zhyc.module.dairyProducts.domain; import java.util.Date; + public class NpSheepMilkAnalysis { + // 唯一键(可用于前端 row-key) private String sheepId; + + // 耳号(从 sheep_file.bs_manage_tags) private String manageEarTag; + private String variety; + + // 最高校正胎次的挤奶开始时间 & 干奶时间 private Date milkingStartTime; private Date dryEndTime; + + // 挤奶天数(该胎次) private Integer milkingDays; + + // 前端传入的筛选天数(screenDays) + private Integer screenDays; + + // 分析天数(若你有不同命名,可忽略) private Integer analysisDays; + + // 校正后最大胎次(即校正奶量之和最大的胎次) private Integer maxParity; + + // 最高校正胎次区间内的系统奶量与校正奶量(按筛选窗口) private Double sumSystemMilk; private Double sumCorrectedMilk; + + // 校正日平均奶量(按 min(挤奶天数, 筛选天数)) private Double avgCorrectedDaily; + + // 各胎次总奶量(校正) private Double sumParity1Milk; private Double sumParity2Milk; private Double sumParity3Milk; private Double sumParity4Milk; + + // 各胎次日平均(按规则) private Double avgParity1Daily; private Double avgParity2Daily; private Double avgParity3Daily; private Double avgParity4Daily; + + // 泌乳天数(sheep_file.lactation_day) private Integer lactationDays; + + // 过去 7 / 14 / 30 日平均(系统奶量) private Double avgLast7Milk; - private Double avgLast7Corrected; + private Double avgLast7Corrected; // = avgLast7Milk * weightCoefficient (默认 1.0) private Double avgLast14Milk; private Double avgLast30Milk; + + // 羊只基础信息(来自 sheep_file) private String sheepCategory; private Date birthday; - private Integer parity; + private Integer parity; // 当前胎次 private Integer monthAge; private Double currentWeight; private String breedStatus; @@ -36,12 +66,16 @@ public class NpSheepMilkAnalysis { private String motherManageTags; private String ranchName; private String family; + + // 母亲相关字段(由已计算的母亲分析结果中取值) private Integer motherMilkingDays; private Double motherSumCorrected; private Integer motherMaxParity; private Double motherAvgCorrectedDaily; + private Date lastUpdate; + // getters and setters public String getSheepId() { return sheepId; } public void setSheepId(String sheepId) { this.sheepId = sheepId; } @@ -60,6 +94,9 @@ public class NpSheepMilkAnalysis { public Integer getMilkingDays() { return milkingDays; } public void setMilkingDays(Integer milkingDays) { this.milkingDays = milkingDays; } + public Integer getScreenDays() { return screenDays; } + public void setScreenDays(Integer screenDays) { this.screenDays = screenDays; } + public Integer getAnalysisDays() { return analysisDays; } public void setAnalysisDays(Integer analysisDays) { this.analysisDays = analysisDays; } @@ -159,4 +196,3 @@ public class NpSheepMilkAnalysis { public Date getLastUpdate() { return lastUpdate; } public void setLastUpdate(Date lastUpdate) { this.lastUpdate = lastUpdate; } } - diff --git a/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/mapper/NpSheepMilkAnalysisMapper.java b/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/mapper/NpSheepMilkAnalysisMapper.java index f330707..002e009 100644 --- a/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/mapper/NpSheepMilkAnalysisMapper.java +++ b/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/mapper/NpSheepMilkAnalysisMapper.java @@ -1,19 +1,36 @@ package com.zhyc.module.dairyProducts.mapper; import com.zhyc.module.dairyProducts.domain.NpSheepMilkAnalysis; +import org.apache.ibatis.annotations.Param; + import java.util.List; +import java.util.Map; public interface NpSheepMilkAnalysisMapper { - NpSheepMilkAnalysis selectNpSheepMilkAnalysisById(Long id); + /** + * 按筛选天数 screenDays 统计并返回所有羊只的奶产量分析 + */ + List selectAnalysisForExport(@Param("screenDays") Integer screenDays); - List selectNpSheepMilkAnalysisList(NpSheepMilkAnalysis analysis); + /** + * 根据羊只ID查询羊只奶产量分析信息,返回Map结构 + */ + Map selectNpSheepMilkAnalysisBySheepId(@Param("sheepId") String sheepId); - int insertNpSheepMilkAnalysis(NpSheepMilkAnalysis analysis); + /** + * 根据管理耳标筛选,返回distinct的sheepId列表 + */ + List selectDistinctSheepIds(@Param("manageEarTag") String manageEarTag); - int updateNpSheepMilkAnalysis(NpSheepMilkAnalysis analysis); + /** + * 根据羊只ID查询羊只档案信息,返回Map结构 + */ + Map selectSheepFileBySheepId(@Param("sheepId") String sheepId); - int deleteNpSheepMilkAnalysisById(Long id); + /** + * 根据羊只ID查询挤奶班次数据,返回List + */ + List> selectMilkRecordsBySheepId(@Param("sheepId") String sheepId); - int deleteNpSheepMilkAnalysisByIds(Long[] ids); } diff --git a/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/service/INpSheepMilkAnalysisService.java b/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/service/INpSheepMilkAnalysisService.java index 7750a5f..8760789 100644 --- a/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/service/INpSheepMilkAnalysisService.java +++ b/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/service/INpSheepMilkAnalysisService.java @@ -5,16 +5,8 @@ import java.util.List; public interface INpSheepMilkAnalysisService { - NpSheepMilkAnalysis selectNpSheepMilkAnalysisById(Long id); + NpSheepMilkAnalysis selectNpSheepMilkAnalysisBySheepId(String sheepId); List selectNpSheepMilkAnalysisList(NpSheepMilkAnalysis analysis); - int insertNpSheepMilkAnalysis(NpSheepMilkAnalysis analysis); - - int updateNpSheepMilkAnalysis(NpSheepMilkAnalysis analysis); - - int deleteNpSheepMilkAnalysisById(Long id); - - int deleteNpSheepMilkAnalysisByIds(Long[] ids); } - diff --git a/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/service/impl/NpSheepMilkAnalysisServiceImpl.java b/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/service/impl/NpSheepMilkAnalysisServiceImpl.java index c2476ee..161a381 100644 --- a/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/service/impl/NpSheepMilkAnalysisServiceImpl.java +++ b/zhyc-module/src/main/java/com/zhyc/module/dairyProducts/service/impl/NpSheepMilkAnalysisServiceImpl.java @@ -1,12 +1,17 @@ package com.zhyc.module.dairyProducts.service.impl; -import java.util.List; - -import com.zhyc.module.dairyProducts.mapper.NpSheepMilkAnalysisMapper; import com.zhyc.module.dairyProducts.domain.NpSheepMilkAnalysis; +import com.zhyc.module.dairyProducts.mapper.NpSheepMilkAnalysisMapper; import com.zhyc.module.dairyProducts.service.INpSheepMilkAnalysisService; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; +import org.springframework.util.CollectionUtils; + +import java.time.LocalDate; +import java.time.ZoneId; +import java.time.temporal.ChronoUnit; +import java.util.*; +import java.util.stream.Collectors; @Service public class NpSheepMilkAnalysisServiceImpl implements INpSheepMilkAnalysisService { @@ -14,34 +19,268 @@ public class NpSheepMilkAnalysisServiceImpl implements INpSheepMilkAnalysisServi @Autowired private NpSheepMilkAnalysisMapper npSheepMilkAnalysisMapper; + // 将 Rec 定义为静态内部类 + private static class Rec { + LocalDate date; + double systemMilk; + double correctedMilk; + int parity; + } + + // 将 ParityStat 定义为静态内部类 + private static class ParityStat { + int parity; + double sumCorrected; + double sumSystem; + LocalDate first; + LocalDate last; + long days; + } + @Override - public NpSheepMilkAnalysis selectNpSheepMilkAnalysisById(Long id) { - return npSheepMilkAnalysisMapper.selectNpSheepMilkAnalysisById(id); + public NpSheepMilkAnalysis selectNpSheepMilkAnalysisBySheepId(String sheepId) { + Map map = npSheepMilkAnalysisMapper.selectNpSheepMilkAnalysisBySheepId(sheepId); + if (map == null) return null; + NpSheepMilkAnalysis ana = new NpSheepMilkAnalysis(); + ana.setSheepId(sheepId); + ana.setManageEarTag((String) map.get("manageEarTag")); + return ana; } @Override public List selectNpSheepMilkAnalysisList(NpSheepMilkAnalysis analysis) { - return npSheepMilkAnalysisMapper.selectNpSheepMilkAnalysisList(analysis); + int screenDays = (analysis != null && analysis.getScreenDays() != null) ? analysis.getScreenDays() : 100; + String manageEarTagFilter = (analysis != null) ? analysis.getManageEarTag() : null; + + List sheepIds = npSheepMilkAnalysisMapper.selectDistinctSheepIds(manageEarTagFilter); + if (CollectionUtils.isEmpty(sheepIds)) return Collections.emptyList(); + + List resultList = new ArrayList<>(); + Map mapByManageTag = new HashMap<>(); + + for (String sheepId : sheepIds) { + Map sf = npSheepMilkAnalysisMapper.selectSheepFileBySheepId(sheepId); + List> records = npSheepMilkAnalysisMapper.selectMilkRecordsBySheepId(sheepId); + + if (records == null || records.isEmpty()) { + NpSheepMilkAnalysis emptyAna = new NpSheepMilkAnalysis(); + emptyAna.setSheepId(sheepId); + if (sf != null) { + emptyAna.setManageEarTag((String) sf.get("manageEarTag")); + emptyAna.setVariety((String) sf.get("variety")); + emptyAna.setLactationDays(toInteger(sf.get("lactationDay"))); + emptyAna.setSheepCategory((String) sf.get("sheepType")); + emptyAna.setBirthday(convertToDate(sf.get("birthday"))); + emptyAna.setParity(toInteger(sf.get("currentParity"))); + emptyAna.setMonthAge(toInteger(sf.get("monthAge"))); + emptyAna.setCurrentWeight(toDouble(sf.get("currentWeight"))); + emptyAna.setBreedStatus((String) sf.get("breedStatus")); + emptyAna.setFatherManageTags((String) sf.get("fatherManageTags")); + emptyAna.setMotherManageTags((String) sf.get("motherManageTags")); + emptyAna.setRanchName((String) sf.get("ranchName")); + emptyAna.setFamily((String) sf.get("family")); + } + resultList.add(emptyAna); + mapByManageTag.put(emptyAna.getManageEarTag(), emptyAna); + continue; + } + + // 使用静态内部类 Rec + List recs = new ArrayList<>(); + for (Map r : records) { + Rec rr = new Rec(); + rr.date = toLocalDate(r.get("classDate")); + rr.systemMilk = toDouble(r.get("systemMilk")); + rr.correctedMilk = toDouble(r.get("correctedMilk")); + rr.parity = (r.get("parity") == null) ? 0 : Integer.parseInt(String.valueOf(r.get("parity"))); + recs.add(rr); + } + + Map> byParity = recs.stream().collect(Collectors.groupingBy(r -> r.parity)); + + // 使用静态内部类 ParityStat + List parityStats = new ArrayList<>(); + for (Map.Entry> e : byParity.entrySet()) { + List list = e.getValue(); + double sumCorr = list.stream().mapToDouble(x -> x.correctedMilk).sum(); + double sumSys = list.stream().mapToDouble(x -> x.systemMilk).sum(); + LocalDate first = list.stream().map(x -> x.date).min(LocalDate::compareTo).get(); + LocalDate last = list.stream().map(x -> x.date).max(LocalDate::compareTo).get(); + long days = ChronoUnit.DAYS.between(first, last) + 1; + ParityStat ps = new ParityStat(); + ps.parity = e.getKey(); + ps.sumCorrected = sumCorr; + ps.sumSystem = sumSys; + ps.first = first; + ps.last = last; + ps.days = Math.max(days, 1); + parityStats.add(ps); + } + + parityStats.sort(Comparator.comparingDouble((ParityStat p) -> p.sumCorrected).reversed() + .thenComparingInt(p -> p.parity)); + ParityStat maxParityStat = parityStats.get(0); + + LocalDate windowStart = maxParityStat.first; + LocalDate windowEndByDays = windowStart.plusDays(screenDays - 1); + LocalDate actualWindowEnd = (maxParityStat.last.isBefore(windowEndByDays)) ? maxParityStat.last : windowEndByDays; + + double sumSystemWindow = recs.stream() + .filter(r -> r.parity == maxParityStat.parity && !r.date.isBefore(windowStart) && !r.date.isAfter(actualWindowEnd)) + .mapToDouble(r -> r.systemMilk).sum(); + + double sumCorrectedWindow = recs.stream() + .filter(r -> r.parity == maxParityStat.parity && !r.date.isBefore(windowStart) && !r.date.isAfter(actualWindowEnd)) + .mapToDouble(r -> r.correctedMilk).sum(); + + long milkingDays = maxParityStat.days; + long denominator = Math.min(milkingDays, screenDays); + double avgCorrectedDaily = (denominator > 0) ? (sumCorrectedWindow / (double) denominator) : 0.0; + + double sumParity1 = parityStats.stream().filter(p -> p.parity == 1).mapToDouble(p -> p.sumCorrected).sum(); + double sumParity2 = parityStats.stream().filter(p -> p.parity == 2).mapToDouble(p -> p.sumCorrected).sum(); + double sumParity3 = parityStats.stream().filter(p -> p.parity == 3).mapToDouble(p -> p.sumCorrected).sum(); + double sumParity4 = parityStats.stream().filter(p -> p.parity == 4).mapToDouble(p -> p.sumCorrected).sum(); + + // 你之前的 computeParityAvg 方法里没实现,保留调用0 + double avgP1 = computeParityAvg(parityStats, 1, screenDays); + double avgP2 = computeParityAvg(parityStats, 2, screenDays); + double avgP3 = computeParityAvg(parityStats, 3, screenDays); + double avgP4 = computeParityAvg(parityStats, 4, screenDays); + + LocalDate lastDate = recs.stream().map(r -> r.date).max(LocalDate::compareTo).get(); + double avgLast7 = computeLastNDaysAvg(recs, lastDate, 7); + double avgLast14 = computeLastNDaysAvg(recs, lastDate, 14); + double avgLast30 = computeLastNDaysAvg(recs, lastDate, 30); + + double weightCoefficient = 1.0; + if (sf != null && sf.get("weighCoefficient") != null) { + weightCoefficient = toDouble(sf.get("weighCoefficient")); + } + double avgLast7Corrected = avgLast7 * weightCoefficient; + + NpSheepMilkAnalysis ana = new NpSheepMilkAnalysis(); + ana.setSheepId(sheepId); + ana.setManageEarTag(sf == null ? null : (String) sf.get("manageEarTag")); + ana.setVariety(sf == null ? null : (String) sf.get("variety")); + ana.setMilkingStartTime(toDate(windowStart)); + ana.setDryEndTime(toDate(maxParityStat.last)); + ana.setMilkingDays((int) milkingDays); + ana.setScreenDays(screenDays); + ana.setMaxParity(maxParityStat.parity); + ana.setSumSystemMilk(sumSystemWindow); + ana.setSumCorrectedMilk(sumCorrectedWindow); + ana.setAvgCorrectedDaily(avgCorrectedDaily); + ana.setSumParity1Milk(sumParity1); + ana.setSumParity2Milk(sumParity2); + ana.setSumParity3Milk(sumParity3); + ana.setSumParity4Milk(sumParity4); + ana.setAvgParity1Daily(avgP1); + ana.setAvgParity2Daily(avgP2); + ana.setAvgParity3Daily(avgP3); + ana.setAvgParity4Daily(avgP4); + ana.setLactationDays(toInteger(sf == null ? null : sf.get("lactationDay"))); + ana.setAvgLast7Milk(avgLast7); + ana.setAvgLast7Corrected(avgLast7Corrected); + ana.setAvgLast14Milk(avgLast14); + ana.setAvgLast30Milk(avgLast30); + + if (sf != null) { + ana.setSheepCategory((String) sf.get("sheepType")); + ana.setBirthday(convertToDate(sf.get("birthday"))); + ana.setParity(toInteger(sf.get("currentParity"))); + ana.setMonthAge(toInteger(sf.get("monthAge"))); + ana.setCurrentWeight(toDouble(sf.get("currentWeight"))); + ana.setBreedStatus((String) sf.get("breedStatus")); + ana.setFatherManageTags((String) sf.get("fatherManageTags")); + ana.setMotherManageTags((String) sf.get("motherManageTags")); + ana.setRanchName((String) sf.get("ranchName")); + ana.setFamily((String) sf.get("family")); + } + + ana.setLastUpdate(toDate(lastDate)); + + resultList.add(ana); + mapByManageTag.put(ana.getManageEarTag(), ana); + } + + // 填充母亲相关字段 + for (NpSheepMilkAnalysis a : resultList) { + String motherTag = a.getMotherManageTags(); + if (motherTag != null && mapByManageTag.containsKey(motherTag)) { + NpSheepMilkAnalysis mom = mapByManageTag.get(motherTag); + a.setMotherMilkingDays(mom.getMilkingDays()); + a.setMotherSumCorrected(mom.getSumCorrectedMilk()); + a.setMotherMaxParity(mom.getMaxParity()); + a.setMotherAvgCorrectedDaily(mom.getAvgCorrectedDaily()); + } + } + + return resultList; } - @Override - public int insertNpSheepMilkAnalysis(NpSheepMilkAnalysis analysis) { - return npSheepMilkAnalysisMapper.insertNpSheepMilkAnalysis(analysis); + private static Date convertToDate(Object obj) { + if (obj == null) return null; + if (obj instanceof Date) { + return (Date) obj; + } + if (obj instanceof java.sql.Date) { + return new Date(((java.sql.Date) obj).getTime()); + } + return null; } - @Override - public int updateNpSheepMilkAnalysis(NpSheepMilkAnalysis analysis) { - return npSheepMilkAnalysisMapper.updateNpSheepMilkAnalysis(analysis); + private static LocalDate toLocalDate(Object obj) { + if (obj == null) return null; + if (obj instanceof java.sql.Date) { + return ((java.sql.Date) obj).toLocalDate(); + } + if (obj instanceof Date) { + return ((Date) obj).toInstant().atZone(ZoneId.systemDefault()).toLocalDate(); + } + return null; } - @Override - public int deleteNpSheepMilkAnalysisById(Long id) { - return npSheepMilkAnalysisMapper.deleteNpSheepMilkAnalysisById(id); + private static Date toDate(LocalDate ld) { + if (ld == null) return null; + return Date.from(ld.atStartOfDay(ZoneId.systemDefault()).toInstant()); } - @Override - public int deleteNpSheepMilkAnalysisByIds(Long[] ids) { - return npSheepMilkAnalysisMapper.deleteNpSheepMilkAnalysisByIds(ids); + private static Integer toInteger(Object obj) { + if (obj == null) return null; + if (obj instanceof Number) return ((Number) obj).intValue(); + try { + return Integer.parseInt(obj.toString()); + } catch (Exception e) { + return null; + } + } + + private static Double toDouble(Object obj) { + if (obj == null) return 0.0; + if (obj instanceof Number) return ((Number) obj).doubleValue(); + try { + return Double.parseDouble(obj.toString()); + } catch (Exception e) { + return 0.0; + } + } + + private double computeParityAvg(List stats, int parity, int screenDays) { + // 这里你之前实现是直接返回0,可按需完善 + return 0.0; + } + + private double computeLastNDaysAvg(List recs, LocalDate lastDate, int days) { + LocalDate startDate = lastDate.minusDays(days - 1); + double sum = 0; + int count = 0; + for (Rec r : recs) { + if (r.date != null && !r.date.isBefore(startDate) && !r.date.isAfter(lastDate)) { + sum += r.correctedMilk; + count++; + } + } + return (count > 0) ? (sum / count) : 0.0; } } - diff --git a/zhyc-module/src/main/resources/mapper/dairyProducts/NpSheepMilkAnalysisMapper.xml b/zhyc-module/src/main/resources/mapper/dairyProducts/NpSheepMilkAnalysisMapper.xml index 34e4ba2..8069e16 100644 --- a/zhyc-module/src/main/resources/mapper/dairyProducts/NpSheepMilkAnalysisMapper.xml +++ b/zhyc-module/src/main/resources/mapper/dairyProducts/NpSheepMilkAnalysisMapper.xml @@ -2,151 +2,61 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - id, manage_ear_tag, variety, milking_date, dry_date, milking_days, - screen_days, max_parity, total_milk, total_corrected_milk, - avg_daily_corrected_milk, parity1_total_milk, parity2_total_milk, - parity3_total_milk, parity4_total_milk, parity1_avg_milk, - parity2_avg_milk, parity3_avg_milk, parity4_avg_milk, - lactation_days, last_7_avg_milk, last_7_corrected_milk, - last_14_avg_milk, last_30_avg_milk, sheep_type, birthday, - current_parity, month_age, current_weight, breed_status, - father_tag, mother_tag, ranch, family, mother_milking_days, - mother_total_corrected_milk, mother_max_parity, - mother_avg_corrected - - - - - + SELECT DISTINCT a.sheep_id + FROM np_milk_prod_classes a + LEFT JOIN sheep_file sf ON a.sheep_id = sf.id - AND manage_ear_tag LIKE CONCAT('%', #{manageEarTag}, '%') + AND sf.bs_manage_tags LIKE CONCAT('%', #{manageEarTag}, '%') - - ORDER BY milking_date DESC + ORDER BY a.sheep_id - - INSERT INTO np_sheep_milk_analysis ( - - ) VALUES ( - #{id}, #{manageEarTag}, #{variety}, #{milkingDate}, #{dryDate}, - #{milkingDays}, #{screenDays}, #{maxParity}, #{totalMilk}, - #{totalCorrectedMilk}, #{avgDailyCorrectedMilk}, #{parity1TotalMilk}, - #{parity2TotalMilk}, #{parity3TotalMilk}, #{parity4TotalMilk}, - #{parity1AvgMilk}, #{parity2AvgMilk}, #{parity3AvgMilk}, - #{parity4AvgMilk}, #{lactationDays}, #{last7AvgMilk}, - #{last7CorrectedMilk}, #{last14AvgMilk}, #{last30AvgMilk}, - #{sheepType}, #{birthday}, #{currentParity}, #{monthAge}, - #{currentWeight}, #{breedStatus}, #{fatherTag}, #{motherTag}, - #{ranch}, #{family}, #{motherMilkingDays}, - #{motherTotalCorrectedMilk}, #{motherMaxParity}, - #{motherAvgCorrected} - ) - + + + - - UPDATE np_sheep_milk_analysis - SET manage_ear_tag = #{manageEarTag}, - variety = #{variety}, - milking_date = #{milkingDate}, - dry_date = #{dryDate}, - milking_days = #{milkingDays}, - screen_days = #{screenDays}, - max_parity = #{maxParity}, - total_milk = #{totalMilk}, - total_corrected_milk = #{totalCorrectedMilk}, - avg_daily_corrected_milk = #{avgDailyCorrectedMilk}, - parity1_total_milk = #{parity1TotalMilk}, - parity2_total_milk = #{parity2TotalMilk}, - parity3_total_milk = #{parity3TotalMilk}, - parity4_total_milk = #{parity4TotalMilk}, - parity1_avg_milk = #{parity1AvgMilk}, - parity2_avg_milk = #{parity2AvgMilk}, - parity3_avg_milk = #{parity3AvgMilk}, - parity4_avg_milk = #{parity4AvgMilk}, - lactation_days = #{lactationDays}, - last_7_avg_milk = #{last7AvgMilk}, - last_7_corrected_milk = #{last7CorrectedMilk}, - last_14_avg_milk = #{last14AvgMilk}, - last_30_avg_milk = #{last30AvgMilk}, - sheep_type = #{sheepType}, - birthday = #{birthday}, - current_parity = #{currentParity}, - month_age = #{monthAge}, - current_weight = #{currentWeight}, - breed_status = #{breedStatus}, - father_tag = #{fatherTag}, - mother_tag = #{motherTag}, - ranch = #{ranch}, - family = #{family}, - mother_milking_days = #{motherMilkingDays}, - mother_total_corrected_milk = #{motherTotalCorrectedMilk}, - mother_max_parity = #{motherMaxParity}, - mother_avg_corrected = #{motherAvgCorrected} - WHERE id = #{id} - - - DELETE FROM np_sheep_milk_analysis WHERE id = #{id} - + + + - - DELETE FROM np_sheep_milk_analysis WHERE id IN - - #{id} - - + +