JavaFX 2 XYCharts和Java 7功能

我最喜欢的JavaFX 2功能之一是它在javafx.scene.chart包中提供的标准图表。 该软件包提供了几种不同类型的现成图表。 除了其中之一( PieChart )以外,所有其他都是“ 2轴图”( XYChart的特定实现)。 在本文中,我将介绍XYChart这些专业之间的共性。 在此过程中,我将介绍一些方便的Java 7功能。

接下来显示javafx.scene.chart包中关键图类型的UML类图。 注意AreaChart , StackedAreaChart , BarChart , StackedBarChart , BubbleChart , LineChart和ScatterChart都扩展了XYChart

正如上面的UML图(使用JDeveloper生成)所示, PieChart直接扩展Chart ,而所有其他图表类型都扩展XYChart 。 因为除PieChart之外的所有其他图表类型都扩展了XYChart ,所以它们共享一些共同的功能。 例如,它们都是带有水平('x')轴和垂直('y')轴的2轴图表。 它们通常允许为所有XY图表以相同的格式(数据结构)指定数据。 这篇文章的其余部分演示了能够对大多数XYChart使用相同的数据。

图表的主要用途是显示数据,因此下一个代码清单指示从Oracle数据库中的“ hr ” 样本架构中检索数据。 请注意,JDBC_URL,USERNAME,PASSWORD和AVG_SALARIES_PER_DEPARTMENT_QUERY是在JDBC连接和查询中使用的常量字符串。

getAverageDepartmentsSalaries()

/*** Provide average salary per department name.* * @return Map of department names to average salary per department.*/
public Map<String, Double> getAverageDepartmentsSalaries()
{final Map<String, Double> averageSalaryPerDepartment = new HashMap<>();try (final Connection connection = DriverManager.getConnection(JDBC_URL, USERNAME, PASSWORD);final Statement statement = connection.createStatement();final ResultSet rs = statement.executeQuery(AVG_SALARIES_PER_DEPARTMENT_QUERY)){while (rs.next()){final String departmentName = rs.getString(COLUMN_DEPARTMENT_NAME);final Double salaryAverage = rs.getDouble(ALIAS_AVERAGE_SALARY);averageSalaryPerDepartment.put(departmentName, salaryAverage);}}catch (SQLException sqlEx){LOGGER.log(Level.SEVERE,'Unable to get average salaries per department - {0}', sqlEx.toString());}return averageSalaryPerDepartment;
}

上面的Java代码段使用JDBC检索数据,以将部门名称字符串Map为每个部门中雇员的平均工资。 此代码中使用了几个方便的Java 7功能。 一个小的功能是与局部变量averageSalaryPerDepartment的声明一起使用的diamond运算符的推断通用参数化类型(第8行)。 这是语法糖的一小部分,但确实使代码更简洁。

Java 7的一项更重要的功能是使用try-with-resources语句来处理Connection , Statement和ResultSet资源(第9-11行)。 与以前使用JDBC相比,即使面对异常,这也是处理这些资源打开和关闭的一种更好的方法。 try-with-resources语句上的Java Tutorials页面广告该语句“确保在语句末尾关闭每个资源”,并且确保每个资源都将被“关闭”,而不管try语句是正常完成还是突然完成。 该页面还指出,与上述代码一样,在同一语句中指定了多个资源时,“资源的close方法将按其创建的相反顺序进行调用。”

从数据库检索的数据可以放入适当的数据结构中,以支持大多数XYCharts的使用。 这在下一个方法中显示。

ChartMaker.createXyChartDataForAverageDepartmentSalary(地图)

