您的问题并不完全清楚,但您对自己的要求比使用ListBoxFor 时要困难得多。对于DropDownListFor 或ListBoxFor,您只需要IEnumerable<SelectListItem>。 Razor 将根据ModelState 选择任何合适的值。
所以,假设ViewBag.IfPoor 是IEnumerable<SelectListItem>,你需要的只是:
@Html.ListBoxFor(m => m.IfQualityPoor, (IEnumerable<SelectListItem>)ViewBag.IfPoor, new { @class = "chosen" })
根据您模型上IfQualityPoor 的值,正确的选项将被标记为selected,应该是这样。此外,没有必要在htmlAttributes 参数中传递multiple = "multiple",因为您只需使用ListBoxFor 而不是DropDownListFor。
如果您使用视图模型,然后将选项添加为属性,那就更好了。然后,您不必担心在视图中进行强制转换,这始终是引入运行时异常的好方法。例如:
public class FooViewModel
{
...
public IEnumerable<SelectListItem> IfQualityPoorOptions { get; set; }
}
然后,您在您的操作中设置它,然后返回视图(而不是设置ViewBag)。最后,在你看来:
@Html.ListBoxFor(m => m.IfQualityPoor, Model.IfQualityPoorOptions, new { @class = "chosen" })
简单得多,而且这样做永远不会有任何问题。
更新(基于评论)
将列表扁平化为用于数据库存储的字符串的最佳方法是为此使用特殊属性,然后自定义 getter 和 setter 以映射到/从。例如:
public string IfQualityPoor
{
get { return IfQualityPoorList != null ? String.Join(",", IfQualityPoorList) : null; }
set { IfQualityPoorList = !String.IsNullOrWhiteSpace(value) ? value.Split(',').ToList() : null; }
}
[NotMapped]
public List<string> IfQualityPoorList { get; set; }
然后,您发布到IfQualityPoorList/与IfQualityPoorList 交互,保存时将在数据库中自动设置正确的字符串。