文章目錄
- 一、靜態類與靜態成員
- 實現方式
- 特點
- 優缺點
- 二、應用程序配置系統
- 1. appsettings.json (ASP.NET Core)
- 使用方式
- 2. 用戶設置 (WinForms/WPF)
- 特點
- 三、依賴注入容器
- ASP.NET Core 示例
- 特點
- 四、內存緩存 (IMemoryCache)
- 實現方式
- 特點
- 五、分布式緩存 (IDistributedCache)
- 實現方式
- 特點
- 六、HttpContext.Items (ASP.NET Core)
- 實現方式
- 特點
- 七、環境變量
- 訪問方式
- 特點
- 八、數據庫存儲
- 實現方式
- 特點
- 九、選擇指南
- 十、最佳實踐建議
- 十一、高級模式示例
- 混合緩存策略
- 配置熱重載

在 .NET 應用程序開發中,全局數據存儲是共享和訪問應用程序范圍內數據的常見需求。以下是幾種主要的全局數據存儲方式及其適用場景、實現方法和優缺點分析。
一、靜態類與靜態成員
實現方式
public static class GlobalData
{public static string ApplicationName { get; set; } = "MyApp";public static int MaxConnections { get; } = 100;private static readonly ConcurrentDictionary<string, object> _cache = new ConcurrentDictionary<string, object>();public static void SetCache(string key, object value){_cache[key] = value;}public static T GetCache<T>(string key){return _cache.TryGetValue(key, out var value) ? (T)value : default;}
}
特點
- 生命周期:應用程序域生命周期
- 線程安全:需要手動實現(如使用
ConcurrentDictionary
) - 適用場景:小型應用、工具類、全局配置
優缺點
- ? 簡單易用
- ? 訪問速度快
- ? 缺乏持久化
- ? 測試困難(靜態依賴)
二、應用程序配置系統
1. appsettings.json (ASP.NET Core)
{"AppConfig": {"Theme": "Dark","Timeout": 30}
}
使用方式
// 在Startup中配置
services.Configure<AppConfig>(Configuration.GetSection("AppConfig"));// 注入使用
public class MyService
{private readonly AppConfig _config;public MyService(IOptions<AppConfig> config){_config = config.Value;}
}
2. 用戶設置 (WinForms/WPF)
// 保存設置
Properties.Settings.Default.Theme = "Dark";
Properties.Settings.Default.Save();// 讀取設置
var theme = Properties.Settings.Default.Theme;
特點
- 生命周期:持久化到配置文件
- 線程安全:內置線程安全
- 適用場景:應用程序配置、用戶偏好設置
三、依賴注入容器
ASP.NET Core 示例
// 注冊服務
services.AddSingleton<IGlobalCache, MemoryCache>();
services.AddScoped<IUserSession, UserSession>();// 使用
public class MyController : Controller
{private readonly IGlobalCache _cache;public MyController(IGlobalCache cache){_cache = cache;}
}
特點
- 生命周期:
- Singleton: 應用程序生命周期
- Scoped: 請求生命周期
- Transient: 每次請求新實例
- 線程安全:取決于實現
- 適用場景:ASP.NET Core 應用、服務共享
四、內存緩存 (IMemoryCache)
實現方式
// 注冊
services.AddMemoryCache();// 使用
public class DataService
{private readonly IMemoryCache _cache;public DataService(IMemoryCache cache){_cache = cache;}public string GetCachedData(string key){return _cache.GetOrCreate(key, entry => {entry.AbsoluteExpirationRelativeToNow = TimeSpan.FromMinutes(30);return ExpensiveDatabaseCall();});}
}
特點
- 生命周期:應用程序重啟后丟失
- 線程安全:內置線程安全
- 適用場景:頻繁訪問的臨時數據
五、分布式緩存 (IDistributedCache)
實現方式
// 使用Redis
services.AddStackExchangeRedisCache(options =>
{options.Configuration = "localhost:6379";
});// 使用
public async Task<byte[]> GetCachedDataAsync(string key)
{return await _distributedCache.GetAsync(key);
}
特點
- 生命周期:持久化到外部存儲
- 線程安全:內置線程安全
- 適用場景:分布式應用、多實例共享數據
六、HttpContext.Items (ASP.NET Core)
實現方式
// 中間件中設置
app.Use(async (context, next) =>
{context.Items["RequestStartTime"] = DateTime.UtcNow;await next();
});// 控制器中訪問
var startTime = HttpContext.Items["RequestStartTime"] as DateTime?;
特點
- 生命周期:單個HTTP請求期間
- 線程安全:每個請求獨立
- 適用場景:請求級數據共享
七、環境變量
訪問方式
var envVar = Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT");
特點
- 生命周期:進程生命周期或系統級
- 線程安全:只讀操作安全
- 適用場景:部署配置、環境特定設置
八、數據庫存儲
實現方式
// 使用EF Core
public class AppDbContext : DbContext
{public DbSet<GlobalSetting> GlobalSettings { get; set; }
}// 使用
var setting = await _dbContext.GlobalSettings.FirstOrDefaultAsync(s => s.Key == "MaintenanceMode");
特點
- 生命周期:持久化
- 線程安全:取決于數據庫訪問層
- 適用場景:需要持久化的全局配置
九、選擇指南
存儲方式 | 生命周期 | 持久化 | 分布式支持 | 典型使用場景 |
---|---|---|---|---|
靜態成員 | 應用程序域 | 否 | 否 | 全局常量、簡單緩存 |
應用程序配置 | 持久化 | 是 | 部分 | 應用設置、用戶偏好 |
依賴注入容器 | 取決于注冊類型 | 否 | 否 | 服務共享、全局服務 |
內存緩存 | 應用程序 | 否 | 否 | 頻繁訪問的臨時數據 |
分布式緩存 | 持久化 | 是 | 是 | 多實例共享數據 |
HttpContext.Items | 請求期間 | 否 | 否 | 請求級數據傳遞 |
環境變量 | 進程/系統 | 是 | 是 | 部署配置、環境特定設置 |
數據庫存儲 | 持久化 | 是 | 是 | 需要持久化的全局配置 |
十、最佳實踐建議
- 按需選擇:根據數據特性(大小、訪問頻率、生命周期)選擇合適方式
- 分層設計:
- 高頻小數據:內存緩存
- 配置數據:appsettings.json
- 用戶數據:數據庫
- 線程安全:
- 多線程訪問時使用線程安全集合(如
ConcurrentDictionary
) - 考慮使用
Immutable
集合避免意外修改
- 多線程訪問時使用線程安全集合(如
- 性能考慮:
- 大數據集避免使用靜態變量
- 考慮使用緩存過期策略
- 測試友好:
- 避免過度使用靜態類
- 優先使用依賴注入
- 分布式場景:
- 多服務器環境使用分布式緩存
- 考慮使用消息隊列同步狀態
十一、高級模式示例
混合緩存策略
public class HybridCache
{private readonly IMemoryCache _memoryCache;private readonly IDistributedCache _distributedCache;public HybridCache(IMemoryCache memoryCache, IDistributedCache distributedCache){_memoryCache = memoryCache;_distributedCache = distributedCache;}public async Task<T> GetOrCreateAsync<T>(string key, Func<Task<T>> factory, TimeSpan expiration){if (_memoryCache.TryGetValue(key, out T memoryValue)){return memoryValue;}var distributedValue = await _distributedCache.GetStringAsync(key);if (distributedValue != null){var value = JsonSerializer.Deserialize<T>(distributedValue);_memoryCache.Set(key, value, expiration);return value;}var newValue = await factory();_memoryCache.Set(key, newValue, expiration);await _distributedCache.SetStringAsync(key, JsonSerializer.Serialize(newValue), new DistributedCacheEntryOptions { AbsoluteExpirationRelativeToNow = expiration });return newValue;}
}
配置熱重載
// Program.cs
builder.Services.Configure<AppConfig>(builder.Configuration.GetSection("AppConfig"));
builder.Services.AddSingleton<IOptionsMonitor<AppConfig>>(provider => provider.GetRequiredService<IOptionsMonitor<AppConfig>>());// 使用
public class ConfigService
{private readonly AppConfig _config;public ConfigService(IOptionsMonitor<AppConfig> configMonitor){_config = configMonitor.CurrentValue;configMonitor.OnChange(newConfig => {_config = newConfig;});}
}
通過合理選擇和組合這些全局數據存儲方式,可以構建出既高效又易于維護的 .NET 應用程序架構。