Java:使用SingletonStream获得性能

仅具有一个元素的Java流有时会在应用程序中造成不必要的开销。 了解如何使用SingletonStream对象并为其中某些此类流获得十倍的性能,并了解如何同时简化代码。

背景

Java 8中的Stream库是有史以来Java语言最强大的功能之一。 一旦您开始了解它的多功能性和所产生的代码可读性,您的Java代码样式将永远改变。 与其使用forifswitch语句以及众多中间变量来充斥所有琐碎的细节,您还可以使用Stream ,它仅包含要做什么的描述,而不是实际上是如何完成的。

SingletonStream

几年前,我们不得不为Java项目做出API决定:我们应该为两种快速本地内存数据缓存方法选择哪种返回类型;

  • 唯一的搜索键,返回一个值或不返回任何值
  • 一个非唯一的搜索键,它返回任意数量的值(零到无穷大)。

这是最初的想法:

Optional<T> searchUnique(K key); // For unique keys
Stream<T> search(K key);         // For non-unique keys

但是,我们希望这两个方法看起来完全相同,并且都返回一个
Stream<T> 。 然后,API看起来会更加整洁,因为唯一缓存将看上去与非唯一缓存完全相同。

但是,唯一搜索必须非常高效,并且每秒必须创建数百万个结果对象,而又不会产生太多开销。

解决方案

通过实现仅包含单个元素的SingletonStream (因此,与具有任意数量元素的普通Stream相比,可以进行高度优化),我们能够让这两种方法在保持性能的同时返回Stream 。 如果未找到键,则方法searchUnique(K key)将返回一个空流( Stream.empty() ),如果该键存在,则它将返回SingletonStream以及与该键关联的值。 我们会得到:

Stream<T> searchUnique(K key); // For unique keys
Stream<T> search(K key);       // For non-unique keys

大! 我们可以吃饼干,仍然可以吃!

实施

SingletonStream是Speedment Stream ORM的一部分,可以在GitHub上查看。 随意使用的Speedment自己的项目中使用Speedment任何它的组件的初始化 。

SingletonStream是使用JVM的Escape Analysis进行堆栈分配的不错选择(在我以前的文章中, 这里和此处有关Escape Analysis的更多信息 )。 该实现有两种形式。 如果将STRICT值设置为true ,我们将获得一个完全惰性的Stream ,但是缺点是,一旦调用诸如.filter(), map()中间操作 ,我们将失去Singleton属性 。另一方面,将STRICT值设置为falseSingletonStream会急切地执行许多中间操作 ,并且它将能够返回新的SingletonStream从而保留Singleton属性 。 在许多情况下,这将提供更好的性能。

这里为参考流设计的解决方案也可以很容易地修改为单例流的原始形式。 因此,编写SingletonIntStream
SingletonLongStreamSingletonDoubleStream 。 这是SingletonLongStream 。

应该注意的是,该类可以进一步发展,以便它可以支持惰性评估,同时始终保持高性能。 这是未来的工作。

性能

有多种方法可以测试SingletonStream的性能,并将其与具有一个元素的标准Stream实现进行比较。

这是使用JMH的一种方法。 第一个测试(计数)仅对流中的元素数进行计数,第二个测试(forEach)对流中的一个元素执行某些操作。

@Benchmark
public long singletonStreamCount() {return SingletonStream.of("A").count();
}@Benchmark
public long streamCount() {return Stream.of("A").count();
}@Benchmark
public void singletonStreamForEach() {SingletonStream.of("A").limit(1).forEach(blackHole());
}@Benchmark
public void streamForEach() {Stream.of("A").limit(1).forEach(blackHole());
}private static <T> Consumer<T> blackHole() {
return t -> {};
}

在MacBook Pro笔记本电脑上运行时,将产生以下结果:

...
Benchmark                               Mode  Cnt           Score   Error  Units
SingletonBench.singletonStreamCount    thrpt        333419753.335          ops/s
SingletonBench.singletonStreamForEach  thrpt       2312262034.214          ops/s
SingletonBench.streamCount             thrpt         27453782.595          ops/s
SingletonBench.streamForEach           thrpt         26156364.956          ops/s
...

“计数”操作的加速因子超过10。 对于“ forEach”操作,看来JVM能够完全优化SingletonStream的完整代码路径。

测试一下

使用Speedment 初始化程序下载Speedment。

完整的测试课程在这里可用。

