C# BL和BE之间延迟加载时的循环依赖关系

C# BL和BE之间延迟加载时的循环依赖关系,c#,oop,lazy-loading,C#,Oop,Lazy Loading,我基本上有一个业务层、一个业务实体和一个数据访问(SQL)层 业务实体层由业务层和数据访问层引用 我做了一个测试来设置lazyloading,我调用了一个函数来填充业务层和实体层之间的实体 问题:循环依赖性!我不能从BE调用BL,因为BE由BL使用 下面是有趣的代码: 实体属性: // Not lazyloaded properties public int Id { get; set; } public string Description { get; se

我基本上有一个业务层、一个业务实体和一个数据访问(SQL)层

业务实体层由业务层和数据访问层引用

我做了一个测试来设置lazyloading,我调用了一个函数来填充业务层和实体层之间的实体

问题:循环依赖性!我不能从BE调用BL,因为BE由BL使用

下面是有趣的代码:

实体属性:

 // Not lazyloaded properties
        public int Id { get; set; }
        public string Description { get; set; }

        // lazy loaded properties
        private Lazy<AuditTypeEntity> _auditType = null;
        public AuditTypeEntity auditType
        {
            get
            {
                return _auditType.Value;
            }
        }
//非懒散加载的属性
公共int Id{get;set;}
公共字符串说明{get;set;}
//延迟加载属性
private Lazy _auditType=null;
公共审核类型实体审核类型
{
得到
{
返回_auditType.Value;
}
}
我创建的实体构造函数(但我不能使用它,因为存在循环冗余:BL调用BE,所以BE可以调用BL):

public MyEntity()
{
_auditType=new Lazy(()=>BusinessLayer.GetAuditTypeById(_auditTypeId).Value);
}
编辑:

我正在使用ADO.NET,它填充一个实体对象

下面是一个如何调用DAL层的示例:

public static IList<Nature> GetAllNature()
        {
            using (DAOManager daomanager = DAOFactory.CreateDaoManager(DataSource.DB_Belval))
            {
                return daomanager.GetNatureDAO().GetAll(BE.EnumEntity.NATURE.ANOMALY);
            }
        }
public静态IList GetAllNature()
{
使用(DAOManager DAOManager=DAOFactory.CreateDaoManager(DataSource.DB_Belval))
{
返回daomanager.GetNatureDAO().GetAll(BE.EnumEntity.NATURE.Exception);
}
}

以下是一个如何实现这一目标的示例。 因此,您可以使用自定义构造函数来提供惰性依赖项

!!DAL是唯一一个应该处理懒惰的人

class Program
{
    static void Main(string[] args)
    {
        var bll = new BLL();
        var person = bll.GetPerson();
        var orders = person.Orders; // GetOrders in DAL will be excuted here
    }
}

// BLL project
public class BLL
{
    public Person GetPerson()
    {
        return new DAL().GetPerson(1);
    }
}

// Entity Project
public class Person
{
    public Person()
    {

    }
    public Person(Lazy<IEnumerable<Order>> orders)
    {
        _orders = orders;
    }
    public int Id { get; set; }
    public string Name { get; set; }
    private Lazy<IEnumerable<Order>> _orders = null;

    public IEnumerable<Order> Orders
    {
        get { return _orders?.Value; }
        set { _orders = new Lazy<IEnumerable<Order>>(() => value); }
    }

}

public class Order
{
    public int Id { get; set; }
    public string Name { get; set; }
}

// DAL Project
public class DAL
{
    public Person GetPerson(int id)
    {
        var person = new Person(new Lazy<IEnumerable<Order>>(() => GetOrders(id))) // Init lazy
        {
            Id = id,
            Name = "Person"
        };
        return person;
    }

    public IEnumerable<Order> GetOrders(int personId)
    {
        return new List<Order> { new Order { Id = 2, Name = "Order" } };
    }
}
类程序
{
静态void Main(字符串[]参数)
{
var bll=新的bll();
var person=bll.GetPerson();
var orders=person.orders;//将在此处执行DAL中的GetOrders
}
}
//BLL项目
公共类BLL
{
公众人物
{
返回新的DAL().GetPerson(1);
}
}
//实体项目
公共阶层人士
{
公众人士()
{
}
公众人士(懒散命令)
{
_订单=订单;
}
公共int Id{get;set;}
公共字符串名称{get;set;}
私有懒惰_orders=null;
公共数字命令
{
获取{return\u orders?.Value;}
设置{u orders=newlazy(()=>value);}
}
}
公共阶级秩序
{
公共int Id{get;set;}
公共字符串名称{get;set;}
}
//DAL项目
公共类DAL
{
公众人物GetPerson(内部id)
{
var person=new person(new Lazy(()=>GetOrders(id))//Init Lazy
{
Id=Id,
Name=“Person”
};
返回人;
}
公共IEnumerable GetOrders(int personId)
{
返回新列表{neworder{Id=2,Name=“Order”};
}
}

您根本不应该让较低的层依赖于较高的层,如果需要这样做,则注入它们可以与上面的层对话的方式。实际上,您已经将这两个层耦合在一起,使它们成为一个层。不要这样做。
Lazy
与延迟加载无关。这是关于延迟初始化的。你在用什么?默认情况下,EF中的子实体是延迟加载的。即使您想创建自己的OMR/数据层(为什么?),也不需要
Lazy
延迟加载任何内容。只需检查字段的值,如果为空,则加载实体。但这不应该暴露在数据层之外。如果您有一个在场景中可能不需要其值的实体,这可能意味着您需要两个单独的实体。我希望延迟加载,因为我的对象非常拥挤,有很多大的列表,有时我使用这些字段,有时不是,这就是为什么我希望使用懒散加载。我使用ADO.NET,正如我在您的问题之后的编辑中提到的;-)太神了这正是我想要的。我总是懒洋洋地坐在沙发上,瞧!许多thnaks@user3608494
class Program
{
    static void Main(string[] args)
    {
        var bll = new BLL();
        var person = bll.GetPerson();
        var orders = person.Orders; // GetOrders in DAL will be excuted here
    }
}

// BLL project
public class BLL
{
    public Person GetPerson()
    {
        return new DAL().GetPerson(1);
    }
}

// Entity Project
public class Person
{
    public Person()
    {

    }
    public Person(Lazy<IEnumerable<Order>> orders)
    {
        _orders = orders;
    }
    public int Id { get; set; }
    public string Name { get; set; }
    private Lazy<IEnumerable<Order>> _orders = null;

    public IEnumerable<Order> Orders
    {
        get { return _orders?.Value; }
        set { _orders = new Lazy<IEnumerable<Order>>(() => value); }
    }

}

public class Order
{
    public int Id { get; set; }
    public string Name { get; set; }
}

// DAL Project
public class DAL
{
    public Person GetPerson(int id)
    {
        var person = new Person(new Lazy<IEnumerable<Order>>(() => GetOrders(id))) // Init lazy
        {
            Id = id,
            Name = "Person"
        };
        return person;
    }

    public IEnumerable<Order> GetOrders(int personId)
    {
        return new List<Order> { new Order { Id = 2, Name = "Order" } };
    }
}