/*** Create XYChart Data representing average salary per department name.* * @param newAverageSalariesPerDepartment Map of department name (keys) to*    average salary for each department (values).* @return XYChart Data representing average salary per department.*/
public static ObservableList<XYChart.Series<String, Double>> createXyChartDataForAverageDepartmentSalary(final Map<String, Double> newAverageSalariesPerDepartment)
{final Series<String, Double> series = new Series<>();series.setName('Departments');for (final Map.Entry<String, Double> entry : newAverageSalariesPerDepartment.entrySet()){series.getData().add(new XYChart.Data<>(entry.getKey(), entry.getValue()));}final ObservableList<XYChart.Series<String, Double>> chartData =FXCollections.observableArrayList();chartData.add(series);return chartData;
}

刚刚显示的方法将检索到的数据放置在几乎所有基于XYChart的图表都可以使用的数据结构中。 现在,将检索到的数据打包到JavaFX可观察的集合中,就可以轻松生成图表。 下一个代码片段显示了用于生成多个基于XYChart的图表(面积,条形图,气泡图,折线图和散点图)的方法。 请注意它们都是多么相似,以及如何使用由相同方法提供的相同数据。 StackedBar和StackedArea图表也可以使用类似的数据,但此处未显示,因为它们对于本示例中使用的单个数据系列没有意义。

除BubbleChart和堆积图表外的生成XYCharts的方法

private XYChart<String, Double> generateAreaChart(final Axis<String> xAxis, final Axis<Double> yAxis)
{final AreaChart<String, Double> areaChart =new AreaChart<>(xAxis, yAxis,ChartMaker.createXyChartDataForAverageDepartmentSalary(this.databaseAccess.getAverageDepartmentsSalaries()));return areaChart;
}private XYChart<String, Double> generateBarChart(final Axis<String> xAxis, final Axis<Double> yAxis)
{final BarChart<String, Double> barChart =new BarChart<>(xAxis, yAxis,ChartMaker.createXyChartDataForAverageDepartmentSalary(this.databaseAccess.getAverageDepartmentsSalaries()));return barChart;
}private XYChart<Number, Number> generateBubbleChart(final Axis<String> xAxis, final Axis<Double> yAxis)
{final Axis<Number> deptIdXAxis = new NumberAxis();deptIdXAxis.setLabel('Department ID');final BubbleChart<Number, Number> bubbleChart =new BubbleChart(deptIdXAxis, yAxis,ChartMaker.createXyChartDataForAverageDepartmentSalaryById(this.databaseAccess.getAverageDepartmentsSalariesById()));return bubbleChart;
}private XYChart<String, Double> generateLineChart(final Axis<String> xAxis, final Axis<Double> yAxis)
{final LineChart<String, Double> lineChart =new LineChart<>(xAxis, yAxis,ChartMaker.createXyChartDataForAverageDepartmentSalary(this.databaseAccess.getAverageDepartmentsSalaries()));return lineChart;
}private XYChart<String, Double> generateScatterChart(final Axis<String> xAxis, final Axis<Double> yAxis)
{final ScatterChart<String, Double> scatterChart =new ScatterChart<>(xAxis, yAxis,ChartMaker.createXyChartDataForAverageDepartmentSalary(this.databaseAccess.getAverageDepartmentsSalaries()));return scatterChart;
}

这些方法是如此相似,以至于我实际上可以使用方法句柄(或更传统的反射API)来反射性地调用适当的图表构造函数,而不是使用单独的方法。 但是,我在2月的2013年RMOUG培训日演讲中使用了这些功能,因此希望保留图表专用的构造函数,以使它们对观众更清晰。

XYChart类型的常规处理的一个例外是BubbleChart的处理。 此图表的x轴需要数字类型,因此上面提供的基于字符串(部门名称)的x轴数据将不起作用。 另一种方法(此处未显示)提供了一个查询,该查询按部门ID(长)而不是部门名称返回平均工资。 接下来显示了稍有不同的generateBubbleChart方法。

generateBubbleChart(Axis,Axis)

private XYChart<Number, Number> generateBubbleChart(final Axis<String> xAxis, final Axis<Double> yAxis){final Axis<Number> deptIdXAxis = new NumberAxis();deptIdXAxis.setLabel('Department ID');final BubbleChart<Number, Number> bubbleChart =new BubbleChart(deptIdXAxis, yAxis,ChartMaker.createXyChartDataForAverageDepartmentSalaryById(this.databaseAccess.getAverageDepartmentsSalariesById()));return bubbleChart;}

