Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/331.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如何避免嵌套使用?_C#_Sql_Asp.net Mvc_Entity Framework_Using - Fatal编程技术网

C# 如何避免嵌套使用?

C# 如何避免嵌套使用?,c#,sql,asp.net-mvc,entity-framework,using,C#,Sql,Asp.net Mvc,Entity Framework,Using,我编写了一个代码,从两个不同的数据库返回一个列表。这两个dbcontext之间的联合字段是accountid和email(两者的值相同)。因为有两个不同的数据库,所以我不能在实体框架中使用连接。所以我对每个块使用了嵌套的和。这是我的密码: namespace AdminMvc.Components.BankDepositHistory { public class BankDepositHistoryHelper { public static List<B

我编写了一个代码,从两个不同的数据库返回一个列表。这两个dbcontext之间的联合字段是
accountid
email
(两者的值相同)。因为有两个不同的数据库,所以我不能在实体框架中使用连接。所以我对每个块使用了嵌套的和。这是我的密码:

namespace AdminMvc.Components.BankDepositHistory
{
    public class BankDepositHistoryHelper
    {
        public static List<BankDepositHistoryItemDto> GetChangeRequestsList(int skip, int take, out int total, string name, string email, AvailableBankDepositStates state)
        {
            using (var myketAdsDB = new MyketAdsEntities())
            {
                using (var myketDB = new MyketReadOnlyDb())
                {
                    #region DefaultQuery
                    var bankDepositHistories = myketAdsDB.BankDepositHistories.AsQueryable();
                    #endregion
                    #region Filtering
                    if (!string.IsNullOrWhiteSpace(name))
                    {
                        var emails = myketDB.AppDevelopers
                            .Where(n => n.RealName.Contains(name))
                            .Select(e => e.Email).ToList();
                        // emails.Add(email);
                        if (emails.Count > 0)
                        {
                            bankDepositHistories = bankDepositHistories.Where(e => emails.Contains(e.AccountId));
                        }
                    }
                    if (!string.IsNullOrWhiteSpace(email))
                    {
                        bankDepositHistories = bankDepositHistories.Where(a => a.AccountId.Contains(email));
                    }
                    if (state != AvailableBankDepositStates.All)
                    {
                        bankDepositHistories = state == AvailableBankDepositStates.Success ?
                        bankDepositHistories.Where(x => x.State == AvailableBankDepositStates.Success.ToString()) :
                        bankDepositHistories.Where(x => x.State == AvailableBankDepositStates.Fail.ToString());
                    }
                    else
                    {
                        bankDepositHistories = bankDepositHistories.
                            Where(x => x.State != BankDepositState.Start.ToString());
                    }
                    #endregion
                    #region GetingTotalpages
                    total = bankDepositHistories.Count();
                    #endregion
                    #region Pagination
                    var pageResult = bankDepositHistories.OrderByDescending(ba => ba.CreationDate).Skip(skip).Take(take).ToList();
                    #endregion
                    #region FillingDomainObjects
                    var emailFilter = pageResult.Select(r => r.AccountId).ToList();
                    var developers = myketDB.AppDevelopers.Where(a => emailFilter.Contains(a.Email)).
                        Select(r => new { r.RealName, r.Email }).ToList();
                    var result = pageResult
                        .Select(b => new BankDepositHistoryItemDto()
                        {
                            Id = b.Id,
                            AccountId = b.AccountId,
                            Amount = b.Amount,
                            ClientIp = b.ClientIp,
                            State = (BankDepositState)Enum.Parse(typeof(BankDepositState), b.State, true),
                            ReturnUrl = b.ReturnUrl,
                            AdditionalData = b.AdditionalData,
                            Gateway = b.Gateway,
                            CreationDate = b.CreationDate,
                            PaymentRefNumber = b.PaymentRefNumber,
                            Uuid = b.Uuid,
                        }).ToList();
                    foreach (var bankDepositHistory in result)
                    {
                        foreach (var developer in developers)
                        {
                            if (bankDepositHistory.AccountId == developer.Email)
                            {
                                bankDepositHistory.RealName = developer.RealName;
                            }
                        }
                    }
                    return result;
                    #endregion
                }
            }
        }
名称空间AdminMvc.Components.bankDepositorHistory
{
公共类BankDepositoryHistoryHelper
{
公共静态列表GetChangeRequestsList(int skip、int take、out int total、字符串名称、字符串电子邮件、AvailableBankDepositStates状态)
{
使用(var myketAdsDB=new MyketAdsEntities())
{
使用(var myketDB=new MyketReadOnlyDb())
{
#区域默认查询
var bankDepositHistories=myketAdsDB.bankDepositHistories.AsQueryable();
#端区
#区域滤波
如果(!string.IsNullOrWhiteSpace(名称))
{
var emails=myketDB.AppDevelopers
.Where(n=>n.RealName.Contains(name))
.Select(e=>e.Email).ToList();
//电子邮件。添加(电子邮件);
如果(emails.Count>0)
{
bankDepositHistories=bankDepositHistories.Where(e=>emails.Contains(e.AccountId));
}
}
如果(!string.IsNullOrWhiteSpace(电子邮件))
{
bankDepositHistories=bankDepositHistories.Where(a=>a.AccountId.Contains(email));
}
if(state!=AvailableBankDepositStates.All)
{
bankDepositHistories=状态==可用的银行存款状态。是否成功?
bankDepositHistories.Where(x=>x.State==AvailableBankDepositStates.Success.ToString()):
bankDepositHistories.Where(x=>x.State==AvailableBankDepositStates.Fail.ToString());
}
其他的
{
银行存款历史记录=银行存款历史记录。
其中(x=>x.State!=BankDepositState.Start.ToString());
}
#端区
#区域获取总页面数
总计=银行存款历史记录。计数();
#端区
#区域分页
var pageResult=bankDepositorHistories.OrderByDescending(ba=>ba.CreationDate).Skip(Skip.Take(Take.ToList();
#端区
#区域填充域对象
var emailFilter=pageResult.Select(r=>r.AccountId.ToList();
var developers=myketDB.AppDevelopers.Where(a=>emailFilter.Contains(a.Email))。
选择(r=>new{r.RealName,r.Email}).ToList();
var result=pageResult
.Select(b=>newbankDepositoryItemTo()
{
Id=b.Id,
AccountId=b.AccountId,
金额=b.金额,
ClientIp=b.ClientIp,
State=(BankDepositState)Enum.Parse(typeof(BankDepositState),b.State,true),
ReturnUrl=b.ReturnUrl,
附加数据=b.附加数据,
网关=b.网关,
肌酸盐=肌酸盐,
PaymentRefNumber=b.PaymentRefNumber,
Uuid=b.Uuid,
}).ToList();
foreach(结果中的var bankDepositHistory)
{
foreach(开发者中的var开发者)
{
if(bankDepositHistory.AccountId==developer.Email)
{
bankDepositHistory.RealName=developer.RealName;
}
}
}
返回结果;
#端区
}
}
}
我想知道是否有可能避免使用嵌套的using,并为每个数据库编写一个单独的using。

您可以按自己的要求执行。来自内部using的电子邮件列表会影响来自外部using的
bankDepositHistories
,但外部查询直到稍后才会执行。(另外,最初的内部使用不依赖于外部的任何东西,因此可以移动到外部)

因此,首先使用
myketDB
获取电子邮件列表:

List<Email> emails = new List<Email>();
using (var myketDB = new MyketReadOnlyDb())
{
    if (!string.IsNullOrWhiteSpace(name))
    {
        emails = myketDB.AppDevelopers
            .Where(n => n.RealName.Contains(name))
            .Select(e => e.Email).ToList();
    }
}

// original outer using is now after the above
列出电子邮件=新建列表();
使用(var myketDB=new MyketReadOnlyDb())
{
如果(!string.IsNullOrWhiteSpace(名称))
{
电子邮件=myketDB.AppDevelopers
.Where(n=>n.RealName.Contains(name))
.Select(e=>e.Email).ToList();
}
}
//最初的外部使用现在是在上述之后
然后通过将原始代码中的外部using of
myketAdsDB
移动到上面using的下方来执行所有其他逻辑。这是一个接一个的,而不是嵌套的

如果您所做的不一定是事务性的,则最好按顺序访问上下文,因为您不必无缘无故地延长外部上下文的生存期。在外部上下文的内部运行可延长外部上下文的生存期。

您可以按要求执行操作。内部使用的电子邮件列表会影响ode>bankDepositHistories,它们来自外部使用,但外部查询直到稍后才会执行。(此外,原始内部使用不依赖于外部中的任何内容,因此可以移动到外部)

所以,去
public static List<BankDepositHistoryItemDto> GetChangeRequestsList(int skip, int take, out int total, string name, string email, AvailableBankDepositStates state)
{
    var statesFilter = new Dictionary<AvailableBankDepositStates, Func<IQueryable<BankDepositHistory>, IQueryable<BankDepositHistory>>>()
    {
        { AvailableBankDepositStates.All, bdh => bdh.Where(x => x.State != BankDepositState.Start.ToString()) },
        { AvailableBankDepositStates.Success, bdh => bdh.Where(x => x.State == AvailableBankDepositStates.Success.ToString()) },
        { AvailableBankDepositStates.Fail, bdh => bdh.Where(x => x.State == AvailableBankDepositStates.Fail.ToString()) },
    };

    List<string> emails = new List<string>();
    ILookup<string, string> developers = null;

    using (var myketDB = new MyketReadOnlyDb())
    {
        if (!string.IsNullOrWhiteSpace(name))
        {
            emails = myketDB.AppDevelopers.Where(n => n.RealName.Contains(name)).Select(e => e.Email).ToList();
        }
        developers = myketDB.AppDevelopers.ToLookup(x => x.Email, x => x.RealName);
    }

    using (var myketAdsDB = new MyketAdsEntities())
    {
        var bankDepositHistories = myketAdsDB.BankDepositHistories.AsQueryable();
        if (emails.Count() > 0)
        {
            bankDepositHistories = bankDepositHistories.Where(e => emails.Contains(e.AccountId));
        }
        if (!string.IsNullOrWhiteSpace(email))
        {
            bankDepositHistories = bankDepositHistories.Where(a => a.AccountId.Contains(email));
        }
        bankDepositHistories = statesFilter[state](bankDepositHistories);

        total = bankDepositHistories.Count();

        var result =
            bankDepositHistories
                .OrderByDescending(ba => ba.CreationDate)
                .Skip(skip)
                .Take(take)
                .ToList()
                .Select(b => new BankDepositHistoryItemDto()
                {
                    Id = b.Id,
                    AccountId = b.AccountId,
                    Amount = b.Amount,
                    ClientIp = b.ClientIp,
                    State = (BankDepositState)Enum.Parse(typeof(BankDepositState), b.State, true),
                    ReturnUrl = b.ReturnUrl,
                    AdditionalData = b.AdditionalData,
                    Gateway = b.Gateway,
                    CreationDate = b.CreationDate,
                    PaymentRefNumber = b.PaymentRefNumber,
                    Uuid = b.Uuid,
                    RealName = developers[b.AccountId].LastOrDefault(),
                }).ToList();

        return result;
    }
}
public enum AvailableBankDepositStates
{
    All, Success, Fail
}

public enum BankDepositState
{
    Start
}

public class BankDepositHistoryItemDto
{
    public string AccountId;
    public BankDepositState State;
    public DateTime CreationDate;
    public string RealName;
}

public class MyketAdsEntities : IDisposable
{
    public IEnumerable<BankDepositHistory> BankDepositHistories;

    public void Dispose()
    {
        throw new NotImplementedException();
    }
}

public class MyketReadOnlyDb : IDisposable
{
    public IEnumerable<AppDeveloper> AppDevelopers;

    public void Dispose()
    {
        throw new NotImplementedException();
    }
}

public class BankDepositHistory
{
    public string AccountId;
    public string State;
    public DateTime CreationDate;
}

public class AppDeveloper
{
    public string RealName;
    public string Email;
}