【问题标题】:How to add auto property using Codedom如何使用 Codedom 添加自动属性
【发布时间】:2021-08-23 05:17:29
【问题描述】:

我正在尝试使用 codedom 生成自动属性,但没有运气。我尝试了不同的解决方案,每一个都会导致问题。我正在尝试生成如下所示的内容

        [FindsBy(How = How.Id, Using = "AllTabs")]
        public IWebElement SaveButton { get; set; }

我能够毫无问题地创建属性,但无法创建自动属性。

如果我尝试使用此处列出的解决方案 autoproperty

        CodeTypeDeclaration newType = new CodeTypeDeclaration("TestType");
        CodeSnippetTypeMember snippet = new CodeSnippetTypeMember();

        snippet.Comments.Add(new CodeCommentStatement("this is integer property", true));
        snippet.Text="public int IntergerProperty { get; set; }";

        newType.Members.Add(snippet);

然后我无法在属性上添加属性,它只是打印出没有属性的属性。有什么办法可以生成自动属性,也可以使用属性?

【问题讨论】:

标签: c# codedom


【解决方案1】:

显然您没有理解您所指的答案。它将文字插入到源流中,因此以下内容应该适合您:

        var newType = new CodeTypeDeclaration("TestType");
        var snippet = new CodeSnippetTypeMember();

        snippet.Text = @"
[FindsBy(How = How.Id, Using = ""AllTabs"")]
public IWebElement SaveButton { get; set; }
";

        newType.Members.Add(snippet);

请注意CodeSnippetTypeMember 完全忽略了 CodeDom 提供的验证,因此使用这种机制很容易生成非编译代码。 Roslyn does support auto-properties natively when in a C# context.

正如对链接问题的公认答案所述,CodeDom 不支持自动属性的原因是它们是所有 .NET 语言中不存在的语法糖,并且 CodeDom 旨在与语言无关可能的。因此,CodeDom 无法了解或支持自动属性的概念。

【讨论】:

  • 另一个原因是十多年来没有人维护 CodeDom。
【解决方案2】:

为了避免使用 sn-p 并在实际编译之前没有发现错误的风险,您可以使用一种方法来自动创建带有支持字段的属性(无论如何,编译器在内部使用自动属性执行此操作):

private static CodeMemberProperty makeAutoProperty(CodeTypeDeclaration containingClass, CodeTypeReference propertyType, string propertyName )
        {
            CodeMemberField backingField = new CodeMemberField();
            backingField.Name = propertyName + "_";
            backingField.Type = propertyType;
            CodeVariableReferenceExpression backingFieldRef = new CodeVariableReferenceExpression(backingField.Name);
            containingClass.Members.Add(backingField);

            CodeMemberProperty property = new CodeMemberProperty();
            property.Name = propertyName;
            property.Type = propertyType;
            property.HasGet = true;
            property.HasSet = true;
            property.GetStatements.Add(new CodeMethodReturnStatement(backingFieldRef));
            property.SetStatements.Add(new CodeAssignStatement(backingFieldRef, new CodeVariableReferenceExpression("value")));
            containingClass.Members.Add(property);

            return property;
        }

这使它与添加自动属性一样容易。您可以使用这样的方法:

            // Make the property
            CodeMemberProperty saveButtonField = makeAutoProperty(_class, new CodeTypeReference("IWebElement"), "saveButton");
            // Modify the access
            saveButtonField.Attributes = MemberAttributes.Public | MemberAttributes.Final;
            // Add the attribute decorator
            var attr = new CodeAttributeDeclaration(new CodeTypeReference("FindsBy"));
            saveButtonField.CustomAttributes.Add(attr);

这是输出:

        private IWebElement saveButton_;
        [FindsBy()]
        public IWebElement saveButton
        {
            get
            {
                return saveButton_;
            }
            set
            {
                saveButton_ = value;
            }
        }

【讨论】:

    猜你喜欢
    • 2010-10-09
    • 2011-01-08
    • 2011-01-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多