可以编写代码来直接调用每种不同的图表生成方法,但这为使用Java 7的方法句柄提供了一个很好的机会。 下一个代码片段显示了此操作。 该代码不仅演示了方法句柄,而且还使用了Java 7的多捕获异常处理机制(第77行)。

/*** Generate JavaFX XYChart-based chart.* * @param chartChoice Choice of chart to be generated.* @return JavaFX XYChart-based chart; may be null.* @throws IllegalArgumentException Thrown if the provided parameter is null.*/
private XYChart<String, Double> generateChart(final ChartTypes chartChoice)
{XYChart<String, Double> chart = null;final Axis<String> xAxis = new CategoryAxis();xAxis.setLabel('Department Name');final Axis<? extends Number> yAxis = new NumberAxis();yAxis.setLabel('Average Salary');if (chartChoice == null){throw new IllegalArgumentException('Provided chart type was null; chart type must be specified.');}else if (!chartChoice.isXyChart()){LOGGER.log(Level.INFO,'Chart Choice {0} {1} an XYChart.',new Object[]{chartChoice.name(), chartChoice.isXyChart() ? 'IS' : 'is NOT'});}final MethodHandle methodHandle = buildAppropriateMethodHandle(chartChoice);try{chart =methodHandle != null? (XYChart<String, Double>) methodHandle.invokeExact(this, xAxis, yAxis): null;chart.setTitle('Average Department Salaries');}catch (WrongMethodTypeException wmtEx){LOGGER.log(Level.SEVERE,'Unable to invoke method because it is wrong type - {0}',wmtEx.toString());}catch (Throwable throwable){LOGGER.log(Level.SEVERE,'Underlying method threw a Throwable - {0}',throwable.toString());}return chart;
}/*** Build a MethodHandle for calling the appropriate chart generation method* based on the provided ChartTypes choice of chart.* * @param chartChoice ChartTypes instance indicating which type of chart*    is to be generated so that an appropriately named method can be invoked*    for generation of that chart.* @return MethodHandle for invoking chart generation.*/
private MethodHandle buildAppropriateMethodHandle(final ChartTypes chartChoice)
{MethodHandle methodHandle = null;final MethodType methodDescription =MethodType.methodType(XYChart.class, Axis.class, Axis.class);final String methodName = 'generate' + chartChoice.getChartTypeName() + 'Chart';try{methodHandle =MethodHandles.lookup().findVirtual(this.getClass(), methodName, methodDescription);}catch (NoSuchMethodException | IllegalAccessException exception){LOGGER.log(Level.SEVERE,'Unable to acquire MethodHandle to method {0} - {1}',new Object[]{methodName, exception.toString()});}return methodHandle;
}

随后的一系列图像显示了由JavaFX渲染时这些XY图表的显示方式。

面积图

条形图

气泡图

折线图

散点图

如上所述,方法句柄可能已被用来进一步减少代码,因为用于生成每个XYChart各个方法不是绝对必要的,并且可以根据所需的图表类型进行反射式调用。 还值得强调的是,如果x轴数据是数字的,则所有XYChart类型(包括气泡图)的代码都是相同的(并且可以被反射地调用)。

JavaFX使生成代表所提供数据的吸引人的图表变得容易。 Java 7功能通过使代码更简洁,更具表现力,并允许在适当的情况下轻松应用反射,使此操作变得更加容易。

参考:来自JCG合作伙伴 Dustin Marx的JavaFX 2 XYCharts和Java 7功能,来自Inspired by Actual Events博客。

翻译自: https://www.javacodegeeks.com/2013/01/javafx-2-xycharts-and-java-7-features.html

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

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

相关文章

前端基础-HTML的的标签详解

