返回顶部
首页 > 资讯 > 精选 >Netty分布式高性能工具类recycler如何使用
  • 560
分享到

Netty分布式高性能工具类recycler如何使用

2023-06-29 18:06:35 560人浏览 八月长安
摘要

这篇文章主要介绍了Netty分布式高性能工具类recycler如何使用的相关知识,内容详细易懂,操作简单快捷,具有一定借鉴价值,相信大家阅读完这篇Netty分布式高性能工具类recycler如何使用文章都会有所收获,下面我们一起来看看吧。r

这篇文章主要介绍了Netty分布式高性能工具类recycler如何使用的相关知识,内容详细易懂,操作简单快捷,具有一定借鉴价值,相信大家阅读完这篇Netty分布式高性能工具类recycler如何使用文章都会有所收获,下面我们一起来看看吧。

recycler的使用

这一小节开始学习recycler相关的知识, recycler是netty实现的一个轻量级对象回收站, 在netty中, recycler的使用也是相当之频繁的

recycler作用是保证了对象的循环利用, 对象使用完可以通过recycler回收, 需要再次使用则从对象池中取出, 不用每次都创建新对象从而减少对系统资源的占用, 同时也减轻了GC的压力

这里看一个示例

public class RecyclerDemo {    private static final Recycler<User> RECYCLER = new Recycler<User>() {        @Override        protected User newObject(Handle<User> handle) {            return new User(handle);        }    };    static class User{        private final Recycler.Handle<User> handle;        public User(Recycler.Handle<User> handle){            this.handle=handle;        }        public void recycle(){            handle.recycle(this);        }    }    public static void main(String[] args){        User user1 = RECYCLER.get();        user1.recycle();        User user2 = RECYCLER.get();        user2.recycle();        System.out.println(user1==user2);    }}

首先定义了一个Recycler的成员变量RECYCLER, 在匿名内部类中重写了newObject方法, 也就是创建对象的方法, 该方法就是用户自定义的

这里newObject返回的new User(handle), 代表当回收站没有此类对象的时候, 可以通过这种方式创建对象

成员变量RECYCLER, 可以用来对此类对象的回收和再利用

定一个了一个静态内部类User, User中有个成员变量handle, 在构造方法中为其赋值, handle的作用, 就是用于对象回收的

并且定义了一个方法recycle, 方法体中通过handle.recycle(this)这种方式将自身对象进行回收, 通过这步操作, 就可以将对象回收到Recycler中

以上逻辑先做了解, 之后会进行详细分析

在main方法中, 通过RECYCLER的get方法获取一个user, 然后进行回收

再通过get方法将回收站的对象取出, 再次进行回收, 最后判断两次取出的对象是否为一个对象, 最后结果输出为true

以上demo就可以说明Recycler的回收再利用的功能

简单介绍了demo, 我们就详细的分析Recycler的机制

在Recycler的类的源码中, 我们看到这一段逻辑

private final FastThreadLocal<Stack<T>> threadLocal = new FastThreadLocal<Stack<T>>() {    @Override    protected Stack<T> initialValue() {        return new Stack<T>(Recycler.this, Thread.currentThread(), maxCapacityPerThread, maxSharedCapacityFactor,                 ratioMask, maxDelayedQueuesPerThread);    }};

这一段逻辑我们并不陌生, 在上一小节的学习中我们知道, 这里用于保存线程共享对象, 而这里的共享对象, 就是一个Stack类型的对象

每个stack中维护着一个DefaultHandle类型的数组, 用于盛放回收的对象, 有关stack和线程的关系如图所示:

Netty分布式高性能工具类recycler如何使用

8-3-1

也就是说在每个Recycler中, 都维护着一个线程共享的栈, 用于对一类对象的回收

跟到Stack的构造方法中

Stack(Recycler&lt;T&gt; parent, Thread thread, int maxCapacity, int maxSharedCapacityFactor,       int ratioMask, int maxDelayedQueues) {    this.parent = parent;    this.thread = thread;    this.maxCapacity = maxCapacity;    availableSharedCapacity = new AtomicInteger(max(maxCapacity / maxSharedCapacityFactor, LINK_CAPACITY));    elements = new DefaultHandle[min(INITIAL_CAPACITY, maxCapacity)];    this.ratioMask = ratioMask;    this.maxDelayedQueues = maxDelayedQueues;}

首先介绍几个构造方法中初始化的关键属性:

属性parent表示Reclycer对象自身

