ASP.NET MVC控制器向视图传递数据的正确方式 TempData传下拉框数据是否可行
1. TempData 用于该场景是否合适?
不合适,原因如下:
- TempData 默认基于Session实现,生命周期为单次请求,仅适用于跨重定向传递临时数据的场景,而非视图渲染的常规数据载体。你当前需要用
Peek()方法保留数据才能应对刷新场景,一旦操作疏漏就会出现数据为空导致的视图报错,稳定性差。 - 每个需要该下拉框的页面都要重复写赋值、取值的逻辑,代码冗余可维护性低。
2. 存入100条数据是否有性能问题?
100条SelectListItem的总数据量仅为KB级别,无论存在TempData还是其他内存存储中,都不会导致系统变慢,不存在性能瓶颈,你当前的问题是用法不合理而非性能问题。
3. Session 方案是否适用?
不适用。该下拉框的请求类型属于全局公共数据,所有用户看到的内容完全一致,Session是用户级别的存储,每个用户独立保存一份相同的数据,用户量上来后反而会造成不必要的内存浪费。
4. 更优实现方案
按推荐优先级排序:
方案1:使用强类型ViewModel(最标准)
这是ASP.NET MVC/ Core 渲染视图的常规做法:
- 在Create和Edit页对应的ViewModel中新增属性:
public List<SelectListItem> ReqTypeOptions { get; set; }
- 控制器中查询数据后直接赋值给ViewModel的该属性,无需借助任何临时存储:
var viewModel = new YourEditViewModel(); viewModel.ReqTypeOptions = db.Request_Types.Where(r => r.Status == true) .Select(r => new SelectListItem { Text = r.Request_Type, Value = r.Id.ToString() }) .ToList(); return View(viewModel);
- 视图中直接绑定即可:
@Html.DropDownListFor(model => model.ReqType, Model.ReqTypeOptions, "Select Request Type", new { @class = "js-dropdown" })
该方案强类型安全,不存在类型转换报错的风险,逻辑清晰。
方案2:结合内存缓存复用查询(适合多页面共用)
如果多个页面都需要用到该下拉框,避免每次请求都查库,可以把查询结果存在全局内存缓存中:
- 注入
IMemoryCache(.NET Core)或使用HttpRuntime.Cache(.NET Framework),设置合理的过期时间(比如1小时,或者数据变更时主动更新缓存),全局仅保存一份公共数据,所有用户共用。 - 控制器中取值时优先读缓存,缓存不存在再查库写入缓存,大幅减少数据库查询次数。
方案3:视图组件(适合多处复用该下拉框)
如果很多页面都要渲染这个下拉框,可以封装成独立的视图组件,组件内部自己处理数据查询/读缓存的逻辑,页面上直接调用组件即可,不需要每个控制器都重复处理下拉框数据,进一步减少代码冗余。
另外注意你当前视图代码里存在笔误:你定义的变量名为ReqType,但DropDownListFor中用的是ReqTypes,运行时会报错。
内容的提问来源于stack exchange,提问作者smc develpments
相关产品推荐
相关产品推荐

