代码之家  ›  专栏  ›  技术社区  ›  Ayende Rahien

Dynamic+linq编译错误

  •  19
  • Ayende Rahien  · 技术社区  · 14 年前

    但我不明白为什么这个查询无法编译:

    public class Program
    {
        public static void Main(string[] args)
        {
            var docs = new dynamic[0];
            var q = from doc in docs
                    where doc["@metadata"]["Raven-Entity-Name"] == "Cases"
                    where doc.AssociatedEntities != null
                    from entity in doc.AssociatedEntities
                    where entity.Tags != null // COMPILER ERROR HERE
                    from tag in entity.Tags
                    where tag.ReferencedAggregate != null
                    select new {tag.ReferencedAggregate.Id, doc.__document_id};
        }
    }
    
    public static class LinqOnDynamic
    {
        private static IEnumerable<dynamic> Select(this object self)
        {
            if (self == null)
                yield break;
            if (self is IEnumerable == false || self is string)
                throw new InvalidOperationException("Attempted to enumerate over " + self.GetType().Name);
    
            foreach (var item in ((IEnumerable) self))
            {
                yield return item;
            }
        }
    
        public static IEnumerable<dynamic> SelectMany(this object source,
                                                        Func<dynamic, int, IEnumerable<dynamic>> collectionSelector,
                                                        Func<dynamic, dynamic, dynamic> resultSelector)
        {
            return Enumerable.SelectMany(Select(source), collectionSelector, resultSelector);
        }
    
        public static IEnumerable<dynamic> SelectMany(this object source,
                                                        Func<dynamic, IEnumerable<dynamic>> collectionSelector,
                                                        Func<dynamic, dynamic, dynamic> resultSelector)
        {
            return Enumerable.SelectMany(Select(source), collectionSelector, resultSelector);
        }
    
        public static IEnumerable<dynamic> SelectMany(this object source,
                                                        Func<object, IEnumerable<dynamic>> selector)
        {
            return Select(source).SelectMany<object, object>(selector);
        }
    
        public static IEnumerable<dynamic> SelectMany(this object source,
                                                                        Func<object, int, IEnumerable<dynamic>> selector)
        {
            return Select(source).SelectMany<object, object>(selector);
    
        }
    }
    

    var docs = new dynamic[0];
    var q = from doc in docs
            where doc["@metadata"]["Raven-Entity-Name"] == "Cases"
            where doc.AssociatedEntities != null
            from entity in doc.AssociatedEntities
            where entity.Tags != null
            from tag in entity.Tags
            select new { tag.ReferencedAggregate.Id, doc.__document_id };
    

    只有当我加上:

    在两行之前我得到一个错误:

    where entity.Tags!=null//此处出现编译器错误

    不知道发生了什么

    3 回复  |  直到 14 年前
        1
  •  13
  •   Richard Anthony Hein    14 年前

    如果我试着把你的电话转换成:

    var q = from doc in docs.Where(doc => doc["@metadata"]["Raven-Entity-Name"] == "Cases" || doc.AssociatedEntities != null)
            from entity in doc.AssociatedEntities.Where(entity => entity.Tags != null)
    

    我得到一个不同的编译器错误,它可能揭示了正在发生的事情:

        2
  •  2
  •   jbehren    14 年前
    var q = from doc in docs
            where doc["@metadata"]["Raven-Entity-Name"] == "Cases"
            where doc.AssociatedEntities != null
            from entity in 
                ((IEnumerable<dynamic>)doc.AssociatedEntities)
                .Where(entity => entity.Tags != null)
            from tag in 
                ((IEnumerable<dynamic>)entity.Tags)
                .Where(tag => tag.ReferencedAggregate != null)
            select new { tag.ReferencedAggregate.Id, doc.__document_id };
    

        3
  •  1
  •   Community CDub    7 年前

    匿名类型返回为<&燃气轮机;h\uu TransparentIdentifier0并由编译器在编译时处理-问题似乎是“动态优先顺序”-请阅读此处: Method-missing difficulties in C# 4.0: dynamic vs RealProxy

    我今天刚在最近的一篇文章中谈到这个。我会有一个小猜测,并说匿名类型是准备好的 之后 动态赋值:)-编译器知道这一点,正在阻挠您。

    如果使用常规类型的return,问题会消失吗?我想一定是这样。