【问题标题】:Circular dependency when Lazy Loading between BL and BEBL和BE之间延迟加载时的循环依赖
【发布时间】:2018-01-03 09:33:50
【问题描述】:

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

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

我已经进行了一项测试以设置延迟加载,我称之为将实体从业务层填充到实体层的函数。

问题:循环依赖!我无法从 BE 调用 BL,因为 BL 使用了 BE

这是有趣的代码:

实体属性:

 // 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;
            }
        }

我制作的实体构造函数(但我不能使用它,因为有一个循环冗余:BL 调用 BE,所以 BE 不能调用 BL):

public MyEntity()
        {
        _auditType = new Lazy<AuditTypeEntity>(() => 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);
            }
        }

【问题讨论】:

  • 您根本不应该让较低层依赖于较高层,如果需要这样做,那么注入它们可以与上面层对话的方式。您基本上将这两层耦合在一起,使它们成为一层。不要这样做。
  • Lazy 与延迟加载无关。这是关于惰性初始化。你用的是什么ORM?在 EF 中默认延迟加载子实体。
  • 即使你想创建自己的 OMR/数据层(为什么?)你也不需要Lazy 来懒加载任何东西。只需检查字段的值并在实体为空时加载实体。但是,不应该暴露在数据层之外。如果您有一个实体的值在场景中可能不需要,这可能意味着您需要两个单独的实体
  • 谢谢大家。我想要延迟加载,因为我的对象非常庞大,有很多大的 List,而且有时我有时不使用这些字段,所以这就是我想使用 LazyLoading 的原因。正如我在您提出问题后的编辑中提到的那样,我使用 ADO.NET ;-)

标签: c# oop lazy-loading


【解决方案1】:

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

! DAL 是唯一应该处理 Lazy 的!

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" } };
    }
}

【讨论】:

  • 太棒了!这正是我想要的。我一直在 DAL 中延迟加载,瞧!许多 thnaks @user3608494
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2015-10-06
  • 1970-01-01
  • 2012-04-12
  • 1970-01-01
  • 2020-12-20
  • 2011-11-08
  • 1970-01-01
相关资源
最近更新 更多