关于Java GC和我的堆栈实现链接列表

问题描述

我决定一天前开始学习Java。我选择实现一个堆栈(链接列表实现)和其他数据结构来学习它,但是我不确定我的代码以及Java GC的行为,你们可以检查我的代码是对还是错? / p>

对不起,我不认识任何Java专家,问我做对的事情是否正确。

顺便说一句,我来自C和C ++,对我的程序占用的内存相当了解。

我试图运行该程序并推入500mb内存,然后当我使用.pop()方法时,内存没有下降,我还等了20分钟,却没有任何反应。 我读到的是java自动为我们分配了内存,但是由于我没有看到它崩溃,所以感觉就像我做错了。

我的堆栈

import java.util.Scanner;

// ------------------------  node  ------------------------
class node<type>{
    type value;
    node<type> prev;

    node(type value){
        this.value = value;
    }

    // for checking I guess
    void recdisp(node<type> recurs){
        if(recurs != null){
            System.out.println(recurs.value);
            recurs.recdisp(recurs.prev);
        }
        return;
    }
}

// ------------------------  STACK  ------------------------
class mystack<type>{
    node<type> top;

    mystack(type value){
        top = new node<type>(value);
        top.prev = null;
    }

    void push(type value){
        node<type> buffer = new node<type>(value);
        buffer.prev = top;
        top = buffer;
        buffer = null;
    }

    type pop(){
        node<type> tmp;
        if(top == null){
            System.out.println("POP: Stack is Empty");
            return null;
        }
        type pass = top.value;
        tmp = top;
        top = top.prev;
        tmp = null;
        return pass;
    }

    void peek(){
        System.out.println("TOP VALUE : "+top.value);
    }

    void display(){
        if(top != null)
            top.recdisp(top);
        else
            System.out.println("display: Stack is empty");
    }
}


//  ------------------------  MAIN CLASS  ------------------------
public class myjava{
    public static void main(String []args){

        mystack<Integer> stacks = new mystack<Integer>(5);
        stacks.pop();
        stacks.pop();
        stacks.pop();
        stacks.display();

        stacks.push(10);
        stacks.push(20);
        stacks.push(30);
        stacks.push(40);

        stacks.display();
    }
}

解决方法

好的,我现在已经知道如何正确监视我的Java程序的内存,我使用“ jconsole”应用程序监视了JVM中分配的堆内存,但是似乎我需要单击此“请求垃圾”收集”之前,它可以将.poped()内存释放出我的堆栈,现在我发现了一种在Java程序中执行此“请求垃圾收集”的方法。

,

这里涉及几个概念。

JVM为您的应用程序提供自动内存管理。与C不同,您不需要为对象显式分配空间。 JVM将在堆中为您完成此操作。当您不再有对对象的引用时,该对象就有资格进行垃圾回收。重要的是要意识到,不能保证何时(或什至是)将收集对象。

大多数GC算法都使用世代堆空间(将其划分为年轻一代和老一代)。您创建的几乎所有对象都仅在很短的时间内被引用。大多数对象都是在年轻一代中收集的,从而减轻了老一代的负担。

直到最近,JVM都不愿将未使用的堆内存返回给操作系统。在JDK 12中,JEP 346引入了针对G1收集器的即时内存释放。其他一些收藏家也做类似的事情,但并非全部。

根据您的问题,无法确切地说出正在发生的事情。您没有说明堆有多大(或计算机有多少内存)。如果年轻一代足够大,则创建500Mb数据甚至可能不会触发较小的GC周期。此外,很大程度上取决于您使用的JDK版本。