日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程语言 > asp.net >内容正文

asp.net

.NET Core中Object Pool的简单使用

發(fā)布時(shí)間:2023/12/4 asp.net 33 豆豆
生活随笔 收集整理的這篇文章主要介紹了 .NET Core中Object Pool的简单使用 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

前言

復(fù)用,是一個(gè)重要的話題,也是我們?nèi)粘i_發(fā)中經(jīng)常遇到的,不可避免的問題。

舉個(gè)最為簡(jiǎn)單,大家最為熟悉的例子,數(shù)據(jù)庫連接池,就是復(fù)用數(shù)據(jù)庫連接。

那么復(fù)用的意義在那里呢?

簡(jiǎn)單來說就是減少不必要的資源損耗。

除了數(shù)據(jù)庫連接,可能在不同的情景或需求下,還會(huì)有很多其他對(duì)象需要進(jìn)行復(fù)用,這個(gè)時(shí)候就會(huì)有所謂的 Object Pool(對(duì)象池)。

小伙伴們應(yīng)該也自己實(shí)現(xiàn)過類似的功能,或用ConcurrentBag,或用ConcurrentQueue,或用其他方案。

這也里分享一個(gè)在微軟文檔中的實(shí)現(xiàn)

How to: Create an Object Pool by Using a ConcurrentBag

當(dāng)然,在.NET Core中,微軟已經(jīng)幫我們實(shí)現(xiàn)了一個(gè)簡(jiǎn)單的Object Pool。

我們只需要添加Microsoft.Extensions.ObjectPool的引用即可使用了。

Microsoft.Extensions.ObjectPool

Microsoft.Extensions.ObjectPool可以說是.NET Core的一個(gè)基礎(chǔ)類庫。

它位于aspnet的Common項(xiàng)目中,類型其他基礎(chǔ)模塊都有使用相關(guān)的功能,也好比Routing項(xiàng)目。

下面就簡(jiǎn)單看看它的用法。

在開始之前,我們先定義一個(gè)可以復(fù)用的object

用法1


在創(chuàng)建pool之前,我們要先定義一個(gè)Policy。這里直接用自帶的DefaultPooledObjectPolicy來構(gòu)造。

對(duì)象池會(huì)有一個(gè)維護(hù)的最大數(shù)量,線程數(shù)。

通過pool對(duì)象的Get方法,從對(duì)象池中取出一個(gè)對(duì)象。

上面代碼運(yùn)行結(jié)果

#1-0--01/01/0001 00:00:00#2-0--01/01/0001 00:00:00#3-0--01/01/0001 00:00:00#4-0--01/01/0001 00:00:00#5-0--01/01/0001 00:00:00#6-0--01/01/0001 00:00:00#7-0--01/01/0001 00:00:00#8-0--01/01/0001 00:00:00

這個(gè)結(jié)果說明,Object Pool 中的對(duì)象都是直接new出來的,并沒有對(duì)一些屬性進(jìn)行貶值操作,這個(gè)時(shí)候往往沒有太多實(shí)際意義。

因?yàn)镈efaultPooledObjectPolicy本來就是直接new了一個(gè)對(duì)象出來,很多時(shí)候,這并不是我們所期望的!

要想符合我們實(shí)際的使用,就要自己定義一個(gè)Policy!

下面來看看用法2

用法2

先定義一個(gè)Policy,實(shí)現(xiàn)?IPooledObjectPolicy?這個(gè)接口。T很自然就是我們的Demo類了。

這里要實(shí)現(xiàn)Create和Return兩個(gè)方法。

見名知義,Create方法就是用來創(chuàng)建Demo對(duì)象的,Return方法就是將Demo對(duì)象扔回Object Pool的(有借有還)。

然后是用DemoPooledObjectPolicy去替換DefaultPooledObjectPolicy。

var demoPolicy = new DemoPooledObjectPolicy();var defaultPoolWithDemoPolicy = new DefaultObjectPool<Demo>(demoPolicy,1);//借item1 = defaultPoolWithDemoPolicy.Get();//還defaultPoolWithDemoPolicy.Return(item1);//借,但是不還item2 = defaultPoolWithDemoPolicy.Get();Console.WriteLine($"{item1.Id}-{item1.Name}-{item1.CreateTimte}"); Console.WriteLine($"{item2.Id}-{item2.Name}-{item2.CreateTimte}"); Console.WriteLine(item1 == item2);//創(chuàng)建一個(gè)新的item3 = defaultPoolWithDemoPolicy.Get(); Console.WriteLine($"{item3.Id}-{item3.Name}-{item3.CreateTimte}"); Console.WriteLine(item3 == item1);

這里定義了對(duì)象池只保留一個(gè)對(duì)象。

由于從object pool中取出來之后,有一步還回去的操作,所以item1和item2應(yīng)當(dāng)是同一個(gè)對(duì)象。