结论

SingletonStream或多或少地作为扩展的Optional起作用,并在保持Stream库优点的同时提供高性能。

您可以通过将STRICT值设置为首选的严格性/性能选择来选择它的两个版本。

SingletonStream可以进一步改进。

翻译自: https://www.javacodegeeks.com/2018/10/java-gain-performance-singletonstream.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/346298.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

多元线性回归分析spss结果解读_多元线性回归分析理论详解及SPSS结果分析

当影响因变量的因素是多个时候&#xff0c;这种一个变量同时与多个变量的回归问题就是多元回归&#xff0c;分为&#xff1a;多元线性回归和多元非线性回归。这里直说多元线性回归。对比一元线性回归&#xff1a;1.1多元回归模型&#xff1a;1.2多元回归方程1.3估计的多元回归方…

gilab无法解析php文件,gitlab重新设置域名后就无法访问了。

gitlab-ctl status ,查看是nignx启动不成功。查看gitlab-ctl tail日志&#xff0c;一直报这个错误 &#xff1a;> /var/log/gitlab/nginx/current <2020-01-06_09:12:15.16681 /opt/gitlab/embedded/sbin/nginx: error while loading shared libraries: libutility_mini_…

nginx请求转发被拒绝_nginx反向代理(请求转发-URL匹配规则)

反向代理适用于很多场合&#xff0c;负载均衡是最普遍的用法。nginx 作为目前最流行的web服务器之一&#xff0c;可以很方便地实现反向代理。当在一台主机上部署了多个不同的web服务器&#xff0c;并且需要能在80端口同时访问这些web服务器时&#xff0c;可以使用 nginx 的反向…

php调用pdf2html,php html2pdf

*安装composer运行html2pdf时&#xff0c;readme里面建议按照composer-setup.exe安装过程中出现openssl的问题&#xff0c;在php.ini中开启相应extension即可&#xff0c;路径写绝对路径&#xff0c;否则按默认路径找不到在html2pdf的文件路径下&#xff0c;cmd运行composer in…

electron 打开调试_Electron 应用调试指南

Electron 是一个基于 Node.js 和 Chromium 的开源框架&#xff0c;用于构建桌面应用&#xff0c;开发者可以使用 web 技术(HTML&#xff0c;JavaScript 和 CSS)完成整个应用的开发。许多知名桌面应用基于 Electron 实现&#xff0c;如 VSCode&#xff0c;Slack 和 GitHub Deskt…

java中方法的命名_Java方法中的参数太多,第5部分:方法命名

java中方法的命名在上一篇文章 &#xff08;有关处理Java方法中过多参数的系列文章的 第4部分 &#xff09;中&#xff0c;我将方法重载视为一种向客户提供需要较少参数的版本的方法或构造函数的方法。 我描述了该方法的一些缺点&#xff0c;并建议从方法重载中摆脱出来以使用不…

oracle lms进程 内存,Oracle RAC 内存融合(Cache Fusion)

原标题&#xff1a;Oracle RAC 内存融合(Cache Fusion)内存融合核心进程LMS(Global Cache Service Process)&#xff1a;这个进程负责完成GCS的大部分工作&#xff0c;它会维护GRD中数据块资源的信息&#xff0c;完成数据块在实例之间的传递工作&#xff0c;相关消息的发送和接…

sougou ubuntu 优麒麟_搜狗输入法 Linux – V2.3 版发布,完美适配优麒麟 19.10

搜狗输入法 Linux – V2.3 版发布&#xff0c;完美适配优麒麟 19.10fenshezhuiyi2 2019年10月19日 暂无评论 阅读 4,346 次昨天已发布优麒麟操作系统 19.10 版本&#xff0c;该版本集成了全新的控制面板和软件商店&#xff0c;不知道大家是否已下载体验。今天小编要为大家介绍一…

oracle多条sql语句常量,如何在Oracle中一次执行多条sql语句

有时我们需要一次性执行多条sql语句&#xff0c;而用来更新的sql是根据实际情况用代码拼出来的解决方案是把sql拼成下面这种形式&#xff1a;beginupdate TB_VG set seq 1, vessel_id Jin14, vessel_type TRACK where batch_number 20837 and train_id 0233086;update TB_…

JDK 11:新的默认收集方法toArray(IntFunction)

