动态分配模型属性类型

Posted

技术标签:

【中文标题】动态分配模型属性类型【英文标题】:dynamically allocating Model property type 【发布时间】:2021-12-10 21:04:21 【问题描述】:

所以我需要创建一个具有动态属性的模型;即,此属性可以是 3 种枚举类型中的任何一种,并且是在模型创建时动态分配的

我的模特:

public class Attribute

    public int AttributeId  get; set; 

    public AttributeConditionType Condition  get; set;  = enGoodBad;


我的动态类型:

public class AttributeConditionType

    public enum enGoodBad
    
        Good,
        Bad, 
        Excellent
    

    public enum enYesNo
    
        Yes,
        No
    

    public enum enMajorMinor
    
        Major,
        Minor, 
    

    public enum enMissing
    
        None,
        Some,
        One,
        Many
    

我知道我写的东西是错误的,但理解我的问题,我如何使它成为可能的代码?

【问题讨论】:

也许你应该有三个不同的属性类,每个可能的类型一个。 这对我来说有点像 XY 问题 @HimBromBeere 那么我如何分配属性? 在 C# 中,您可以定义属性的唯一类型是 Enum,这将允许您在其中存储任何 enum 值。但正如大卫所说,这感觉就像XY problem。 【参考方案1】:

您可以创建一个具有四个成员的枚举 AttributeConditionTypeenGoodBadenYesNoenMajorMinorenMissing。并修改属性类如下:

public class TestAttribute

    public int AttributeId  get; set; 

    // this property is used to store the select AttributeConditionType type.
    public AttributeConditionType Condition  get; set;  = AttributeConditionType.enGoodBad;

    //this property is used to store the select AttributeConditionType's selected value, such as: Good, Bad, Excellent, Yes or No
    public string SelectType  get; set;  



public enum AttributeConditionType

    enGoodBad,
    enYesNo,
    enMajorMinor,
    enMissing

public enum enGoodBad

    Good,
    Bad,
    Excellent

public enum enYesNo

    Yes,
    No

public enum enMajorMinor

    Major,
    Minor,

public enum enMissing

    None,
    Some,
    One,
    Many

然后,当您添加 TestAttribute 时,您可以使用 Cascading Dropdown 来显示 AttributeConditionType 和相关类型。

这样的代码:

@model Core5_0MVC.Models.TestAttribute

@
    ViewData["Title"] = "AddAttribute";

  
<div class="row">
    <div class="col-md-4">
        <form asp-action="AddAttribute">
            <div asp-validation-summary="ModelOnly" class="text-danger"></div>
            <div class="form-group">
                <label asp-for="AttributeId" class="control-label"></label>
                <input asp-for="AttributeId" class="form-control" />
                <span asp-validation-for="AttributeId" class="text-danger"></span>
            </div>
            <div class="form-group">
                <label asp-for="Condition" class="control-label"></label>
                <select asp-for="Condition" class="form-control"
                        asp-items="html.GetEnumSelectList<AttributeConditionType>()">
                    <option value="0">Select type ...</option>
                </select>
                <span asp-validation-for="Condition" class="text-danger"></span>
            </div>
            <div class="form-group">
                <label asp-for="SelectType" class="control-label"></label>
                <select asp-for="SelectType" class="form-control">

                </select>
                <span asp-validation-for="SelectType" class="text-danger"></span>
            </div>
            <div class="form-group">
                <input type="submit" value="Create" class="btn btn-primary" />
            </div>
        </form>
    </div>
</div>

@section Scripts 
    @await Html.RenderPartialAsync("_ValidationScriptsPartial");
<script>
    $(function ()
        $("#Condition").change(function () 
            var value = $("#Condition option:selected").text();
            $.ajax(
                url: "/Home/GetSubEnum",
                data:  "type": value ,
                method: "Post",
                success: function (response) 
                    //clear the SelectType dropdownlist.
                    $("#SelectType").empty();
                    //add new items in the dropdownlist.
                    $.each(response, function (index, item) 
                        $("#SelectType").append("<option value=" + item.text + ">" + item.text + "</option>");
                    );
                
            );
        );
    );
</script>


家庭控制器:

    public IActionResult AddAttribute()
    
        return View();
    
    [HttpPost]
    public IActionResult AddAttribute(TestAttribute attribute)
    
        return View();
    

    [HttpPost]
    public IActionResult GetSubEnum(string type)
    
        var result = new List<SelectListItem>();

        switch (type)
         
            case "enYesNo":
                result = GetEnumSelectList<enYesNo>();
                break;
            case "enMajorMinor":
                result = GetEnumSelectList<enMajorMinor>();
                break;
            case "enMissing":
                result = GetEnumSelectList<enMissing>();
                break;
            default:
                result = GetEnumSelectList<enGoodBad>();
                break;
        

        return Json(result);
    

    //Convert the Enum to select list.
    public static List<SelectListItem> GetEnumSelectList<T>()
    
        return (Enum.GetValues(typeof(T)).Cast<T>().Select(
            enu => new SelectListItem()  Text = enu.ToString(), Value = enu.ToString() )).ToList();
    

结果如下:

【讨论】:

天哪,谢谢!!!!这正是我所需要的

以上是关于动态分配模型属性类型的主要内容,如果未能解决你的问题,请参考以下文章

如何在 TypeScript 中为对象动态分配属性?

Rails 3.2,批量分配,动态角色?

在 WIX 中运行时为快捷方式动态分配名称

具有动态分配成员的动态分配结构的 MPI 派生数据类型

通过 javascript 将索引动态分配给 Razor 模型

如何在 TypeScript 中为类属性动态分配值