從object pool中拿出了item2之后,它并沒有還回去,所以object pool會(huì)基于我們定義的Policy去創(chuàng)建一個(gè)新的對(duì)象出來。

下面是用法2的輸出結(jié)果:

1-catcher-09/17/2018 22:32:381-catcher-09/17/2018 22:32:38True1-catcher-09/17/2018 22:32:38False

可以看到item1,item2和item3的各個(gè)屬性是一樣的,并且item1和item2確實(shí)是同一個(gè)對(duì)象。item3和item1并不是同一個(gè)。

用法3

除了DefaultObjectPool外,還有DefaultObjectPoolProvider也可以創(chuàng)建一個(gè)Object Pool。

創(chuàng)建一個(gè)Object Pool,一定是離不開Policy的,所以這里還是用了我們自己定義的DemoPooledObjectPolicy。

var defaultProvider = new DefaultObjectPoolProvider();var policy = new DemoPooledObjectPolicy();//default maximumRetained is Environment.ProcessorCount * 2ObjectPool<Demo> pool = defaultProvider.Create(policy);item1 = pool.Get(); pool.Return(item1); item2 = pool.Get();Console.WriteLine($"{item1.Id}-{item1.Name}-{item1.CreateTimte}"); Console.WriteLine($"{item2.Id}-{item2.Name}-{item2.CreateTimte}"); Console.WriteLine(item1 == item2);item3 = pool.Get(); Console.WriteLine($"{item3.Id}-{item3.Name}-{item3.CreateTimte}"); Console.WriteLine(item3 == item2);

用Provider創(chuàng)建Object Pool時(shí),不能指定保留的最大對(duì)象數(shù)量,只能用的是默認(rèn)的Environment.ProcessorCount * 2

后面的使用,和用法2是一樣的。

可以看到item1和item2是同一個(gè)對(duì)象。從Object Pool中取對(duì)象的時(shí)候,會(huì)取第一個(gè),所以還回去后,再取的話,還是會(huì)取到原來的第一個(gè)。

item3那里是直接從Object Pool中取出來的,沒有再次創(chuàng)建,因?yàn)檫@里的Object Pool維護(hù)著多個(gè)對(duì)象,而不是用法2中的只有一個(gè),所以它是直接從Pool中拿的。

下面是輸出結(jié)果

1-catcher-09/17/2018 22:38:341-catcher-09/17/2018 22:38:34True1-catcher-09/17/2018 22:38:34False

和用法2,本質(zhì)是一樣的。

用法4

好像上面的用法,都不那么像我們正常使用的。我們還是需要依賴注入的。

那么我們最后就來看看怎么結(jié)合依賴注入吧。當(dāng)然這里的本質(zhì)還是離不開Policy和Provider這兩個(gè)東西。

IServiceCollection services = new ServiceCollection(); services.AddSingleton<ObjectPoolProvider, DefaultObjectPoolProvider>(); services.AddSingleton(s => { ? ?var provider = s.GetRequiredService<ObjectPoolProvider>(); ? ?return provider.Create(new DemoPooledObjectPolicy()); }); ServiceProvider serviceProvider = services.BuildServiceProvider();var pool = serviceProvider.GetService<ObjectPool<Demo>>();item1 = pool.Get(); pool.Return(item1); item2 = pool.Get();Console.WriteLine($"{item1.Id}-{item1.Name}-{item1.CreateTimte}"); Console.WriteLine($"{item2.Id}-{item2.Name}-{item2.CreateTimte}"); Console.WriteLine(item1 == item2);item3 = pool.Get(); Console.WriteLine($"{item3.Id}-{item3.Name}-{item3.CreateTimte}"); Console.WriteLine(item3 == item2);

我們首先需要完成對(duì)Provider的注冊(cè),然后直接拿它的實(shí)例去創(chuàng)建一個(gè)Object Pool即可。

如果想在其他地方用,通過構(gòu)造函數(shù)注入即可。

這里的結(jié)果也是和前面一樣的,沒什么好多說的。

總結(jié)

在這幾種用法中,我們最常用的應(yīng)該是用法4。

但是無論那種用法,我們都需要了解,Object Pool離不開Pool,Policy和Provider這三個(gè)家伙。

有了這三個(gè),或許我們就可以為所欲為了。

當(dāng)然,它還提供了幾個(gè)特殊的東西,有興趣的可以去看看。

  • LeakTrackingObjectPool

  • StringBuilderPooledObjectPolicy

最后用一個(gè)腦圖結(jié)束本文。

原文地址:?https://www.cnblogs.com/yilezhu/p/9664977.html


.NET社區(qū)新聞,深度好文,歡迎訪問公眾號(hào)文章匯總 http://www.csharpkit.com


總結(jié)

以上是生活随笔為你收集整理的.NET Core中Object Pool的简单使用的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。