“ JDK 11 Early-Access发行说明 ”表明JDK 11的Early Access Build 20在Collection接口上包括一个新的默认方法 &#xff0c;该方法 “允许将集合的元素转移到所需运行时类型的新创建的数组中”。 这个新的默认方法 [ Collection.toArray&#xff08;IntFunction&#xff09; …

获取清空textarea的文字内容_运用|你会做 词云图(文字云) 吗?

词云图,也叫文字云,是对文本中出现频率较高的“关键词”予以视觉化的展现,词云图过滤掉大量的低频低质的文本信息,使得浏览者只要一眼扫过文本就可领略文本的主旨。今天&#xff0c;兰色就分享一下词云图的做法。制作步骤&#xff1a;1、打开词云图网站打开网页https://wordart…

oracle today函数,oracle日期函数集锦

一、 常用日期数据格式1.Y或YY或YYY 年的最后一位&#xff0c;两位或三位SQL> Select to_char(sysdate,Y) from dual;TO_CHAR(SYSDATE,Y)--------------------7SQL> Select to_char(sysdate,YY) from dual;TO_CHAR(SYSDATE,YY)---------------------07SQL> Select to_…

kali查看共享 linux_在Linux下访问Windows共享文件夹

在Linux下访问Windows共享文件夹说明以下操作以Ubuntu为例&#xff0c;大家可以参考。我在Ubuntu 14.04和16.04都试过了。Windows共享文件夹如果局域网内有一台Windows主机&#xff0c;将指定文件夹设为共享&#xff0c;就可以在局域网内访问了。如果要从Linux下访问该如何操作…

oracle 11gdata guard,Oracle 11g Data Guard配置

操作环境说明&#xff1a;两台服务器使用相同的Redhat 5.5内核版本为&#xff1a;2.6.18-194.el5在主库(primary database)中提前安装好了Oracle 11gR2软件&#xff0c;通过DBCA创建了数据库&#xff0c;实例名为PRIMARY备库(standby database)中只安装了Oracle 11gR2软件&…

java 可变参数方法_Java方法中的参数太多,第7部分:可变状态

java 可变参数方法在我的系列文章的第七篇中&#xff0c;有关解决Java方法或构造函数中过多参数的问题 &#xff0c;我着眼于使用状态来减少传递参数的需要。 我等到本系列的第七篇文章来解决这个问题的原因之一是&#xff0c;它是我最不喜欢的减少传递给方法和构造函数的参数的…

联想笔记本e480恢复出厂设置_联想e480进入bios设置_thinkpade480进入bios的方法

ThinkPad E480笔记本win10改win7如何修改BIOS设置?想要将预装win10系统换成win7系统&#xff0c;最重要的一步就是修改bios设置&#xff0c;这样才能在装机过程中不受到报错困扰&#xff0c;所以今天快启动小编为大家分享了详细图文教程&#xff0c;一起来看看吧。ThinkPad E4…

oracle一页显示15行,oracle rownum分页与显示记录小测

同事问及关于rownum表记录不显示问题,经查阅官方手册,附上测试笔记:SQL> insert into t_rownum select level from dual connect by level<5;5 rows insertedSQL> commit;Commit completeSQL> select * from t_rownum;A---------------------------------------123…

自动化用户特定实体的访问控制

实际上&#xff0c;每个Web应用程序都应该有多个用户&#xff0c;每个用户都有一些数据-帖子&#xff0c;文档&#xff0c;消息等等。 最明显的事情是保护这些实体免遭非这些资源合法所有者的用户获取。 不幸的是&#xff0c;这不是最容易的事情。 我并不是说很难&#xff0c;…

sqlserver安装显示句柄无效_Sqlserver 2016 R Service环境安装的各种错误(坑)解决办法...

相信很多朋友都会慕名Sqlserver 2016的R语言功能&#xff0c;将自己的数据库升级到Sqlserver 2016&#xff0c;但是当你安装完Sqlserver 2016的R语言组件之后&#xff0c;你会发现并不能直接使用&#xff0c;比如当你在SSMS中执行下面这段测试R语言命令的时候&#xff0c;Sqlse…

oracle用一个字段往上递归,深入sql oracle递归查询

获取数据库所有表名&#xff0c;表的所有列名 select name from sysobjects where xtypeuselect name from syscolumns where id(select max(id) from sysobjects where xtypeu and name表名)查询数据sql语句里的递归查询 sqlServer2005和Oracle 两个版本以前使用Oracle&#x…