对于我的java程序,是我的2个静态方法(实际上只是函数)导致内存泄漏

时间:2017-07-10 15:53:52

标签: java memory

我的java程序永远运行(故意); main有一段时间(true),它在从服务器读取JSON数据并在嵌入式h2数据库中进行大量内部处理方面做了大量工作。

我在main之外定义了两个静态函数来完成大部分工作:getUrl(使用输入参数执行HTTP GET)和postUrl(使用参数执行HTTP POST)。两者都只是从localhost服务器请求HTTP数据,并将一个JsonNode对象(来自jackson json类)返回给调用者,该对象将while(true)处理数据的内容输入h2。

几天之后,java进程神秘地被杀死了#34 ;;研究表明,OOM很可能是罪魁祸首。我尝试在最后一段时间使用System.gc()(true),但这没有用。这是postUrl(getUrl几乎相同,postUrl有2个args输入,getUrl只需要1)

  static JsonNode postUrl(String requestType, String postData) throws Exception {
  //use HTTP POST to API and return JSON data
    String output="";
    try {
      URL obj = new URL(post + requestType);
      HttpURLConnection con = (HttpURLConnection) obj.openConnection();
      con.setRequestMethod("POST");
      String urlParameters = urlParmPrefix + requestType + postData;
      con.setDoOutput(true);
      DataOutputStream wr = new DataOutputStream(con.getOutputStream());
      wr.writeBytes(urlParameters);
      wr.flush();
      wr.close();
      BufferedReader in = new BufferedReader(new InputStreamReader(con.getInputStream()));
      String inputLine;
      StringBuilder response = new StringBuilder();
      while ((inputLine = in.readLine()) != null) {
        response.append(inputLine);
      }
      in.close();
      output = response.toString();
      } catch (Exception postUrlFUNCTION) {
        System.out.println("Function postUrl failed for: " + postData);
        postUrlFUNCTION.printStackTrace(System.out);
      }
    if (arg.equals("debug")) System.out.println(output);
      ObjectMapper mapper = new ObjectMapper();
      return (JsonNode)mapper.readValue(output, JsonNode.class);
  }

这两个函数被称为,每秒几百次。我可以在HTOP程序中看到RES场每分钟都在增长。它完全没有意图将任何内存/对象带入其中的每个交互(true),id就像扔掉它一样,但System.gc()似乎没有帮助。

这是导致我的问题的一部分,还是其他什么东西?

2 个答案:

答案 0 :(得分:0)

Java将使用它可用的任何内存来进行垃圾收集:

What are the Xms and Xmx parameters when starting JVMs?

正如你所描述的那样,你有一个循环无休止地做某事而且经常这样做,这意味着你一直在分配对象,例如ObjectMapper和许多其他对象。

没有必要调用System.gc(),因为垃圾收集器通常现在总是在后台运行,并且有时会收集,以减少收集过程中程序减速的可能性。

答案 1 :(得分:0)

简短回答。你的功能看起来很好。

很长的答案你必须学习使用内存分析工具lice MAT

您可以配置JVM以便在因OOM崩溃时保存内存转储。 当你得到一个加载到MAT并分析对象的数量和大小。它还可以向您显示导致泄漏对象的参考链。

PS:System.gc()永远无法解决此类问题。不建议打电话。