我想向用户展示一张10000 * 400瓷砖的热图。我的程序中的当前状态是我有一个JComponent
的类。在此JComponent
中,我为切片设置了Image
个实例。如果我有300 * 300矩阵,程序使用800到1000 MB的RAM。这太过分了。
我还能做什么,或者有人可以展示如此大的热图?
今天我测试了JHeatChart
,创建了BufferedImage
。 10000 * 400矩阵的大小不到400 MB,但是这个类需要超过15分钟来创建它。这太长了。
是否有人知道或知道可以处理数据的控件?
答案 0 :(得分:2)
您可以尝试缩放地图。因此,如果您在远处进行缩放,而不是将每个图块都打印到屏幕上,请使用更大的图块。也可以尝试将单个图块合并到一个对象,而不是保留每个图块的引用。
答案 1 :(得分:2)
由于这是一张地图,因此您无需为每个图块创建一个组件。其中许多可以重复使用。您要做的是在应用程序初始化期间,创建所有可能组件的映射,然后在每个磁贴上传递对该组件的引用。
这是一个例子。
public class HeatMap{
private static List<JComponent> tiles = new ArrayList<JComponent>();
private List<JComponent> heatmap = new ArrayList<JComponent>();
private Random rand = new Random();
static{
tiles.add(new JLabel("Cold"));
tiles.add(new JLabel("Hot"));
tiles.add(new JLabel("Warm"));
}
public HeatMap(){
for(int i=0; i<10000; i++){
for(int j=0; j<400; j++){
heatmap.add(tiles.get(rand.nextInt(3)));
}
}
}
}
在上面的例子中,我们只需要创建3个tile,其余的都是对它们的引用。这种方法应该有助于减少内存使用。
答案 2 :(得分:1)
是否真的必须将图块表示为图像或者彩色框是否足够?
如果彩色框足够,您可以在paint(...)
方法中绘制可见图块。没有必要加载这些图像。
如果必须是图像,我认为不是每个图块都是唯一的,因此不是每个图块加载图像,而是可以尝试加载所有需要的图像并使图块引用相应的图像。因此,如果您有100个不同的图像,而不是4000000个拷贝,那么您将拥有100和4000000个非常小的参考。
答案 3 :(得分:1)
无论如何呈现它,用户将永远无法同时感知四百万个数据点。因此,您永远不应该拥有四百万个图形小部件。要么缩小显示,要么(放大时),您应该一次只显示所有切片的子集。无论哪种方式,您都必须将名义上的4,000,000映射到更少的图形小部件并重用已有的小部件。
正如其他答案所指定的那样,您还应该考虑使用最简单的小部件类型来完成这项工作。
答案 4 :(得分:1)
显然,10000 * 400的瓷砖太多了,无法一次查看。相反,使用fly-weight pattern仅渲染JScrollPane
视口中可见的切片。 JTable
就是一个例子。