文档章节

ASP.NET Core 中的缓存 / MemoryCache

o
 osc_o4spoba6
发布于 07/01 15:18
字数 1426
阅读 45
收藏 0

精选30+云产品,助力企业轻松上云!>>>

十年河东,十年河西,莫欺少年穷

学无止境,精益求精

ASP.NET Core 缓存Caching,.NET Core 中为我们提供了Caching 的组件。

目前Caching 组件提供了三种存储方式。

Memory

Redis

SqlServer

学习在ASP.NET Core 中使用Caching。

Memory Caching

1.新建一个 ASP.NET Core 项目,选择Web 应用程序,将身份验证 改为 不进行身份验证。

2.添加引用

Install-Package Microsoft.Extensions.Caching.Memory

3.使用

在Startup.cs 中 ConfigureServices

public void ConfigureServices(IServiceCollection services)
        {
            services.AddMemoryCache();
            // Add framework services.
            services.AddMvc();            
        }

然后在控制器中依赖注入、

private IMemoryCache _cache;

        public LongLongController(IMemoryCache memoryCache)
        {
            _cache = memoryCache;
        }

1、方法:TryGetValue 及 方法缓存的存取

public IActionResult Index()
        {
            string cacheKey_2 = "CacheKey";
            List<string> cacheEntry;
            //如果缓存没有过期,则Out测试就是缓存存储的值,注意存放值的类型应该和Out参数一致。
            var bol = _cache.TryGetValue<List<string>>(cacheKey_2, out cacheEntry);
            //判断缓存是否存在
            if (!bol)
            {
                List<string> lst = new List<string>() { "陈大六", "陈卧龙", "陈新宇", "刘丽", "花国锋" };
                var cacheEntryOptions = new MemoryCacheEntryOptions()
                 .SetSlidingExpiration(TimeSpan.FromMinutes(10));
                _cache.Set(cacheKey_2, lst, cacheEntryOptions);
            }
            ViewBag.cacheEntry = _cache.Get(cacheKey_2);
            return View();
        }

在TryGetValue 中,Out 参数的类型应与缓存中存储的值的类型一致。否则TryGetValue 中的Out参数永远为NULL。

2、设置缓存的过期时间,可采用绝对过期时间或相对过期时间两种模式;

相对过期时间设置方式:

var cacheEntryOptions = new MemoryCacheEntryOptions()
                 .SetSlidingExpiration(TimeSpan.FromSeconds(10));

代码如下:

/// <summary>
        /// 相对过期时间十秒 如果:十秒内不间断有人访问,那么在访问期间缓存不会消失。除非前后访问时间大于十秒,缓存会消失
        /// </summary>
        /// <returns></returns>
        public IActionResult Slid()
        {
            string cacheKey_2 = "SlidCache";
            List<string> cacheEntry;
            var bol = _cache.TryGetValue<List<string>>(cacheKey_2, out cacheEntry);
            //判断缓存是否存在
            if (!bol)
            {
                List<string> lst = new List<string>() { "陈大六", "陈卧龙", "陈新宇", "刘丽", "花国锋" };
                var cacheEntryOptions = new MemoryCacheEntryOptions()
                 .SetSlidingExpiration(TimeSpan.FromSeconds(10));
                _cache.Set(cacheKey_2, lst, cacheEntryOptions);
            }
            ViewBag.cacheEntry = _cache.Get(cacheKey_2);
            return View();
        }
View Code

注意上述代码中的备注;假设我们设置一个缓存的相对过期时间为10秒,缓存由A创建,十秒中内,B进入可系统,并读取了缓存,这时缓存的有效时间又会变成十秒,同理,只要缓存在十秒钟内不间断有其他人访问,则缓存永远不会过期。如果大于十秒,则缓存过期。

绝对过期时间设置方式:

var cacheEntryOptions = new MemoryCacheEntryOptions()
                 .SetAbsoluteExpiration(TimeSpan.FromSeconds(10));

代码如下:

/// <summary>
        /// 绝对过期时间 10秒
        /// </summary>
        /// <returns></returns>
        public IActionResult Abs()
        {
            string cacheKey_2 = "SlidCache";
            List<string> cacheEntry;
            var bol = _cache.TryGetValue<List<string>>(cacheKey_2, out cacheEntry);
            //判断缓存是否存在
            if (!bol)
            {
                List<string> lst = new List<string>() { "陈大六", "陈卧龙", "陈新宇", "刘丽", "花国锋" };
                var cacheEntryOptions = new MemoryCacheEntryOptions()
                 .SetAbsoluteExpiration(TimeSpan.FromSeconds(10));
                _cache.Set(cacheKey_2, lst, cacheEntryOptions);
            }
            ViewBag.cacheEntry = _cache.Get(cacheKey_2);
            return View();
        }
View Code

绝对过期时间不管期间有没有人访问,在时间过后,就会过期,清空。

3、移除缓存

_cache.Remove(cacheKey_2);

移除缓存没什么好说的,就是把缓存清空

代码如下:

/// <summary>
        /// 测试移除缓存
        /// </summary>
        /// <returns></returns>
        public IActionResult Remove()
        {
            //先添加缓存
            string cacheKey_2 = "RemoveCache";
            List<string> lst = new List<string>() { "陈大六", "陈卧龙", "陈新宇", "刘丽", "花国锋" };
            var cacheEntryOptions = new MemoryCacheEntryOptions()
             .SetAbsoluteExpiration(TimeSpan.FromHours(10));
            _cache.Set(cacheKey_2, lst, cacheEntryOptions);

            //直接移除
            _cache.Remove(cacheKey_2);
            return View();
        }
View Code

4、缓存的优先级分为四种:永不过期  大于  高优先级  大于  一般优先级  大于  低优先级。

/缓存优先级 (程序压力大时,会根据优先级自动回收)

 永不过期:

var cacheEntryOptions = new MemoryCacheEntryOptions()
             .SetPriority(CacheItemPriority.NeverRemove);

高优先级:

var HighCacheEntryOptions = new MemoryCacheEntryOptions()
             .SetPriority(CacheItemPriority.High);

一般优先级:

var NormalCacheEntryOptions = new MemoryCacheEntryOptions()
             .SetPriority(CacheItemPriority.Normal);

低优先级:

var LowCacheEntryOptions = new MemoryCacheEntryOptions()
             .SetPriority(CacheItemPriority.Low);

代码如下:

/// <summary>
        /// 缓存优先级
        /// </summary>
        /// <returns></returns>
        public IActionResult CacheLevel()
        {
            List<string> lst = new List<string>() { "陈大六", "陈卧龙", "陈新宇", "刘丽", "花国锋" };
            //NeverRemove 最高优先级 永远不会过期
            string NeverRemove = "NeverRemove";
            var cacheEntryOptions = new MemoryCacheEntryOptions()
             .SetPriority(CacheItemPriority.NeverRemove);
            _cache.Set(NeverRemove, lst, cacheEntryOptions);
            //
            //High 高优先级 永远不会过期
            string High = "High";
            var HighCacheEntryOptions = new MemoryCacheEntryOptions()
             .SetPriority(CacheItemPriority.High);
            _cache.Set(High, lst, cacheEntryOptions);
            //Normal 一般的优先级 永远不会过期
            string Normal = "Normal";
            var NormalCacheEntryOptions = new MemoryCacheEntryOptions()
             .SetPriority(CacheItemPriority.Normal);
            _cache.Set(Normal, lst, cacheEntryOptions);

            //Normal 一般的优先级 永远不会过期
            string Low = "Low";
            var LowCacheEntryOptions = new MemoryCacheEntryOptions()
             .SetPriority(CacheItemPriority.Low);
            _cache.Set(Low, lst, cacheEntryOptions);
            return View();
        }
View Code

5、缓存过期后,执行回调函数,

_cache.Set(cacheKey, lst, new MemoryCacheEntryOptions()
                .SetAbsoluteExpiration(TimeSpan.FromSeconds(10))
                .RegisterPostEvictionCallback((key, value, reason, substate) =>
                {
                    //调用回调函数
                    GetIntList(key,value,reason,substate);
                }));

代码如下:

public IActionResult cacheCallback()
        {
            List<string> lst = new List<string>() { "陈大六", "陈卧龙", "陈新宇", "刘丽", "花国锋" };
            //缓存回调 10秒过期会回调
            string cacheKey = "cacheKey";
            _cache.Set(cacheKey, lst, new MemoryCacheEntryOptions()
                .SetAbsoluteExpiration(TimeSpan.FromSeconds(10))
                .RegisterPostEvictionCallback((key, value, reason, substate) =>
                {
                    //调用回调函数
                    GetIntList(key,value,reason,substate);
                }));
            //
            return View();
        }
        public void GetIntList(object key,object value, object reason, object substate)
        {
            List<string> lst=(List<string>)value;
            //说白了就是被释放了
            Console.WriteLine($"键{key}的缓存因:{reason}而改变。");
            foreach(var item in lst)
            {
                Console.WriteLine(item);
            }
        }
View Code

6、缓存回调 根据Token过期

var cts = new CancellationTokenSource();
            _cache.Set(cacheKey, lst, new MemoryCacheEntryOptions()
                .AddExpirationToken(new CancellationChangeToken(cts.Token))
                .RegisterPostEvictionCallback((key, value, reason, substate) =>
                {
                    Console.WriteLine($"键{key}值{value}改变,因为{reason}");
                }));
            cts.Cancel(); //执行到Cancel()方法时,会执行回调删除

代码如下:

public ActionResult CacheToken()
        {
            List<string> lst = new List<string>() { "陈大六", "陈卧龙", "陈新宇", "刘丽", "花国锋" };
            string cacheKey = "CacheToken";
            //缓存回调 根据Token过期
            var cts = new CancellationTokenSource();
            _cache.Set(cacheKey, lst, new MemoryCacheEntryOptions()
                .AddExpirationToken(new CancellationChangeToken(cts.Token))
                .RegisterPostEvictionCallback((key, value, reason, substate) =>
                {
                    Console.WriteLine($"键{key}值{value}改变,因为{reason}");
                }));
            cts.Cancel(); //执行到Cancel()方法时,会执行回调删除
            return View();
        }
