命中率=返回正确结果数/请求缓存次数,命中率问题是缓存中的一个很是重要的问题,它是衡量缓存有效性的重要指标。命中率越高,代表缓存的使用率越高。程序员
缓存中能够存放的最大元素的数量,一旦缓存中元素数量超过这个值(或者缓存数据所占空间超过其最大支持空间),那么将会触发缓存启动清空策略根据不一样的场景合理的设置最大元素值每每能够必定程度上提升缓存的命中率,从而更有效的时候缓存。redis
如上描述,缓存的存储空间有限制,当缓存空间被用满时,如何保证在稳定服务的同时有效提高命中率?这就由缓存清空策略来处理,设计适合自身数据特征的清空策略能有效提高命中率。算法
先进先出策略,最早进入缓存的数据在缓存空间不够的状况下(超出最大元素限制)会被优先被清除掉,以腾出新的空间接受新的数据。策略算法主要比较缓存元素的建立时间。在数据实效性要求场景下可选择该类策略,优先保障最新数据可用。数据库
最少使用策略,不管是否过时,根据元素的被使用次数判断,清除使用次数较少的元素释放空间。策略算法主要比较元素的hitCount(命中次数)。在保证高频数据有效性场景下,可选择这类策略。编程
最近最少使用策略,不管是否过时,根据元素最后一次被使用的时间戳,清除最远使用时间戳的元素释放空间。策略算法主要比较元素最近一次被get使用时间。在热点数据场景下较适用,优先保证热点数据的有效性。缓存
根据过时时间判断,清理过时时间最长的元素;网络
根据过时时间判断,清理最近要过时的元素;架构
随机清理;框架
根据关键字(或元素内容)长短清理等。less
虽然从硬件介质上来看,无非就是内存和硬盘两种,但从技术上,能够分红内存、硬盘文件、数据库。
将缓存存储于内存中是最快的选择,无需额外的I/O开销,可是内存的缺点是没有持久化落地物理磁盘,一旦应用异常break down而从新启动,数据很难或者没法复原。
通常来讲,不少缓存框架会结合使用内存和硬盘,在内存分配空间满了或是在异常的状况下,能够被动或主动的将内存空间数据持久化到硬盘中,达到释放空间或备份数据的目的。
前面有提到,增长缓存的策略的目的之一就是为了减小数据库的I/O压力。如今使用数据库作缓存介质是 不是又回到了老问题上了?其实,数据库也有不少种类型,像那些不支持SQL,只是简单的key-value存储结构的特殊数据库(如BerkeleyDB 和Redis),响应速度和吞吐量都远远高于咱们经常使用的关系型数据库等。
缓存有各种特征,并且有不一样介质的区别,那么实际工程中咱们怎么去对缓存分类呢?在目前的应用服务框架中,比较常见的,时根据缓存与应用的藕合度,分为local cache(本地缓存)和remote cache(分布式缓存)。
指的是在应用中的缓存组件,其最大的优势是应用和cache是在同一个进程内部,请求缓存很是快速,没有过多的网络开销等,在单应用不须要集群支持或者集群状况下各节点无需互相通知的场景下使用本地缓存较合适;同时,它的缺点也是应为缓存跟应用程序耦合,多个应用程序没法直接的共享缓存,各应用或集群的各节点都须要维护本身的单独缓存,对内存是一种浪费。
指的是与应用分离的缓存组件或服务,其最大的优势是自身就是一个独立的应用,与本地应用隔离,多个应用可直接的共享缓存。
目前各类类型的缓存都活跃在成千上万的应用服务中,还没有一种缓存方案能够解决一切的业务场景或数据类型,咱们须要根据自身的特殊场景和背景,选择最适合的缓存方案。缓存的使用是程序员、架构师的必备技能,好的程序员能根据数据类型、业务场景来准确判断使用何种类型的缓存,如何使用这种缓存,以最小的成本最快的效率达到最优的目的。
将redis集成进系统,也是能够采用这几种方式:侵入式硬编码,抽象服务化应用,以及轻量的注解式使用。
侵入式硬编码太low,并且代码可读性差且很差维护,不推荐这种方式。学习、试验时能够尝试写小例子来理解涉及的接口和类,可是实际项目中最好不要采用。
注解式是SpringBoot中提供和推荐的方式,实际项目中可使用。可是有个性化的需求时不必定能知足项目需求,可能还须要在此基础上进行扩展。
抽象化服务要作好有较高的要求,须要对框架源码有深刻的理解,长期跟踪维护、优化代码。固然,这也是能提现出理解力和水平的一个方向。