import Foundation import UIKit import Combine // MARK: - 内存压力等级枚举 enum MemoryPressureLevel: CaseIterable { case normal case moderate case high case critical case extreme var description: String { switch self { case .normal: return "正常" case .moderate: return "中等" case .high: return "高" case .critical: return "严重" case .extreme: return "极端" } } } // MARK: - 系统内存使用结构 struct SystemMemoryUsage { let freeMB: Double let activeMB: Double let inactiveMB: Double let wiredMB: Double } // MARK: - 详细内存信息结构 struct DetailedMemoryInfo { let residentMemoryMB: Double let virtualMemoryMB: Double let physicalMemoryMB: Double let memoryPressure: MemoryPressureLevel let availableMemoryMB: Double let systemMemoryUsage: SystemMemoryUsage let timestamp: Date } // MARK: - 内存监控器 class MemoryMonitor: ObservableObject { static let shared = MemoryMonitor() @Published var currentMemoryUsage: String = "Unknown" @Published var memoryWarningCount: Int = 0 private var memoryCheckTimer: Timer? init() { // 监听内存警告 NotificationCenter.default.addObserver( self, selector: #selector(handleMemoryWarning), name: UIApplication.didReceiveMemoryWarningNotification, object: nil ) // 启动内存监控 startMemoryMonitoring() } deinit { NotificationCenter.default.removeObserver(self) stopMemoryMonitoring() } // MARK: - 内存使用监控 /// 获取当前内存使用情况(更准确的方法) func getMemoryUsage() -> String { let usedMB = getMemoryUsageInMB() return String(format: "%.1f MB", usedMB) } /// 获取内存使用量(MB) func getMemoryUsageInMB() -> Double { // 使用更准确的内存统计方法 let stats = getAccurateMemoryStats() return stats.residentMemoryMB } /// 获取准确的内存统计信息 private func getAccurateMemoryStats() -> (residentMemoryMB: Double, virtualMemoryMB: Double, physicalMemoryMB: Double) { var info = mach_task_basic_info() var count = mach_msg_type_number_t(MemoryLayout.size / MemoryLayout.size) let kerr: kern_return_t = withUnsafeMutablePointer(to: &info) { $0.withMemoryRebound(to: integer_t.self, capacity: Int(count)) { task_info(mach_task_self_, task_flavor_t(MACH_TASK_BASIC_INFO), $0, &count) } } if kerr == KERN_SUCCESS { let residentMB = Double(info.resident_size) / 1024.0 / 1024.0 let virtualMB = Double(info.virtual_size) / 1024.0 / 1024.0 let physicalMB = Double(ProcessInfo.processInfo.physicalMemory) / 1024.0 / 1024.0 return (residentMB, virtualMB, physicalMB) } else { // 如果 mach 调用失败,使用备用方法 return getFallbackMemoryStats() } } /// 备用内存统计方法 private func getFallbackMemoryStats() -> (residentMemoryMB: Double, virtualMemoryMB: Double, physicalMemoryMB: Double) { // 使用 NSProcessInfo 作为备用方案 let processInfo = ProcessInfo.processInfo let physicalMemory = Double(processInfo.physicalMemory) / 1024.0 / 1024.0 // 估算内存使用(基于系统总内存的百分比) let estimatedUsage = physicalMemory * 0.1 // 假设使用10%,这是一个保守估计 return (estimatedUsage, estimatedUsage * 2, physicalMemory) } /// 获取内存使用详情 func getMemoryUsageDetails() -> (usedMB: Double, totalMB: Double, percentage: Double) { let stats = getAccurateMemoryStats() let usedMB = stats.residentMemoryMB let totalMB = stats.physicalMemoryMB let percentage = totalMB > 0 ? (usedMB / totalMB) * 100.0 : 0.0 return (usedMB, totalMB, percentage) } /// 获取更详细的内存信息 func getDetailedMemoryInfo() -> DetailedMemoryInfo { let stats = getAccurateMemoryStats() _ = ProcessInfo.processInfo return DetailedMemoryInfo( residentMemoryMB: stats.residentMemoryMB, virtualMemoryMB: stats.virtualMemoryMB, physicalMemoryMB: stats.physicalMemoryMB, memoryPressure: getMemoryPressureLevel(), availableMemoryMB: getAvailableMemoryMB(), systemMemoryUsage: getSystemMemoryUsage(), timestamp: Date() ) } /// 获取可用内存 private func getAvailableMemoryMB() -> Double { // 简化版本:使用 ProcessInfo 获取可用内存信息 let processInfo = ProcessInfo.processInfo let physicalMemory = Double(processInfo.physicalMemory) / 1024.0 / 1024.0 // 基于系统总内存估算可用内存 // 这是一个简化的估算,实际应用中可能需要更复杂的计算 let estimatedAvailable = physicalMemory * 0.3 // 假设30%可用 return estimatedAvailable } /// 获取系统内存使用情况 private func getSystemMemoryUsage() -> SystemMemoryUsage { var stats = vm_statistics64() var count = mach_msg_type_number_t(MemoryLayout.size / MemoryLayout.size) let result = withUnsafeMutablePointer(to: &stats) { $0.withMemoryRebound(to: integer_t.self, capacity: Int(count)) { host_statistics64(mach_host_self(), HOST_VM_INFO64, $0, &count) } } if result == KERN_SUCCESS { let pageSize = vm_kernel_page_size let freeMB = Double(stats.free_count) * Double(pageSize) / 1024.0 / 1024.0 let activeMB = Double(stats.active_count) * Double(pageSize) / 1024.0 / 1024.0 let inactiveMB = Double(stats.inactive_count) * Double(pageSize) / 1024.0 / 1024.0 let wiredMB = Double(stats.wire_count) * Double(pageSize) / 1024.0 / 1024.0 return SystemMemoryUsage( freeMB: freeMB, activeMB: activeMB, inactiveMB: inactiveMB, wiredMB: wiredMB ) } return SystemMemoryUsage(freeMB: 0, activeMB: 0, inactiveMB: 0, wiredMB: 0) } /// 获取内存压力等级 private func getMemoryPressureLevel() -> MemoryPressureLevel { let stats = getAccurateMemoryStats() let percentage = stats.physicalMemoryMB > 0 ? (stats.residentMemoryMB / stats.physicalMemoryMB) * 100.0 : 0.0 switch percentage { case 0..<50: return .normal case 50..<70: return .moderate case 70..<85: return .high case 85..<95: return .critical default: return .extreme } } // MARK: - 内存压力检查 /// 检查内存压力 func checkMemoryPressure() { let memoryUsage = getMemoryUsage() currentMemoryUsage = memoryUsage print("📊 当前内存使用: \(memoryUsage)") let detailedInfo = getDetailedMemoryInfo() print("📊 内存压力等级: \(detailedInfo.memoryPressure.description)") // 基于内存压力等级进行清理 switch detailedInfo.memoryPressure { case .high, .critical, .extreme: print("⚠️ 内存压力较高,执行清理操作") performMemoryCleanup() case .moderate: print("⚠️ 内存压力中等,建议清理") suggestMemoryCleanup() case .normal: print("✅ 内存使用正常") } } /// 执行内存清理 func performMemoryCleanup() { print("🧹 执行内存清理操作") // 清理图片缓存 ImageCacheManager.shared.clearCache() // 清理临时文件 cleanupTempFiles() // 通知其他组件进行清理 NotificationCenter.default.post(name: .memoryCleanup, object: nil) // 强制垃圾回收 autoreleasepool { // 执行一些内存密集型操作来触发垃圾回收 } } /// 建议内存清理 func suggestMemoryCleanup() { print("💡 建议执行内存清理") // 只清理非关键缓存 ImageCacheManager.shared.clearCache() // 通知其他组件进行轻度清理 NotificationCenter.default.post(name: .memoryCleanupSuggestion, object: nil) } // MARK: - 临时文件清理 /// 清理临时文件 private func cleanupTempFiles() { let tempPath = NSTemporaryDirectory() let fileManager = FileManager.default do { let tempFiles = try fileManager.contentsOfDirectory(atPath: tempPath) var cleanedCount = 0 for file in tempFiles { let filePath = (tempPath as NSString).appendingPathComponent(file) // 只删除图片相关的临时文件 if file.hasSuffix(".jpg") || file.hasSuffix(".png") || file.hasSuffix(".tmp") { try fileManager.removeItem(atPath: filePath) cleanedCount += 1 } } print("🗑️ 清理了 \(cleanedCount) 个临时文件") } catch { print("❌ 清理临时文件失败: \(error)") } } // MARK: - 监控控制 /// 启动内存监控 func startMemoryMonitoring() { stopMemoryMonitoring() // 先停止之前的监控 // 每30秒检查一次内存使用情况 memoryCheckTimer = Timer.scheduledTimer(withTimeInterval: 30.0, repeats: true) { [weak self] _ in self?.checkMemoryPressure() } print("📊 内存监控已启动") } /// 停止内存监控 func stopMemoryMonitoring() { memoryCheckTimer?.invalidate() memoryCheckTimer = nil print("📊 内存监控已停止") } // MARK: - 内存警告处理 @objc private func handleMemoryWarning() { memoryWarningCount += 1 print("🚨 收到内存警告 #\(memoryWarningCount)") // 立即执行内存清理 performMemoryCleanup() // 通知其他组件 NotificationCenter.default.post(name: .memoryWarning, object: nil) } // MARK: - 内存统计 /// 获取内存统计信息 func getMemoryStatistics() -> MemoryStatistics { let details = getMemoryUsageDetails() return MemoryStatistics( usedMB: details.usedMB, totalMB: details.totalMB, percentage: details.percentage, warningCount: memoryWarningCount, timestamp: Date() ) } /// 打印内存统计信息 func printMemoryStatistics() { let stats = getMemoryStatistics() print("📊 内存统计信息:") print(" - 已使用: \(String(format: "%.1f MB", stats.usedMB))") print(" - 总内存: \(String(format: "%.1f MB", stats.totalMB))") print(" - 使用率: \(String(format: "%.1f%%", stats.percentage))") print(" - 警告次数: \(stats.warningCount)") print(" - 检查时间: \(stats.timestamp)") } } // MARK: - 内存统计结构 struct MemoryStatistics { let usedMB: Double let totalMB: Double let percentage: Double let warningCount: Int let timestamp: Date } // MARK: - 通知名称扩展 extension Notification.Name { static let memoryWarning = Notification.Name("memoryWarning") static let memoryCleanup = Notification.Name("memoryCleanup") static let memoryCleanupSuggestion = Notification.Name("memoryCleanupSuggestion") } // MARK: - 内存优化工具 extension MemoryMonitor { /// 检查是否需要进行内存优化 func shouldOptimizeMemory() -> Bool { let details = getMemoryUsageDetails() return details.percentage > 70.0 || details.usedMB > 200.0 } /// 获取内存优化建议 func getMemoryOptimizationSuggestions() -> [String] { var suggestions: [String] = [] let details = getMemoryUsageDetails() if details.percentage > 80.0 { suggestions.append("内存使用率过高,建议关闭其他应用") } if details.usedMB > 250.0 { suggestions.append("内存使用量过大,建议重启应用") } if memoryWarningCount > 3 { suggestions.append("频繁收到内存警告,建议检查内存泄漏") } if suggestions.isEmpty { suggestions.append("内存使用正常") } return suggestions } /// 执行深度内存清理 func performDeepMemoryCleanup() { print("🧹 执行深度内存清理") // 1. 清理所有缓存 ImageCacheManager.shared.clearCache() // 2. 清理临时文件 cleanupTempFiles() // 3. 清理系统缓存 URLCache.shared.removeAllCachedResponses() // 4. 通知所有组件进行清理 NotificationCenter.default.post(name: .deepMemoryCleanup, object: nil) // 5. 强制垃圾回收 autoreleasepool { // 执行内存密集型操作 let _ = Array(0..<1000).map { _ in String(repeating: "x", count: 1000) } } print("✅ 深度内存清理完成") } } // MARK: - 深度清理通知 extension Notification.Name { static let deepMemoryCleanup = Notification.Name("deepMemoryCleanup") } // MARK: - 改进的内存监控方法 extension MemoryMonitor { /// 获取更准确的系统内存信息 func getSystemMemoryInfo() -> SystemMemoryInfo { let processInfo = ProcessInfo.processInfo let physicalMemory = Double(processInfo.physicalMemory) / 1024.0 / 1024.0 // 获取当前应用的内存使用 let appMemory = getMemoryUsageInMB() // 估算系统其他进程的内存使用 let systemMemory = physicalMemory - appMemory return SystemMemoryInfo( totalPhysicalMemoryMB: physicalMemory, appMemoryMB: appMemory, systemMemoryMB: max(0, systemMemory), availableMemoryMB: getAvailableMemoryMB(), memoryPressure: getMemoryPressureLevel() ) } /// 检查内存泄漏 func checkMemoryLeak() -> MemoryLeakReport { let currentMemory = getMemoryUsageInMB() // 记录内存使用历史(这里简化处理,实际应用中应该保存历史数据) let report = MemoryLeakReport( currentMemoryMB: currentMemory, memoryGrowth: 0, // 需要历史数据来计算 potentialLeak: currentMemory > 300, // 超过300MB可能有问题 recommendation: currentMemory > 300 ? "内存使用过高,可能存在内存泄漏" : "内存使用正常" ) return report } /// 优化内存监控频率 func optimizeMonitoringFrequency() { let memoryPressure = getMemoryPressureLevel() switch memoryPressure { case .normal: // 正常情况:每60秒检查一次 updateMonitoringInterval(60.0) case .moderate: // 中等压力:每30秒检查一次 updateMonitoringInterval(30.0) case .high: // 高压力:每15秒检查一次 updateMonitoringInterval(15.0) case .critical, .extreme: // 严重压力:每5秒检查一次 updateMonitoringInterval(5.0) } } /// 更新监控间隔 private func updateMonitoringInterval(_ interval: TimeInterval) { stopMemoryMonitoring() memoryCheckTimer = Timer.scheduledTimer(withTimeInterval: interval, repeats: true) { [weak self] _ in self?.checkMemoryPressure() } print("📊 内存监控间隔已更新为 \(interval) 秒") } /// 获取内存使用趋势 func getMemoryTrend() -> MemoryTrend { // 这里应该基于历史数据计算趋势 // 简化版本返回当前状态 _ = getMemoryUsageInMB() let pressure = getMemoryPressureLevel() return MemoryTrend( currentLevel: pressure, trend: .stable, // 需要历史数据来判断 recommendation: getMemoryOptimizationSuggestions().first ?? "内存使用正常" ) } } // MARK: - 新增数据结构 struct SystemMemoryInfo { let totalPhysicalMemoryMB: Double let appMemoryMB: Double let systemMemoryMB: Double let availableMemoryMB: Double let memoryPressure: MemoryPressureLevel } struct MemoryLeakReport { let currentMemoryMB: Double let memoryGrowth: Double let potentialLeak: Bool let recommendation: String } struct MemoryTrend { let currentLevel: MemoryPressureLevel let trend: MemoryTrendDirection let recommendation: String } enum MemoryTrendDirection { case increasing case decreasing case stable var description: String { switch self { case .increasing: return "上升" case .decreasing: return "下降" case .stable: return "稳定" } } }