View Code

7、页面缓存、distributed-cache

Cshtml页面代码如下:

<distributed-cache name="mycache" expires-after="TimeSpan.FromSeconds(10)">
    <p>缓存项10秒过期-LineZero</p>
    @DateTime.Now
</distributed-cache>
<distributed-cache name="mycachenew" expires-sliding="TimeSpan.FromSeconds(10)">
    <p>缓存项有人访问就不会过期,无人访问10秒过期-LineZero</p>
    @DateTime.Now
</distributed-cache>

这样就能缓存标签内的内容。

如果你觉得本文对你有帮助,请点击“推荐”,谢谢。

@陈卧龙的博客

o
粉丝 0
博文 71
码字总数 0
作品 0
私信 提问
加载中
请先登录后再评论。
【无私分享:ASP.NET CORE 项目实战(第十一章)】Asp.net Core 缓存 MemoryCache 和 Redis

原文:【无私分享:ASP.NET CORE 项目实战(第十一章)】Asp.net Core 缓存 MemoryCache 和 Redis 目录索引  【无私分享:ASP.NET CORE 项目实战】目录索引 简介      经过 N 久反复的尝...

osc_9belkob6
05/24
9
0
【无私分享:ASP.NET CORE 项目实战(第十一章)】Asp.net Core 缓存 MemoryCache 和 Redis

原文:【无私分享:ASP.NET CORE 项目实战(第十一章)】Asp.net Core 缓存 MemoryCache 和 Redis 目录索引  【无私分享:ASP.NET CORE 项目实战】目录索引 简介      经过 N 久反复的尝...

一条属于你的未来之路
05/23
0
0
【无私分享:ASP.NET CORE 项目实战(第十一章)】Asp.net Core 缓存 MemoryCache 和 Redis

目录索引  【无私分享:ASP.NET CORE 项目实战】目录索引 简介      经过 N 久反复的尝试,翻阅了网上无数的资料,GitHub上下载了十几个源码参考, Memory 和 Redis 终于写出一个 简陋 ...

果冻布丁喜之郎
2016/08/23
0
0
.Net Core 跨平台开发实战-服务器缓存:本地缓存、分布式缓存、自定义缓存

.Net Core 跨平台开发实战-服务器缓存:本地缓存、分布式缓存、自定义缓存 1、概述   系统性能优化的第一步就是使用缓存!什么是缓存?缓存是一种效果,就是把数据结果存在某个介质中,下次...

osc_08xf0119
04/07
58
0
.Net Core 跨平台开发实战-服务器缓存:本地缓存、分布式缓存、自定义缓存

.Net Core 跨平台开发实战-服务器缓存:本地缓存、分布式缓存、自定义缓存 1、概述   系统性能优化的第一步就是使用缓存!什么是缓存?缓存是一种效果,就是把数据结果存在某个介质中,下次...

专注于房地产领域信息化-管理系统开发
04/06
0
0

没有更多内容

加载失败,请刷新页面

加载更多

Kafka如何在千万级别时优化JVM GC问题?

大家都知道Kafka是一个高吞吐的消息队列,是大数据场景首选的消息队列,这种场景就意味着发送单位时间消息的量会特别的大,那既然如此巨大的数据量,kafka是如何支撑起如此庞大的数据量的分发...

hummerstudio
06/18
6
0
我打赌!90%程序员都破解不了这个粽子,不信你试!

放假了 各位读者朋友们,马上就是端午小长假啦,开心激动有木有? 新的故事文章还在创作中,写了初稿感觉不太满意又推倒重来。其实写故事还是挺难的,读者可能第一次第二次有新鲜感,写多了就...

轩辕之风
06/24
20
0
如何删库跑路?教你使用Binlog日志恢复误删的MySQL数据

前言 “删库跑路”是程序员经常谈起的话题,今天,我就要教大家如何删!库!跑!路! 开个玩笑,今天文章的主题是如何使用Mysql内置的Binlog日志对误删的数据进行恢复,读完本文,你能够了解...

后端技术漫谈
01/14
22
0
PHP设计模式之代理模式

PHP设计模式之代理模式 代理人这个职业在中国有另外一个称呼,房产经济人、保险经济人,其实这个职业在国外都是叫做房产代理或者保险代理。顾名思义,就是由他们来帮我们处理这些对我们大部分...

硬核项目经理
2019/09/23
7
0
Redis的复制模式

Redis的复制功能分为同步(sync)和命令传播(command propagate)两个操作。 同步 同步操作用于将从服务器的数据库状态更新至主服务器当前所处的数据库状态。 1. 旧版本的执行步骤 从服务器...

osc_s9cni3go
33分钟前
5
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部