package service import ( "strings" "time" ) const ( depreciationStartAgeDayCloseHouse = 155 depreciationStartAgeDayOpenHouse = 176 ) func NormalizeDepreciationHouseType(raw string) string { return strings.TrimSpace(strings.ToLower(raw)) } func DepreciationStartAgeDay(houseType string) int { switch NormalizeDepreciationHouseType(houseType) { case "close_house": return depreciationStartAgeDayCloseHouse case "open_house": return depreciationStartAgeDayOpenHouse default: return 0 } } func FlockAgeDay(originDate time.Time, periodDate time.Time) int { origin := time.Date(originDate.Year(), originDate.Month(), originDate.Day(), 0, 0, 0, 0, originDate.Location()) period := time.Date(periodDate.Year(), periodDate.Month(), periodDate.Day(), 0, 0, 0, 0, periodDate.Location()) if period.Before(origin) { return 0 } return int(period.Sub(origin).Hours()/24) + 1 } func DepreciationScheduleDay(originDate time.Time, periodDate time.Time, houseType string) int { ageDay := FlockAgeDay(originDate, periodDate) startAgeDay := DepreciationStartAgeDay(houseType) if ageDay <= 0 || startAgeDay <= 0 || ageDay < startAgeDay { return 0 } return ageDay - startAgeDay + 1 } func CalculateDepreciationAtDayN( initialPulletCost float64, dayN int, houseType string, percentByHouseType map[string]map[int]float64, ) (float64, float64, float64) { return CalculateDepreciationFromDayRange(initialPulletCost, 1, dayN, houseType, percentByHouseType) } func CalculateDepreciationFromDayRange( initialPulletCost float64, startDay int, endDay int, houseType string, percentByHouseType map[string]map[int]float64, ) (float64, float64, float64) { if initialPulletCost <= 0 || endDay <= 0 { return 0, 0, 0 } if startDay <= 0 { startDay = 1 } if endDay < startDay { return 0, 0, 0 } normalizedHouseType := NormalizeDepreciationHouseType(houseType) housePercent, exists := percentByHouseType[normalizedHouseType] if !exists { return 0, 0, 0 } current := initialPulletCost pulletCostDayN := 0.0 depreciationValue := 0.0 depreciationPercent := 0.0 for day := startDay; day <= endDay; day++ { pct := housePercent[day] dep := current * (pct / 100) if day == endDay { pulletCostDayN = current depreciationValue = dep depreciationPercent = pct } current -= dep if current < 0 { current = 0 } } return pulletCostDayN, depreciationValue, depreciationPercent } func CalculateEffectiveDepreciationPercent(totalDepreciationValue, totalPulletCostDayN float64) float64 { if totalPulletCostDayN <= 0 { return 0 } return (totalDepreciationValue / totalPulletCostDayN) * 100 }