2

我有一个动态对象,我认为它是用 Clay 实现的。它具有两个可能的属性名称之一。我想使用可用的属性名称。以下不起作用:

dynamic workItemPart = item.WorkItem; // is an Orchard.ContentManagement.ContentPart
var learnMore = workItemPart.LearnMore ?? workItemPart.LearnMoreField;

它抛出一个Microsoft.CSharp.RuntimeBinder.RuntimeBinderException

不包含“LearnMore”的定义

我们如何检查动态 Clay 对象是否具有属性? 例如,在 JavaScript 中,我们可以执行以下操作。

var workItemPart = {
    LearnMoreField: "Sure"    
    }
console.log(workItemPart.LearnMore || workItemPart.LearnMoreField);

C# 中是否有这么简洁的 Clay 内容?

有关的:

Orchard.ContentManagement.ContentPart 是用 Clay 实现的吗?

https://twitter.com/bleroy/status/497078654405312512

4

3 回答 3

2

您还可以使用索引方法:

var learnMore = workItemPart["LearnMore"] != null ? 
     workItemPart.LearnMore : workItemPart.LearnMoreField;

希望这可以帮助。

更新

我不确定为什么没有。两种方法都应该有效。

        dynamic New = new ClayFactory();
        var person = New.Person();
        person.skill = "Outstanding";
        var talent = person.talent;
        var talentTwo = person["talent"];
        var skill = person.talent ?? person.skill;
        Console.WriteLine(skill);
        skill = person.skill ?? person.talent;
        Console.WriteLine(skill);

也许是果园给你扔了一个曲线球......

有趣的是,null-coalesce 运算符没有正确处理第一个测试用例。但是,标准测试成功:

        skill = person.talent != null ? person.talent : person.skill;
        Console.WriteLine(skill);

不知道在这一点上给你什么建议。

于 2014-08-05T22:55:46.553 回答
1

您可以使用扩展方法来检查属性是否存在:

public static class Extensions
{
    public static bool HasProperty(this object d, string propertyName)
    {
        return d.GetType().GetProperty(propertyName) != null;
    }
}

用法:

bool hasProperty = Extensions.HasProperty(workItemPart, "LearnMore");

var learnMore =  hasProperty ? workItemPart.LearnMore : workItemPart.LearnMoreField;

虽然它看起来不像扩展方法.. 因为它workItemPart是动态的,所以您需要通过指定类名来显式调用它。

于 2014-08-05T22:58:32.177 回答
1

@Shaun Luttin,在 Orchard cms 的上下文中是一个相当老的问题,但最近我提出了这个已提交的拉取请求

因此,现在您可以使用以下内容而不会引发异常

    if (contentItem.SomePart != null)
    if (part.SomeField != null)

ContentItem 和 ContentPart 类继承自 System.Dynamic.DynamicObject 并覆盖 TryGetMember() 方法。并且,之前,如果没有找到属性,则该方法返回 false

    return false;

现在,即使结果对象(方法的 out 参数)设置为 null,该方法也会返回 true,从而防止抛出异常

    result = null;
    return true;

更多详情,请查看上面的相关 PR 链接

最好的

于 2015-09-17T04:50:50.310 回答