属性thread表示当前stack绑定的哪个线程

属性maxCapacity表示当前stack的最大容量, 表示stack最多能盛放多少个元素

属性elements, 就表示stack中存储的对象, 类型为DefaultHandle, 可以被外部对象引用, 从而实现回收

属性ratioMask是用来控制对象回收的频率的, 也就是说每次通过Reclycer回收对象的时候, 不是每次都会进行回收, 而是通过该参数控制回收频率

属性maxDelayedQueues, 这里稍微有些复杂, 在很多时候, 一个线程创建的对象, 有可能会被另一个线程所释放, 而另一个线程释放的对象是不会放在当前线程的stack中的, 而是会存放在一个叫做WeakOrderQueue的数据结构中, 里面也是存放着一个个DefaultHandle, WeakOrderQueue会存放线程1创建的并且在线程2进行释放的对象

这里只是稍作了解, 之后的会对此做详细剖析, 这里我们只需知道, maxDelayedQueues属性的意思就是我这个线程能回收几个其他创建的对象的线程, 假设当前线程是线程1, maxDelayedQueues为2, 那么我线程1回收了线程2创建的对象, 又回收了线程3创建的对象, 那么不可能回收线程4创建的对象了, 因为maxDelayedQueues2, 我只能回收两个线程创建的对象

属性availableSharedCapacity, 表示在线程1中创建的对象, 在其他线程中缓存的最大个数, 同样, 相关逻辑会在之后的内容进行剖析

另外介绍两个没有在构造方法初始化的属性:

private WeakOrderQueue cursor, prev;private volatile WeakOrderQueue head;

这里相当于指针, 用于指向WeakOrderQueue的, 这里也是稍作了解, 之后会进行详细剖析

有关stack异线程之间对象的关系如图所示(简略):

Netty分布式高性能工具类recycler如何使用

8-3-2

我们再继续介绍Recycler的构造方法, 同时熟悉有关stack各个参数的默认值:

protected Recycler() {    this(DEFAULT_MAX_CAPACITY_PER_THREAD);}

这里调用了重载的构造方法, 并传入了参数DEFAULT_MAX_CAPACITY_PER_THREAD

DEFAULT_MAX_CAPACITY_PER_THREAD的默认值是32768, 在static块中被初始化的, 我们可以跟进去自行分析

这个值就代表的每个线程中, stack中最多回收的元素的个数

继续跟重载的构造方法

protected Recycler(int maxCapacityPerThread) {    this(maxCapacityPerThread, MAX_SHARED_CAPACITY_FACTOR);}

这里又调用了重载的构造方法, 并且传入刚才传入的32768和MAX_SHARED_CAPACITY_FACTOR

MAX_SHARED_CAPACITY_FACTOR默认值是2, 同样在static块中进行了初始化, 有关该属性的用处稍后讲解

继续跟构造方法:

protected Recycler(int maxCapacityPerThread, int maxSharedCapacityFactor) {    this(maxCapacityPerThread, maxSharedCapacityFactor, RATIO, MAX_DELAYED_QUEUES_PER_THREAD);}

这里同样调用了重载的构造方法, 传入了刚才32768和2, 还有两个属性RATIO和MAX_DELAYED_QUEUES_PER_THREAD

RATIO也在static中被初始化, 默认值是8

同上, MAX_DELAYED_QUEUES_PER_THREAD的默认值是2倍cpu核数

我们继续跟构造方法:

protected Recycler(int maxCapacityPerThread, int maxSharedCapacityFactor,                    int ratio, int maxDelayedQueuesPerThread) {    ratioMask = safeFindNextPositivePowerOfTwo(ratio) - 1;    if (maxCapacityPerThread &lt;= 0) {        this.maxCapacityPerThread = 0;        this.maxSharedCapacityFactor = 1;        this.maxDelayedQueuesPerThread = 0;    } else {        this.maxCapacityPerThread = maxCapacityPerThread;        this.maxSharedCapacityFactor = max(1, maxSharedCapacityFactor);        this.maxDelayedQueuesPerThread = max(0, maxDelayedQueuesPerThread);    }}

这里将几个属性进行了初始化

首先看ratioMask, 这里的方法safeFindNextPositivePowerOfTwo的参数ratio为8, 该方法的意思就是大于等于8的2的幂次方-1, 这里就是ratioMask就是7

maxCapacityPerThread是刚才分析的32768, 是一个大于0的数, 所以进入else

