问题 为什么更新时间太长?

Raysefo

知名会员
已加入
2019年2月22日
留言内容
194
编程经验
10+
你好,

我正在尝试按照以下服务方法更新数据库表:
C#:
//Query GameBank database
var gameBankResult = await _unitOfWork.GameBankRepository.GetGamesAsync(g =>
                                                                        g.productCode == requestDto.productCode && g.referenceId == Guid.Empty);

if (gameBankResult.Count() >= requestDto.quantity)
{
    var k = requestDto.quantity - 1;
    for (var i = k; i >= 0; --i)
    {
        gameBankResult[i].referenceId = gameRequest.referenceId;
        gameBankResult[i].requestDateTime = DateTime.Now;
        gameBankResult[i].responseDateTime = DateTime.Now;
    }

    //Update GameBank
    _unitOfWork.GameBankRepository.Update(gameBankResult[k]);

这是通用仓库更新和GetGamesAsync:
C#:
public virtual void Update(TEntity entityToUpdate)
{
    dbSet.Attach(entityToUpdate);
    context.Entry(entityToUpdate).State = EntityState.Modified;
}

C#:
public virtual async Task<List<TEntity>> GetGamesAsync(
    Expression<Func<TEntity, bool>> where)
{
    return await dbSet.Where(where).ToListAsync();
}

如果查询中有几个记录(gameBankResult)没问题,则更新非常快。但是,如果有2000条记录,则需要2分钟。顺便说一句,gameBankResult中总是有1个结果,假设是业务规则。可能是什么问题?


最好的祝福。
 
由主持人最后编辑:

金西尼

C#论坛主持人
工作人员
已加入
2011年4月23日
留言内容
3,525
地点
悉尼,澳大利亚
编程经验
10+
我已修复您代码的格式。请不要修剪掉第一行中的前导空格,然后将其留在其余行上。您只是很难阅读。如果在选择代码块时按下Alt键,则可以忽略整个代码块的空白。
 

羊皮

退休程序员
工作人员
已加入
2018年9月5日
留言内容
1,933
地点
英国
编程经验
10+
您还记得我写的关于您上一个主题的很长的帖子吗?现在您知道我为什么写它了。
如果查询中有几个记录(gameBankResult)没问题,则更新非常快。但是,如果有2000条记录,则需要2分钟。
欢迎使用EF。

我猜想它是您数据库中的SQL数据类型,以及您可能为特定列使用了错误类型的事实。数据库中的某些列可能未使用适当的数据类型,但是EF可能会假设您的数据类型与实际的数据类型不同。进行交易时,我相信交易会经历转换过程,这很可能会花费您大量的时间来执行。我建议您在EF外运行查询,直到您发现问题所在为止。如果执行正常,则说明问题出在EF之内,并且更加危险。如果没有,那么我将向您的系统管理员寻求解答。请记住,我不是这方面的专家,但这是我首先要检查的内容。也许其他人会对这个问题有更多的见识或经验。当涉及到许多查询时,EF并不是很好,尤其是在上述情况为真时。
 

Raysefo

知名会员
已加入
2019年2月22日
留言内容
194
编程经验
10+
我猜想它是您数据库中的SQL数据类型,以及您可能为特定列使用了错误类型的事实。数据库中的某些列可能未使用适当的数据类型,但是EF可能会假设您的数据类型与实际的数据类型不同。

为什么列类型错误?他们对我来说似乎还可以。

表格如下:
C#:
CREATE TABLE [dbo].[GameBanks](
    [GameBankID] [int] IDENTITY(1,1) NOT NULL,
    [referenceId] [uniqueidentifier] NOT NULL,
    [productCode] [nvarchar](max) NULL,
    [quantity] [int] NOT NULL,
    [version] [nvarchar](max) NULL,
    [requestDateTime] [datetime] NULL,
    [customerID] [int] NULL,
    [password] [nvarchar](max) NULL,
    [responseDateTime] [datetime] NULL,
    [initiationResultCode] [nvarchar](max) NULL,
    [companyToken] [nvarchar](max) NULL,
    [used] [int] NOT NULL,
    [productDescription] [nvarchar](max) NULL,
    [currency] [nvarchar](max) NULL,
    [unitPrice] [float] NOT NULL,
    [totalPrice] [float] NOT NULL,
    [ApplicationCode] [nvarchar](max) NULL,
    [estimateUnitPrice] [float] NOT NULL,
    [validatedToken] [nvarchar](max) NULL,
    [signature] [nvarchar](max) NULL,
    [status] [int] NOT NULL,
 CONSTRAINT [PK_dbo.GameBanks] PRIMARY KEY CLUSTERED
(
    [GameBankID] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
 

羊皮

退休程序员
工作人员
已加入
2018年9月5日
留言内容
1,933
地点
英国
编程经验
10+
为这些声明回发您的结构,这些声明将插入到这些字段中。
 

Raysefo

知名会员
已加入
2019年2月22日
留言内容
194
编程经验
10+
这是实体:
C#:
public class GameBank
    {
        public int GameBankID { get; set; }
        public Guid referenceId { get; set; }
        public string productCode { get; set; }
        public int quantity { get; set; }
        public string version { get; set; }
        public DateTime? requestDateTime { get; set; } = DateTime.Now;
        public int? customerID { get; set; }
        public string password { get; set; }
        public DateTime? responseDateTime { get; set; } = DateTime.Now;
        public string initiationResultCode { get; set; }
        public string companyToken { get; set; }
        public int used { get; set; }
        public string productDescription { get; set; }
        public string currency { get; set; }
        public double unitPrice { get; set; }
        public double totalPrice { get; set; }
        public string ApplicationCode { get; set; }
        public double estimateUnitPrice { get; set; }
        public string validatedToken { get; set; }
        public string signature { get; set; }
        public int status { get; set; }
        public virtual List<GameBankPin> coupons { get; set; }
    }
 

跳伞

工作人员
已加入
2019年4月6日
留言内容
2,536
地点
弗吉尼亚州切萨皮克
编程经验
10+
Have you run with a profiler? Where is most of the time spent? In the call to Update() or in the call to GetGameAsync()?

顺便说一句,从后端浏览列表并不十分友好,但是如果您的探查器显示它是for循环而要花费大量时间,则可以在以后解决此优化问题。
 

Raysefo

知名会员
已加入
2019年2月22日
留言内容
194
编程经验
10+
我运行了探查器,查询没有性能问题。问题是自动映射器:

C#:
//Query GameBank database
var gameBankResult = await _unitOfWork.GameBankRepository.GetGamesAsync(g =>
g.productCode == requestDto.productCode && g.referenceId == Guid.Empty);

if (gameBankResult.Count() >= requestDto.quantity)
{
     var k = requestDto.quantity - 1;
     for (var i = k; i >= 0; --i)
      {
            gameBankResult[i].referenceId = gameRequest.referenceId;
            gameBankResult[i].requestDateTime = DateTime.Now;
            gameBankResult[i].responseDateTime = DateTime.Now;
      }

//Update GameBank
_unitOfWork.GameBankRepository.Update(gameBankResult[k]);

var gameBankConfirmResponse = iMapper.Map<IList<GameBank>, IList<GameConfirmResponse>>(gameBankResult);
 
Last edited:

Raysefo

知名会员
已加入
2019年2月22日
留言内容
194
编程经验
10+
我现在如下更改了代码,根据数量,gameBankResult最多变为2或3个项目列表。现在没有映射延迟。
C#:
//Query GameBank database
var gameBankResult = await _unitOfWork.GameBankRepository.GetGamesAsync(g =>
g.productCode == requestDto.productCode && g.referenceId == Guid.Empty);

gameBankResult = gameBankResult.Take(requestDto.quantity).ToList();
 
Last edited:
最佳 底部