阅读目录 一、head内常用标签二、 HTML语义化三、 字符实体四、 h系列标签五、 p标签六、 img标签七、 a标签八、 列表标签九、 table标签十、 form标签 一、 head内常用标签 1、meta相关 #1、指定字符集<meta charset"gbk">#2、页面描述<meta name"…

new失败跟踪函数_WinDbg预览时间线:调试器中的时间线可以允许用户记录跟踪

时间旅行调试(TTD)允许用户记录跟踪&#xff0c;这些跟踪是对程序执行的记录。时间线是执行过程中发生的事件的直观表示&#xff0c;这些事件可以是包括断点&#xff0c;内存读/写&#xff0c;函数调用和返回以及异常。使用时间线窗口可以快速查看重要事件&#xff0c;了解相对…

linux 进程的执行时间,Linux 获取进程执行时间

Linux 获取进程执行时间1 前言测试一个程序的执行时间, 时间包括用户 CPU 时间系统 CPU 时间时钟时间之前获取之前时间都是在程序的 main 函数用 time 函数实现, 这个只能粗略的计算程序的执行时间, 不能准确的获取其他时间在看 APUE 时, 书中有关程序时间测试程序, 非常正规, …

Java环境变量的设置

1.计算机->属性->高级系统设置->环境变量 2.设置JAVA_HOME和path&#xff0c;1.5之后的JDK可以不设置classpath 3.JAVA_HOME的路径是JDK的安装路径 4.在系统变量里面找到path&#xff0c;然后点击修改&#xff0c;在最后面添加%JAVA_HOME%\bin;%JAVA_HOME%\jre\bin; 5…

华为抢购助手_华为荣耀20系列手机采用的五项新科技,科普简介

5月底荣耀20系列在上海发布&#xff0c;荣耀20系列旗舰手机拥有五项荣耀自主研发的新科技&#xff0c;包括LinkTurbo网络聚合加速、超级NFC、方舟编译器、人性化YOYO智慧生命体&#xff0c;超级蓝牙。下面分别介绍一下这五项新科技。LinkTurbo网络聚合加速先来科普一下LinkTurb…

Flex弹性布局

1 Flex: 弹性布局 (转) 任何一个容器都可以指定为 Flex 布局。 1 .box {2  display: flex;3 } 行内元素也可以使用 Flex 布局。 1 .box{2 display: inline-flex;3 } 注意&#xff0c;设为 Flex 布局以后&#xff0c;子元素的 float、 clear 和 vertical-align 属性将失效…

firewallD卸载Linux,在Ubuntu 18.04/16.04系统上安装和使用Firewalld的方法

本文介绍Firewalld在Ubuntu 18.04或Ubuntu 16.04发行版上的安装方法及基本用法。简介Firewalld是Linux防火墙管理工具&#xff0c;支持IPv4、IPv6、以太网桥和IPSet防火墙设置&#xff0c;它充当Linux内核的netfilter框架的前端&#xff0c;同时Firewalld是RHEL 7系列上的默认防…

PCGen的垃圾收集分析

介绍 我决定结合我的两个软件爱好&#xff0c;并在PCGen上进行一些分析&#xff0c; PCGen是一种流行的基于Java的开放源代码角色生成器&#xff0c;用于角色扮演游戏。 我用Censum &#xff0c;我们&#xff08; jClarity的&#xff09;新的垃圾收集日志分析工具来进行分析。 …

springboot不会运行gc_SpringBoot 和JVM 调优(深度好文,建议收藏)

点击上方[全栈开发者社区]→右上角[...]→[设为星标⭐]项目调优作为一名工程师&#xff0c;项目调优这事&#xff0c;是必须得熟练掌握的事情。在SpringBoot项目中&#xff0c;调优主要通过配置文件和配置JVM的参数的方式进行。一、修改配置文件关于修改配置文件 application.p…

3dobject用什么打开_第一次用开塞露是什么感觉?网友:像打开了新世界的大门

