如何使用linq与两个相关的实体?

时间:2016-09-18 20:44:42

标签: c# entity-framework linq

你好我在dotnet项目中使用两个相关实体时遇到了问题 我有两个实体表和预订,我需要得到明天保留的表,但日期是在预订表中 这是代码

public class Table
{
    public int Id { get; set; }
    public bool isAvailable { get; set; }
    public int Numero { get; set; }
    public virtual ICollection<Reservation> IReservation { get; set; }
}

public class Reservation
{
    public DateTime DateReservation { get; set; }
    public int Id { get; set; }
    public string Nom { get; set; }
    public virtual Table table { get; set; }
}
public class RestaurantContext :DbContext
{
    public DbSet<Table> tTable { set; get; }
    public DbSet<Reservation> tReservation { set; get; }
    public RestaurantContext() : base("RestaurentDB") {     
    }
}
class TableRepository
{
    RestaurantContext rc = null;

    public TableRepository()
    {
        rc = new RestaurantContext();
    }
    public void Commit()
    {
        rc.SaveChanges();
    }
    public void AddTable(Table m)
    {
        rc.tTable.Add(m);
    }

    public IEnumerable<Table> GetAllTables() {
        return rc.tTable.ToList();
    }
    public IEnumerable<Table> GetTablesReserverdTomorrow() {
       ....
    }

在这里,我需要获得为明天保留的表格 我试过了

var res=rc.tReservation.Where(r => (r.DateReservation == DateTime.Today.AddDays(1))).ToList();
            var res1 = rc.tTable.Select(r => res.Contains(r.Id));
            return res1;

但似乎是错误

  

Argument1:无法从int转换为Reservation

3 个答案:

答案 0 :(得分:1)

您可以尝试在查询中使用导航,例如:

return rc.tReservation
    .Include(reservation => reservation.Table)
    .Where(r => (r.DateReservation == DateTime.Today.AddDays(1)))
    .Select(reservation => reservation.table).ToList();

答案 1 :(得分:1)

在你的情况下,res是IEnumerable,它包含Reservation实例,而不是int值。根据代码的逻辑,表和resrvation似乎应该具有相同的id来获得结果。 我认为您应该将代码更改为:

var res=rc.tReservation.Where(r => (r.DateReservation == DateTime.Today.AddDays(1))).ToList();
        var res1 = rc.tTable.Where(r => res.Any(resItem=>resItem.Id == r.Id));
        return res1;

答案 2 :(得分:0)

我假设您正在接收实体sql异常的linq。这意味着您正在尝试使用sql server中不可用的方法。

我对你的问题采取了不同的方法:

步骤#1:介绍了al

的存储库方法
/// <summary>
/// A method that allows you to get all tables reserved in a specific period. tables are only returned if they are reserverd.
/// </summary>
/// <param name="start"></param>
/// <param name="end"></param>
/// <returns></returns>
public IEnumerable<Table> GetAllReservedTables(DateTime start, DateTime end)
{
    return this.rc.tReservation
        // filter by date range
        .Where(x => x.DateReservation >= start && x.DateReservation <= end)

        // ensure table is returned
        .Select(x => x.table);
}

步骤2:调用存储库方法并确保您拥有正确的日期范围,即明天:

    TableRepository repo = new TableRepository();

    // figure out the 24 hour period you need to find reserved tables for
    // it is advisible when searching by date to use a date range instead of once specific date
    // the start date and end date will satisfy the 24 hour period of tomorrow.

    // get start tomorrow
    DateTime startDate = new DateTime(DateTime.Now.Year, DateTime.Now.Month, DateTime.Now.Day, 0, 0, 0).AddDays(1);

    // get end of tomorrow
    DateTime endDate = new DateTime(DateTime.Now.Year, DateTime.Now.Month, DateTime.Now.Day, 0, 0, 0).AddDays(2);

    // call the repository method with the date range (the 24 hour period for tomorrow)
    var tablesForTomorrow = repo.GetAllReservedTables(startDate, endDate);

    // dispaly data in console
    foreach(var table in tablesForTomorrow)
    {
        Console.WriteLine("Table Number: #{0}", table.Numero);
    }

请参阅以下完整解决方案:

using System;
using System.Collections.Generic;
using System.Data.Entity;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ReservationTableIssue
{
    class Program
    {
        static void Main(string[] args)
        {

            TableRepository repo = new TableRepository();

            // step #1 - figure out the 24 hour period you need to find reserved tables for
            // it is advisible when searching by date to use a date range instead of once specific date
            // the start date and end date will satisfy the 24 hour period of tomorrow.

            // get start tomorrow
            DateTime startDate = new DateTime(DateTime.Now.Year, DateTime.Now.Month, DateTime.Now.Day, 0, 0, 0).AddDays(1);

            // get end of tomorrow
            DateTime endDate = new DateTime(DateTime.Now.Year, DateTime.Now.Month, DateTime.Now.Day, 0, 0, 0).AddDays(2);

            // call the repository method with the date range (the 24 hour period for tomorrow)
            var tablesForTomorrow = repo.GetAllReservedTables(startDate, endDate);

            // dispaly data in console
            foreach(var table in tablesForTomorrow)
            {
                Console.WriteLine("Table Number: #{0}", table.Numero);
            }

            Console.WriteLine("press any key to exit");
            Console.ReadKey();

        }
    }

    public class Table
    {
        public int Id { get; set; }
        public bool isAvailable { get; set; }
        public int Numero { get; set; }
        public virtual ICollection<Reservation> IReservation { get; set; }
    }

    public class Reservation
    {
        public DateTime DateReservation { get; set; }
        public int Id { get; set; }
        public string Nom { get; set; }
        public virtual Table table { get; set; }
    }
    public class RestaurantContext :DbContext
    {
        public DbSet<Table> tTable { set; get; }
        public DbSet<Reservation> tReservation { set; get; }
        public RestaurantContext() : base("RestaurentDB") {     
        }
    }

    public class TableRepository
    {
        RestaurantContext rc = null;

        public TableRepository()
        {
            rc = new RestaurantContext();
        }
        public void Commit()
        {
            rc.SaveChanges();
        }
        public void AddTable(Table m)
        {
            rc.tTable.Add(m);
        }

        public IEnumerable<Table> GetAllTables()
        {
            return rc.tTable.ToList();
        }

        /// <summary>
        /// A method that allows you to get all tables reserved in a specific period. tables are only returned if they are reserverd.
        /// </summary>
        /// <param name="start"></param>
        /// <param name="end"></param>
        /// <returns></returns>
        public IEnumerable<Table> GetAllReservedTables(DateTime start, DateTime end)
        {
            return this.rc.tReservation
                // filter by date range
                .Where(x => x.DateReservation >= start && x.DateReservation <= end)

                // ensure table is returned
                .Select(x => x.table);
        }
    }

}