java - 加载 Podcast 音频导致 Java 中出现 OutOfMemoryError

标签 java audio memory-leaks playframework

我有一个 Java 方法,可以加载播客的分块音频数据。据我所知,2 或 3 个用户可以访问播客中的音频(通常约为 40MB),然后我的应用程序内存不足并崩溃(java.lang.OutOfMemoryError:null)。我正在使用 Java 和 Play 框架。

@With(MP3Headers.class)
public static Result getAudioByChunk(Integer audioId) {
    try {
        final Audio requestedAudio = Audio.findById.byId(audioId);
        int songLength = Files.readAllBytes(Paths.get(requestedAudio.filePath)).length;

        final int begin, end;
        final boolean isRangeReq;
        response().setHeader("Accept-Ranges", "bytes");
        if (request().hasHeader("RANGE")) {
            isRangeReq = true;
            String[] range = request().getHeader("RANGE").split("=")[1].split("-");
            begin = Integer.parseInt(range[0]);
            if (range.length > 1) {
                end = Integer.parseInt(range[1]);
            } else {
                end = songLength - 1;
            }
            response().setHeader("Content-Range", String.format("bytes %d-%d/%d", begin, end, songLength));
        } else {
            isRangeReq = false;
            begin = 0;
            end = songLength - 1;
        }

        Chunks<byte[]> chunks = new ByteChunks() {
            public void onReady(Chunks.Out<byte[]> out) {
                try {
                    if (isRangeReq) {
                        out.write(Arrays.copyOfRange(Files.readAllBytes(Paths.get(requestedAudio.filePath)), begin, end));
                    } else {
                        out.write(Files.readAllBytes(Paths.get(requestedAudio.filePath)));
                    }
                } catch (IOException ioe) {
                } finally {
                    out.close();
                }
            }
        };
        response().setHeader("Content-Length", (end - begin + 1) + "");
        if (isRangeReq) {
            return status(206, chunks);
        } else {
            return status(200, chunks);
        }
    } catch (Exception e) {
        return ok();
    }
}

我已经尝试增加 JVM 内存(我在服务器上只有 1 GB 的总内存可使用)。出于绝望,我尝试使“ block ”无效并在 return 语句之后的 finally block 中调用垃圾收集器。

我认为我缺少一个在将 block 写入结果后释放内存的命令,我到底缺少什么?

如果需要更多详细信息,请告诉我。

最佳答案

您可能需要使用流模式,而不是将整个音频加载到内存中。

看看这个答案以寻求帮助:

https://stackoverflow.com/a/32865159/5430900

关于java - 加载 Podcast 音频导致 Java 中出现 OutOfMemoryError,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33351912/

相关文章:

java - JProfiler 报告 Object.wait() 中 Long 的分配情况

c++ - libmysqlclient.18.dylib 内存泄漏

java - 流中的条件过滤器

java - Spring surf 和 webscripts 项目消歧

java - Jackson ObjectMapper 无法识别 @JsonProperty 注解

java - SpEL : get current bean name during bean instantiation

c# - 如何让计算机在 C# 中发出蜂鸣声?

c# - C#中的二进制到.Beep方法

python - Python 中的 Google Talk/XMPP 音频支持

ios - Unowned Reference 导致 leak , weak 不会