第一次用开塞露是什么感觉&#xff1f;网友:像打开了新世界的大门我妈说我小时候便秘去医院&#xff0c;医生给开了支开塞露&#xff0c;然后在医院的公厕里使用的&#xff0c;我妈的描述是:“要不是我手挪走的快点&#xff0c;就直接喷我手了”。。。。。。。。。。。。。。。…

Java 7中对String.substring的更改

众所周知&#xff0c;在您生成相同源字符串的许多子字符串的情况下&#xff0c;Java会优化子字符串操作。 它通过使用(value, offset, count)存储信息的方式来做到这一点。 请参阅以下示例&#xff1a; 在上图中&#xff0c;您会看到字符串“ Hello”和“ World&#xff01;”…

原生js创建模态框

1.效果图如下&#xff1a; 2.代码如下&#xff1a; <!DOCTYPE html><html><head><meta charset"UTF-8"><title>Test</title><style>#pageMask {visibility: hidden; position: absolute;left: 0px; top: 0px;width:…

CSS节选——选择器

CSS&#xff0c;cascading style sheet&#xff0c;层叠样式表&#xff0c;请留意层叠概念。 css3为了区分伪类和伪元素&#xff0c;伪元素采用双冒号写法。 常见伪类——:hover,:link,:active,:target,:not(),:focus。 常见伪元素——::first-letter,::first-line,::before…

vue.js基础知识篇(7):表单校验详解

目录 网盘 第12章:表单校验 1.npm安装vue-validator $ npm install vue-validator 代码示例: var Vuerequire("vue"); var VueValidatorrequire("vue-validator"); Vue.use(VueValidator); 2.直接使用script标签引入vue.js 要下载vue-validator&#xff0c…

SQL数据库中临时表、临时变量和WITH AS关键词创建“临时表”的区别

原文链接&#xff1a;https://www.cnblogs.com/zhaowei303/articles/4204805.html SQL数据库中数据处理时&#xff0c;有时候需要建立临时表&#xff0c;将查询后的结果集放到临时表中&#xff0c;然后在针对这个数据进行操作。 创建“临时表”&#xff08;逻辑上的临时表&…

zbb20170626 myeclipse 2017 ci 构建 spring hibernate struts jar

转载于:https://www.cnblogs.com/super-admin/p/7081209.html

Java线程:保留的内存分析

本文将为您提供一个教程&#xff0c;使您可以确定活动应用程序Java线程保留Java堆空间的数量和位置。 将提供来自Oracle Weblogic 10.0生产环境的真实案例研究&#xff0c;以使您更好地理解分析过程。 我们还将尝试证明过多的垃圾回收或Java堆空间的内存占用问题通常不是由真正…

软件测试白皮书-等价类

设有一个档案管理系统&#xff0c;要求用户输入以年月表示的日期。假设日期限定在1990年1月~2049年12月&#xff0c;并规定日期由6位数字字符组成&#xff0c;前4位表示年&#xff0c;后2位表示月。现用等价类划分法设计测试用例&#xff0c;来测试程序的"日期检查功能&qu…

深入css布局 (1) — 盒模型 元素分类

深入css布局&#xff08;1&#xff09;—— 盒模型 & 元素分类 “ 在css知识体系中&#xff0c;除了css选择器&#xff0c;样式属性等基础知识外&#xff0c;css布局相关的知识才是css比较核心和重要的点。今天我们来深入学习一下css布局相关的知识。” 首先来列下大纲 盒模…

批改网禁止粘贴怎么破_教育部对家长批改作业表态了,明令禁止!你怎么看?...

互联网的发展&#xff0c;的确方便了现代人生活。视频电话、出去买东西你都不用带钱带卡&#xff0c;手机一扫就可以完成支付。很多中小学的家长都会建一个家长群&#xff0c;方便老师和家长的沟通。这个群可以说是家长和学校的桥梁和纽带&#xff0c;家长们为了支持老师的工作…