maxCapacityPerThread为32768

maxSharedCapacityFactor的值为2

maxDelayedQueuesPerThread的值为2倍CPU核数

我们再回到Stack的构造方法中

Stack(Recycler&lt;T&gt; parent, Thread thread, int maxCapacity, int maxSharedCapacityFactor,       int ratioMask, int maxDelayedQueues) {    this.parent = parent;    this.thread = thread;    this.maxCapacity = maxCapacity;    availableSharedCapacity = new AtomicInteger(max(maxCapacity / maxSharedCapacityFactor, LINK_CAPACITY));    elements = new DefaultHandle[min(INITIAL_CAPACITY, maxCapacity)];    this.ratioMask = ratioMask;    this.maxDelayedQueues = maxDelayedQueues;}

根据Recycler初始化属性的逻辑, 我们可以知道Stack中几个属性的值:

maxCapacity默认值为32768

ratioMask默认值为7

maxDelayedQueues默认值是两倍cpu核数

availableSharedCapacity的默认值是32768/2, 也就是16384

关于“Netty分布式高性能工具类recycler如何使用”这篇文章的内容就介绍到这里,感谢各位的阅读!相信大家对“Netty分布式高性能工具类recycler如何使用”知识都有一定的了解,大家如果还想学习更多知识,欢迎关注编程网精选频道。

--结束END--

本文标题: Netty分布式高性能工具类recycler如何使用

本文链接: https://lsjlt.com/news/325942.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

