日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

关于JAVA输入输出流造成的Runtime线程阻塞问题【新人笔记】

發布時間:2023/12/31 编程问答 29 豆豆
生活随笔 收集整理的這篇文章主要介紹了 关于JAVA输入输出流造成的Runtime线程阻塞问题【新人笔记】 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

萌新最近搬磚遇到一個問題,上面讓我做一個dump文件的自動解析系統,至于解析的工具,準備用的是google的breakpad,項目部署環境是linux+jdk1.8。其他的無關緊要也就不談了。

一開始寫了一個demo放到測試機上面跑,最初代碼如下(只保留轉換相關的代碼,所以不可以運行):

import java.io.InputStreamReader;public class DumpAnalyseUtil {public static boolean analyseDumpFile(String stackPath, String dumpPath, String symPath, String logPath){boolean result = false;Process process = null;File stackFile = new File(stackPath);File dumpFile = new File(dumpPath);File symbolFile = new File(symPath);File logFile = new File(logPath);try{if (stackFile.exists() && dumpFile.exists() && symbolFile.exists()){String command = stackPath + " " + dumpPath + " " + symPath + " > " + logPath;System.out.println(command);Runtime.getRuntime().exec(command).waitFor();result = true;}}catch (Exception e){System.out.println("Dump File Analysis Error: " + e.getMessage());if (process != null){try{process.getErrorStream().close();process.getInputStream().close();process.getOutputStream().close();}catch (IOException ie){ie.printStackTrace();}}}return result;}public static void main(String[] args) {String stackPath = "/data/breakpad/src/processor/minidump_stackwalk";String dumpPath = "/data/dump/lalala.dmp";String symPath = "/data/symbols/";String logPath = "/data/symbols/123456.log";boolean result = analyseDumpFile(stackPath, dumpPath, symPath, logPath);System.out.println(result);} }

在測試環境中運行這個demo的時候,程序跑到waitFor()方法那里就卡住不動了。。。

后來發現是自己的java基礎還是有些薄弱,java在執行runtime命令時,輸入流和錯誤流都會不斷地進入JVM的緩沖區(一般來說不會有輸出流,但是如果我們的命令和java程序有信息交互的話,比如需要我們通過程序輸入什么參數的時候,這時候也會產生一些輸出流進入緩沖區,但是這些輸出流應該很快就被讀取了,所以出現阻塞一般都是輸入流和錯誤流引起的)。如果我們不去將緩沖區的這些信息流讀出來的話,他們就會一直待在緩沖區,并最終將其填滿,造成runtime的阻塞。

知道了問題的所在,就好解決了。既然這些數據流不讀取就會淤積的話,讀出來就好了,于是有了改進第一版(只放了改進的那部分代碼):

Process exec = Runtime.getRuntime().exec(command);BufferedReader insertReader = new BufferedReader(new InputStreamReader(exec.getInputStream())); BufferedReader errorReader = new BufferedReader(new InputStreamReader(exec.getErrorStream()));exec.waitFor();

還有一種方式,就是如果這個錯誤輸出流里面的信息對你來說沒有什么價值的話,可以利用ProcessBuilder的redirectErrorStream方法,來把錯誤流和輸入流整合到一起,一并讀出來:

ProcessBuilder processBuilder = new ProcessBuilder(command); processBuilder.redirectErrorStream(true); Process p = processBuilder.start(); InputStream is = p.getInputStream(); BufferedReader bs = new BufferedReader(new InputStreamReader(is));

另外,如果你的輸入流信息非常多,比如拷貝文件的話,則可以單獨起一個線程來讀取輸入流中的信息:

(這一塊是參考了 望星辰大海 的博客中的代碼 點擊打開鏈接)

就不具體放出來了,有興趣可以點擊鏈接過去看一下。

總結

以上是生活随笔為你收集整理的关于JAVA输入输出流造成的Runtime线程阻塞问题【新人笔记】的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。