当前位置: 首页 > 知识库问答 >
问题:

Java内存和Windows

白文彬
2023-03-14

今天我注意到一些有意义的事情,但是我不能准确地解释语义。

基本上,我创建了一个简单的旧javamain方法,其中有一个永无止境的while循环。在这个循环中,我创建了一些字符串并将它们放在HashMap中。我真正想要的是一个在一段时间内运行并建立其内存利用率的进程。

public class Test {

public static void main(String[] args) throws InterruptedException {
    final HashMap<String, String> names = new HashMap<String, String>();
    while(true) {
        names.put(new Date().toString(), "lskjflksjdflksjdflkjsieurlskjflksn,kdsgkjsdlkfjslkdjfs");
        Thread.sleep(50);
    }
}

}

该过程从< code>-Xms512m -Xmx512m开始。

一旦开始,我可以使用procexp.exe来查看我的java进程。我试图理解的位是虚拟内存和物理内存。虚拟内存(私有字节)似乎映射到请求的jvm大小,即512MB。从进程随时间变化的配置文件中,我假设物理内存(工作集)是进程使用的实际内存,因为随着时间的推移,随着我的进程生成更多字符串值并填满映射,它会逐渐增加。它总是比512MB少得多。

所以我的问题是,为什么Java使用虚拟内存?

不都是在RAM即物理内存中吗?

因为我使用的是虚拟内存,这是否意味着它正在交换到磁盘?

这对性能不好吗?

有没有一种方法可以将所有内容都放在RAM中以获得更好的性能?

在Windows上任何关于这种事情的好文章都会很棒。

共有2个答案

花俊雄
2023-03-14

对于32位计算机上的每个进程,可寻址的内存是4GB,计算机实际上是否有4GB的RAM内存并不重要。

例如,如果您的计算机有2GB的RAM,对于JVM来说,它看起来有4GB的内存。另一个2GB的内存来自将内存映射到HDD中的文件(这是虚拟内存)。

如果有多个进程在运行,对于每个进程,它似乎是计算机上运行的唯一进程,有4GB的可寻址内存。由于JVM不是唯一运行的进程,操作系统中的内存管理器可能会决定将未使用内存的内容推送到虚拟内存文件中。这由操作系统决定。

由于它正在交换到磁盘,因此性能滞后将很明显(除非它是固态硬盘驱动器)

晏卓君
2023-03-14

为什么Java使用虚拟内存?

所有用户应用程序都使用虚拟内存与操作系统内存进行交互。由操作系统将其映射回物理 RAM/磁盘(通过页表)。由于您是使用 -Xms512m 启动 JVM 的,因此它在启动时将请求 500 MB 的虚拟内存空间,但操作系统选择不为此保留 500MB 的物理 RAM,因为它可能永远不会被使用。

不都是在RAM即物理内存中吗?

除非您的机器使用高百分比(

因为我使用的是虚拟内存,这是否意味着它正在交换到磁盘?

不。见上文。

这对性能不好吗?

在将数据分页到磁盘的应用程序中,分页可能会降低性能。Windows将尝试用几种方法来最小化这种影响:

  1. 发送到磁盘的虚拟内存页是最近使用最少的。
  2. 如果Windows能够检测到某个页面即将被使用(即,如果您开始迭代地图中的键,则Windows将尝试在迭代到达下一个键块之前将包含下一个键块的页面拉回),则有几种优化设计可用于从磁盘中拉回该页面

此外,正如我提到的,您很可能没有分页到磁盘。

有没有一种方法可以将所有内容都放在RAM中以获得更好的性能?

您可以在windows中关闭页面文件。这是一个带有说明的YouTube视频。

在Windows上任何关于这种事情的好文章都会很棒。

 类似资料:
  • 问题内容: 我已经在Jersey tomcat下使用Neo4j Java嵌入式版本针对REST API部署了一个应用程序。通过使用jconsole测量内存使用情况,我注意到每个REST调用都会增加200Mb的内存(我认为这是因为整个图形都已加载到内存中)。因此,仅用5个调用,服务器便分配了1Gb的内存!要清理内存,我必须等待垃圾收集器(阈值设置为1Gb)。 这是因为我使用的是neo4j java嵌

  • 本文向大家介绍java 中堆内存和栈内存理解,包括了java 中堆内存和栈内存理解的使用技巧和注意事项,需要的朋友参考一下  Java把内存分成两种,一种叫做栈内存,一种叫做堆内存 在函数中定义的一些基本类型的变量和对象的引用变量都是在函数的栈内存中分配。当在一段代码块中定义一个变量时,java就在栈中为这个变量分配内存空间,当超过变量的作用域后,java会自动释放掉为该变量分配的内存空间,该内存

  • 问题内容: 我热衷于研究Scala,并提出了一个似乎无法找到答案的基本问题:一般来说,Scala和Java在性能和内存使用方面是否有所不同? 问题答案: Scala使得无需意识到即可轻松使用大量内存。这通常非常强大,但有时可能很烦人。例如,假设您有一个字符串数组(称为),以及从这些字符串到文件的映射(称为)。假设您要获取地图中所有来自长度大于两个的字符串的文件。在Java中,您可能 ew!辛苦了

  • 我试图理解java volatile的本质及其语义,以及它对底层架构和指令的转换。如果我们考虑以下博客和资源 生成的栅栏的易失性,什么得到生成的读/写的易失性和堆栈溢出问题上的栅栏 以下是我收集的信息: volatile read在其后面插入loadStore/LoadLoad屏障(x86上的LFENCE指令) 它可以防止在后续写入/加载时对加载进行重新排序 它应该保证加载由其他线程修改的全局状态

  • 是否有可能在内存中实现缓存以避免完全堆消耗? 我的spring boot java应用程序使用内存缓存,过期策略设置为1小时(咖啡因库用于缓存目的)。在此之后,所有缓存实例都处于旧代,需要收集完整的GC。现在,当XMX设置为10GB时,我可以看到经过几个小时的测试,我的缓存包含大约100k个实例,但在heap中(正好是旧一代),我可以找到数百万个缓存对象的实例。是否有可能在内存中使用缓存并避免这种

  • 问题内容: 考虑以下代码: 似乎对象的内部数组()从未缩小。因此,当我向地图添加10000个元素,并且在调用之后,它将在其内部数组中保留10000个null。因此,我的问题是,JVM如何处理没有任何内容的数组,因此内存有效吗? 问题答案: 这个想法是仅在您想重新使用时才调用。重复使用对象的原因仅应与以前使用过的原因相同,因此,您的条目数将大致相同。为避免无用的收缩和容量调整,在调用时应保持不变。