Icollection不包含任何定义

问题描述 投票:0回答:1

美好的一天,使用Assigned方法使用预先加载来加载来自Include的相关数据的代码。我正在尝试获取IsAvailable的值,以便从Assigned访问数据并检查是否存在ReturnDate值等于null的记录。我一直在说错误

Icollection不包含任何定义

public ActionResult Index()
    {
        var item = db.Item.Include(h => h.Assigned).Select(b => new ItemViewModel
        {
            ItemID = b.ItemID,
            ItemName = b.ItemName,
            Category = b.Category,
            Description = b.Description,
            Model = b.Model,
            IsAvailable = !b.Assigned.Any(h => h.ReturnDate == null)
        }).ToList();

        return View(item);
    }

ItemViewModel

public class ItemViewModel
{

    public int ItemID { get; set;}
    [Display(Name = "Item")]
    public string ItemName { get; set; }
    [Required(ErrorMessage = "Category is required")]
    public string Category { get; set; }
    public string Model { get; set; }
    public string Description { get; set; }
    public bool IsAvailable { get; set; }
}

物品类

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.ComponentModel.DataAnnotations;
using System.Collections;

    namespace Inventoryproto3.Models
    {
        public class Item
        {

            public int ItemID { get; set; }
            [Required(ErrorMessage ="Please enter a title"),Display(Name ="Item")]
            public string ItemName { get; set;}
            [Required(ErrorMessage ="Category is required")]
            public string Category { get; set;}
            public string Model { get; set;}
            public string Description{get; set;}

            public ICollection Assigned { get; set; }


        }
    }

'System.Collections.Generic.ICollection'不包含'Any'的定义,也没有可访问的扩展方法'Any'接受类型为'System.Collections.Generic.ICollection'的第一个参数'(你是否错过了使用指令或汇编参考?

Screenshot of error

asp.net-mvc entity-framework linq model-view-controller
1个回答
0
投票

每个Item都有一个属性Assigned,类型为ICollection

如果你看一下Queryable.Any的定义,你会发现:

public static bool Any<TSource> (this IQueryable<TSource> source, 
       Expression<Func<TSource,bool>> predicate);

因此,属性Assigned应该实现ICollection<TSource>,其中TSource是您希望在集合中找到的实际类型。

正确的解决方案是更改属性Assigned的类型,以便您知道该集合仅包含您期望的类型的项目。唉,你选择给我们提供很多不重要的信息,但是你忘了提及Assigned中的项目类别,所以让我们假设它是MyClass类型。

class MyClass
{
    public Datetime ReturnDate {get; set;}
    ...
}

class Item
{
     ...
     public ICollection<MyClass> Assigned {get; set;}
}

这将解决您的问题:Any(...)工作,并且您确定人们只能将MyClass对象放入集合中。

如果您不想将集合限制为MyClass对象,则至少可以限制自己使用属性ReturnDate的类:

interface IMyInterface
{
    public Datetime ReturnDate {get; set;}
}

class Item
{
     ...
     public ICollection<IMyInterface> Assigned {get; set;}
}

如果你真的希望人们可以在集合中添加除MyClass对象之外的其他东西,我强烈建议你反对,你必须指定你想要的东西:

  • 忽略集合中不是MyClass对象的项目?使用OfType
  • 只是希望没有人在集合中放入其他东西?使用Cast,但是再次:为什么不防止有人在类中放置一个不正确的对象,并定义ICollection<MyClass>

OfType可能不起作用AsQueryable,在这种情况下,你应该使用AsEnumerable将数据移动到本地进程。使用正确类型进行ICollection权利的第三个原因。

IsAvailable = !b.Assigned.OfType<MyClass>().Any(h => h.ReturnDate == null);
IsAvailable = !b.Assigned.Cast<MyClass>().Any(h => h.ReturnDate == null);

第一个将忽略您的集合与其他类型的项目。如果你的收藏中有另一种类型,后者将抛出异常(第四个原因使它成为ICollection<MyClass>

© www.soinside.com 2019 - 2024. All rights reserved.