EF?Core通過(guò)顯式編譯提高查詢性能
今天,我將向您展示這些EF Core中一個(gè)很酷的功能,通過(guò)使用顯式編譯的查詢,提高查詢性能。
不過(guò)在介紹具體內(nèi)容之前,需要說(shuō)明一點(diǎn),EF Core已經(jīng)對(duì)表達(dá)式的編譯使用了緩存;當(dāng)您的代碼需要重用以前執(zhí)行的查詢時(shí),EF Core將使用哈希查找并從緩存中返回已編譯的查詢。
不過(guò),您可能希望直接對(duì)查詢進(jìn)行編譯,跳過(guò)哈希的計(jì)算和緩存查找。我們可以通過(guò)在EF靜態(tài)類中下面兩個(gè)方法來(lái)實(shí)現(xiàn):
- EF.CompileQuery()
- EF.CompileAsyncQuery()
這些方法允許您定義一個(gè)已編譯的查詢,然后通過(guò)調(diào)用一個(gè)委托調(diào)用它。
為了避免因?yàn)閿?shù)據(jù)庫(kù)查詢產(chǎn)生測(cè)試結(jié)果的差異,我們這里使用內(nèi)存數(shù)據(jù)庫(kù),它開銷更小,同時(shí)也可以避免數(shù)據(jù)庫(kù)優(yōu)化執(zhí)行計(jì)劃以及緩存所帶來(lái)的問(wèn)題。
實(shí)體定義以前數(shù)據(jù)庫(kù)DbContext
定義實(shí)體
在這我們定義一個(gè)Category實(shí)體類型,非常簡(jiǎn)單,只有兩個(gè)屬性。
public class Category
{
public Guid Id { get; set; }
public string Name { get; set; }
}數(shù)據(jù)庫(kù)DbContext
在FillCategories方法中,將內(nèi)存數(shù)據(jù)庫(kù)中增加三條記錄。
public class TestDbContext : DbContext
{
public TestDbContext(DbContextOptions<TestDbContext> options) : base(options)
{
}
public DbSet<Category> Categories { get; set; }
public void FillCategories()
{
var foodCategory = new Category {
Id = Guid.NewGuid(),
Name = "Food"
};
Categories.AddRange(foodCategory, new Category {
Id = Guid.NewGuid(),
Name = "Drinks"
}, new Category {
Id = Guid.NewGuid(),
Name = "Clothing"
}, new Category {
Id = Guid.NewGuid(),
Name = "Electronis"
});
SaveChanges(true);
}
}測(cè)試代碼
public class CompileQueryTest
{
private Func<TestDbContext, Guid, Category> _getCategory =
EF.CompileQuery((TestDbContext context, Guid id) => context.Categories.FirstOrDefault(c => c.Id == id));
private readonly TestDbContext _dbContext;
public CompileQueryTest()
{
var options = new DbContextOptionsBuilder<TestDbContext>().UseInMemoryDatabase(Guid.NewGuid().ToString()).Options;
var context = new TestDbContext(options);
context.FillCategories();
_dbContext = context;
}
private readonly Guid _queryId = Guid.NewGuid();
[Benchmark]
public void CompiledQuery()
{
_ = _getCategory(_dbContext, _queryId);
}
[Benchmark]
public void UnCompiledQuery()
{
_ = _dbContext.Categories.FirstOrDefault(c => c.Id == _queryId);
}
}為了更加接近測(cè)試結(jié)果,我們?cè)跇?gòu)造函數(shù)中創(chuàng)建TestDbContext對(duì)象以及填充數(shù)據(jù)庫(kù)。
測(cè)試結(jié)果
我們使用Benchmark.Net進(jìn)行基準(zhǔn)測(cè)試,測(cè)試結(jié)果如下:
| Method | Mean | Error | StdDev |
|---|---|---|---|
| CompiledQuery | 10.59 us | 0.0580 us | 0.0543 us |
| UnCompiledQuery | 79.55 us | 0.7860 us | 0.7353 us |
經(jīng)過(guò)編譯的查詢比未編譯過(guò)的查詢存在接近8倍的差距。如果您對(duì)這個(gè)功能感興趣,不防自己測(cè)試一下。
到此這篇關(guān)于EF Core通過(guò)顯式編譯提高查詢性能的文章就介紹到這了。希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
AJAX使用post發(fā)送數(shù)據(jù)xml格式接受數(shù)據(jù)
AJAX使用post發(fā)送數(shù)據(jù)xml格式接受數(shù)據(jù),需要的朋友可以參考一下2013-03-03
asp.net HttpWebRequest自動(dòng)識(shí)別網(wǎng)頁(yè)編碼
HttpWebRequest獲取網(wǎng)頁(yè)源代碼時(shí)自動(dòng)識(shí)別網(wǎng)頁(yè)編碼,通過(guò)讀取頁(yè)面中的charset和讀取http頭中的編碼信息獲取頁(yè)面的編碼,基本可以正確獲取網(wǎng)頁(yè)編碼2008-09-09
asp.net 學(xué)習(xí)之路 項(xiàng)目整體框架簡(jiǎn)單的搭建
最近剛學(xué)了些關(guān)于asp.net mvc方面的知識(shí),于是了要拿個(gè)小項(xiàng)目來(lái)練練手,提高下自己的code能力跟思維能力2012-12-12
如何在ASP.NET Core中使用HttpClientFactory
這篇文章主要介紹了如何在ASP.NET Core中使用HttpClientFactory,幫助大家更好的理解和學(xué)習(xí)使用.net技術(shù),感興趣的朋友可以了解下2021-04-04
使用ASP.Net?WebAPI構(gòu)建REST服務(wù)
這篇文章介紹了使用ASP.Net?WebAPI構(gòu)建REST服務(wù)的方法,文中通過(guò)示例代碼介紹的非常詳細(xì)。對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2022-06-06
解析GridView自帶分頁(yè)及與DropDownList結(jié)合使用
本文主要介紹了GridView自帶的分頁(yè)功能的實(shí)現(xiàn)方法。具有一定的參考價(jià)值,需要的朋友一起來(lái)看下吧2016-12-12
ASP.NET下將Excel表格中的數(shù)據(jù)規(guī)則的導(dǎo)入數(shù)據(jù)庫(kù)思路分析及實(shí)現(xiàn)
今天接到新的需求,要求將Excel表格中的數(shù)據(jù)顯示在頁(yè)面上個(gè)人想法:首先是規(guī)則的Excel數(shù)據(jù)導(dǎo)入,再有就是不規(guī)則的Excel數(shù)據(jù)導(dǎo)入,還有就是根據(jù)數(shù)據(jù)生成Excel2013-01-01

