首页 学海无涯 .NET进阶 .NET缓存系列(一):缓存入门
.NET缓存系列(一):缓存入门
摘要 缓存系列合集第一篇,缓存简介、本地缓存封装等。

境准备

Visuat Studio 2019 16.8.3

.NET 5.0

目录导航

一、缓存简介

    1.什么是缓存

    2.缓存工作模式

    3.缓存的作用

    4.常见缓存

二、缓存实践

    1.查询性能问题

    2.缓存类封装

    3.使用缓存前后对比

文章正文

一、缓存简介

1.什么是缓存

缓存(Cache)就是一种数据缓冲,从客户端到数据源之间的一块数据缓冲区,当客户端请求数据源时,如果缓冲区存在数据,优先从缓冲区取得数据,不存在时则从数据源取数据。

2.缓存工作模式

  

当客户端第一次查询数据库时,缓存中没有数据,只能从数据库中查询,查询到的数据同时存一份到缓存中,客户端第二次查询数据时,直接获取缓存中的数据,不用查询数据库。

缓存的出现减少了操作步骤,减轻数据源的压力,提高性能。  

PS:缓存适用于经常查询,很少改动的数据。

3.缓存的作用

①提升性能

系统性能优化的第一步就是使用缓存,成本不高,立竿见影。当数据量大时,数据库的查询和数据传递就比较耗时,缓存有效的避免了这个问题,提高了。业务操作中有个二八原则,20%增删改,80%查询。针对这80%使用缓存,可以大大提高性能。

②缓解数据库压力

每次查询数据都使用数据库,当用户数量多,请求频繁,也会加大数据库的压力,使用缓存就会大大降低了数据库压力。

4.常见缓存

下面是网站程序中,客户端到数据库过程中能用到缓存的地方(这里简单提一下,不做详细介绍):


①浏览器客户端缓存

浏览器可以和服务器进行缓存协商,然后将服务器允许缓存的资源,缓存在内存或硬盘中。浏览器也可以进行DNS缓存。

影响范围:对单个用户生效

②CDN缓存

用户在浏览器输入域名后,DNS服务器解析后发现域名CNAME到CDN指定的域名,这时候CDN的域名交给CDN专用DNS服务器解析(这时如果CDN中有缓存,就可以使用缓存中的IP地址),然后返回IP地址给浏览器,浏览器再请求对应IP地址的服务器。

影响范围:对一批用户生效(CDN分区域分发)

③反向代理缓存

真实服务器可以使用反向代理服务器进行代理和缓存,客户端请求反向代理服务器,代理服务器会先看有没有缓存,如果有会把数据返回给客户端,如果没有,则把请求转发到真实服务器,真实服务器再把数据返回给代理服务器,代理服务器再返回给客户端。

影响范围:对所有用户生效。

④服务器本地缓存

在服务器内部分配一块内存临时存储数据用作缓存。

影响范围:对所有用户生效。  

⑤服务器分布式缓存

多个服务器共用同一个缓存(如Redis)。

影响范围:对所有用户生效。  

⑥数据库缓存

可以对数据表建立的高速缓存。

影响范围:对所有用户生效。  

二、缓存实践

1.查询性能问题

for (int i = 0; i < 5; i++)
{
    var res = Query(666);
   Console.WriteLine($"【{DateTime.Now.ToString("HH:mm:ss fff")}】查询第{i}次:{res}");
}

//查询方法
public static int Query(int count)
{
    //模拟查询耗时
    int res = 0;
    for (int i = 0; i < 400_000_000; i++)
        res += i;
    return count;
}

假定查询的数据都相同,查询比较耗时


可以看到每次查询经过1秒多才出结果。查询方法因为要连接数据库,执行SQL语句,如果数据量大的话,比较耗时,非常影响用户体验。

2.缓存类封装

对于查询结果相同的数据,我们可以使用缓存来解决性能损耗。

class CustomCache
{
    public static Dictionary<string, object> Cache { get; set; } = new Dictionary<string, object>();

    public static void Add<T>(string key, T value)
    {
        Cache[key] = value;
    }

    public static T Get<T>(string key)
    {
        if (Cache.ContainsKey(key))
        {
            return (T)Cache[key];
        }
        else
        {
            return default;
        }
    }
}

简单的缓存类封装,使用一个Dictionary集合来存储数据,将数据通过键值对的方式存放。

3.使用缓存前后对比

Console.WriteLine("------------没使用缓存------------");
for (int i = 0; i < 5; i++)
{
    var res = Query(666);
    Console.WriteLine($"【{DateTime.Now.ToString("HH:mm:ss ffff")}】查询第{i}次:{res}");
}
Console.WriteLine("------------使用缓存------------");
for (int i = 0; i < 5; i++)
{
    string key = "123";
    var res = CustomCache.Get<int>(key);
    if (res == 0)
    {
        res = Query(666);
        CustomCache.Add(key, res);
    }
    Console.WriteLine($"【{DateTime.Now.ToString("HH:mm:ss ffff")}】查询第{i}次:{res}");
}

第一次查询数据时,将数据存入缓存,后面几次全部从缓存中读取,耗时几乎可以忽略。

这就是最简单的缓存实现,性能确实提高了很多。

附录

暂无

感谢阅读,敬请斧正!


版权声明:本文由不落阁原创出品,转载请注明出处!

本文链接:http://www.leo96.com/article/detail/61

广告位

来说两句吧
最新评论

暂无评论,大侠不妨来一发?