猜你喜欢
  • Netty分布式高性能工具类recycler如何使用
    这篇文章主要介绍了Netty分布式高性能工具类recycler如何使用的相关知识,内容详细易懂,操作简单快捷,具有一定借鉴价值,相信大家阅读完这篇Netty分布式高性能工具类recycler如何使用文章都会有所收获,下面我们一起来看看吧。r...
    99+
    2023-06-29
  • Netty分布式高性能工具类FastThreadLocal和Recycler分析
    目录概述第一节:FastThreadLocal的使用和创建首先我们看一个最简单的demo跟到nextVariableIndex方法中我们首先剖析slowGet()方法我们跟进fast...
    99+
    2024-04-02
  • Netty分布式高性能工具类recycler的使用及创建
    目录recycler的使用这里看一个示例在Recycler的类的源码中, 我们看到这一段逻辑跟到Stack的构造方法中继续跟重载的构造方法我们再回到Stack的构造方法中前...
    99+
    2024-04-02
  • Netty分布式高性能工具类异线程下回收对象分析
    这篇文章主要介绍“Netty分布式高性能工具类异线程下回收对象分析”,在日常操作中,相信很多人在Netty分布式高性能工具类异线程下回收对象分析问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”Netty分布式高...
    99+
    2023-06-29
  • Netty分布式高性能工具类异线程下回收对象解析
    目录异线程回收对象跟到pushLater方法中跟到allocate方法中回到pushLater方法中简单看下link的类的定义回到pushLater方法中前文传送门:Netty分布式...
    99+
    2024-04-02
  • Netty分布式高性能工具类同线程下回收对象解析
    目录同线程回收对象回顾第三小节的demo中的main方法我们跟进recycle方法然后获取当前size同线程回收对象 上一小节剖析了从recycler中获取一个对象, 这一小节分析在...
    99+
    2024-04-02
  • 性能分析工具Systrace如何使用
    这篇“性能分析工具Systrace如何使用”文章的知识点大部分人都不太理解,所以小编给大家总结了以下内容,内容详细,步骤清晰,具有一定的借鉴价值,希望大家阅读完这篇文章能有所收获,下面我们一起来看看这篇“性能分析工具Systrace如何使用...
    99+
    2023-07-05
  • mysql中如何使用percona-toolkit性能类工具
    小编给大家分享一下mysql中如何使用percona-toolkit性能类工具,相信大部分人都还不怎么了解,因此分享这篇文章给大家参考一下,希望大家阅读完这篇文章后大有收获,下面让我们一起去了解一下吧! ...
    99+
    2024-04-02
  • 分布式系统监视工具Zabbix如何使用
    分布式系统监视工具Zabbix如何使用,很多新手对此不是很清楚,为了帮助大家解决这个难题,下面小编将为大家详细讲解,有这方面需求的人可以来学习下,希望你能有所收获。对于运维人员来说,监控是非常重要的,因为如果想要保证线上业务整体能够稳定运行...
    99+
    2023-06-28
  • Netty分布式ByteBuf如何使用page级别的内存分配
    这篇文章主要为大家展示了“Netty分布式ByteBuf如何使用page级别的内存分配”,内容简而易懂,条理清晰,希望能够帮助大家解决疑惑,下面让小编带领大家一起研究并学习一下“Netty分布式ByteBuf如何使用page级别的内存分配”...
    99+
    2023-06-29
  • 如何使用 Go 语言和 numpy 构建高性能分布式缓存?
    在当今互联网时代,数据量不断增加,对于大型应用系统而言,缓存是提高系统性能的重要手段之一。缓存机制可以有效地减少数据库的访问次数,从而提高系统的响应速度和稳定性。但是传统的单机缓存存在容量有限、可靠性差等问题,因此分布式缓存成为了一种越来...
    99+
    2023-09-03
    分布式 缓存 numpy
  • ASP网站如何使用分布式缓存来提高并发性能?
    随着互联网应用的发展,越来越多的网站需要处理大量的并发请求。为了提高网站的并发性能,我们可以使用分布式缓存技术。 分布式缓存是一种将数据缓存在多台服务器上的技术,通过将缓存数据分散在多个节点上,可以提高系统的并发性能和可扩展性。在ASP网...
    99+
    2023-10-21
    分布式 缓存 并发
  • 分布式大数据缓存如何使用 ASP 技术提高性能?
    随着互联网的快速发展,用户对网站的访问量越来越大,如何提高网站的性能成为了网站开发者的重要问题。而分布式大数据缓存是提高网站性能的一种重要方式。本文将介绍如何使用 ASP 技术来实现分布式大数据缓存,从而提高网站的性能。 一、什么是分布式...
    99+
    2023-08-16
    分布式 大数据 缓存
  • 如何使用systemtap调试工具分析MySQL的性能
    这篇文章将为大家详细讲解有关如何使用systemtap调试工具分析MySQL的性能,小编觉得挺实用的,因此分享给大家做个参考,希望大家阅读完这篇文章后可以有所收获。一、 分析SQL语句在执行各个阶段的消耗比...
    99+
    2024-04-02
  • 如何使用工具分析 PHP 函数性能瓶颈?
    php 函数性能分析工具:安装 xdebug,分析函数执行时间和内存使用情况。使用 blackfire 分析函数性能,生成交互式图表和详细报告。 如何使用工具分析 PHP 函数性能瓶颈...
    99+
    2024-04-25
    php 性能瓶颈 php7
  • 分布式索引中使用Go语言能否提高性能?
    随着互联网的快速发展,数据量急速增长,传统的单机索引已经无法满足大规模数据的需求。因此,分布式索引成为了处理大规模数据的重要方法之一。而在分布式索引的实现中,选择合适的编程语言也是至关重要的。本文将探讨在分布式索引中使用Go语言能否提高性...
    99+
    2023-07-22
    同步 分布式 索引
  • Linux各类性能分析工具用法详解
    文章目录 静态性能分析工具文件系统观测工具虚拟文件系统(VFS)分析工具磁盘管理工具进程资源占用监测系统库调用分析工具网络配置防火墙配置多路径配置进程调度系统命令操作查看硬件信息磁盘管理网络端...
    99+
    2023-09-02
    linux 运维 性能优化 自动化 监测
  • 如何在Java分布式应用程序中使用Spring函数来提高性能?
    Java分布式应用程序在实际应用中经常面临性能瓶颈的挑战,而Spring函数则是提高性能的一个有效手段。本文将探讨如何在Java分布式应用程序中使用Spring函数来提高性能。 一、什么是Spring函数? Spring函数是Spring ...
    99+
    2023-09-27
    分布式 spring 函数
  • 使用SQLBooster工具分析Oracle性能问题
    问题现象 下午开发人员反映,一个测试环境数据库访问非常慢,让我帮忙分析原因。 正好刚装了 SQLBooster ,通过它来分析,顺便熟悉一下它的使用。 原因分析 获取等待事件 数据库慢的话首先看等...
    99+
    2024-04-02
  • 性能分析工具 之 Perfetto基本使用
            Perfetto是google从Android10开始引入的一个全新的平台级跟踪分析工具。适用于Android、Linux和Chrome的更加通用和复杂的用于性能检测和跟踪分析的生产级开源项目。在android系统中对性能分...
    99+
    2023-09-05
    android 性能优化
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作