2010-07-24 65 views
4

我正在用JAVA(J2ME準確地)寫一個自定義存檔格式。存檔工作正常,但是我在解壓縮時遇到了一些問題。Java的DataInputStream.readUTF和讀取的字節數

如何通過readUTF方法讀取UTF8字符串時讀取多少字節?我知道使用writeUTF保存的字符串的前兩個字節是字符串長度的短值,但我想要一個更好的解決方案。

或者有什麼方法可以知道直到DataInputStream結束時剩下多少個字節(available方法似乎沒有返回有意義的值)。該流通過FileConnection打開,即FileConnection.openDataInputStream

謝謝你們!

回答

4

我無法直接看到使用CLDC API實現此目的的方法。然而,一個簡單的解決方案是推出自己的「CountingInputStream」,它擴展了InputStream並計算讀取的字節數。你基本上只需要重寫三個讀取方法。

文件大小通過FileConnection可用。

+0

我知道'fileSize()'。我同意'CountingInputStream',但這看起來很醜陋(至少對我來說)。 – 2010-07-24 13:48:41

+0

我明白你的觀點,但我不認爲這很醜陋。這樣的類相當有用,並且絕對可重用,在FileConnections之外的其他情況下也是如此。即使它稍微醜陋,它也被封裝並存放在一個小班中。 – aioobe 2010-07-25 09:04:16

1

available()方法返回記錄返回的內容,這不是您正在嘗試使用它的內容。看到Javadoc。

您可以編寫自己的字節計數FilterInputStream並將其放在數據輸入流和基礎流之間。但是您必須從源中獲取源的總字節數,該信息不可用於任何輸入流。

+0

據我所知,FilterInputStream中的不可用MID上的個人資料。 – aioobe 2010-07-24 13:20:39

+0

真的不重要,你可以輕鬆地自己寫下它。 – EJP 2010-07-24 13:22:13

+0

你也真的需要這些字節數嗎?當你到達流的末尾時,你將得到EOF指示... – EJP 2010-07-24 13:24:54

2

這可能有點晚,但我最近一直在一些地方,我需要知道,有一直讀取的字節數,而不是有多少是留下被讀取,如這個問題問。但是你可以從我得到的解決方案中得到這個數字。我想知道讀取的字節數量,以便我可以監視下載的進度(以防它花了一段時間)。

我最初只是使用DataInputStream#readFully()來下載文件。

buffer = new byte[length]; 
in.readFully(buffer); 

但有時我被留下等待50的任何地方 - 60秒下載完成,這取決於大小。我想實時更新事情的進展情況,所以我改爲使用常規的DataInputStream#read(byte [] b,int off,int len)。所以在最後告訴我是一個有的System.out每當我跨越過一個個百分點:

buffer = new byte[length]; 
int totalRead = 0; 
int percentage = 0; 

while (totalRead < length) 
{ 
    int bytesRead = in.read(buffer, totalRead, (length - totalRead)); 

    if (bytesRead < 0) 
     throw new IOException("Data stream ended prematurely"); 

    totalRead += bytesRead; 
    double progress = ((totalRead*1.0)/length) * 100; 
    if ((int)progress > percentage) 
    { 
     percentage = (int)progress; 
     System.out.println("Downloading: " + percentage + "%"); 
    } 
} 

知道有多少字節要被讀取,一些小的修改可到最後的例子進行說明。有一個跟蹤變量來代替我的百分比,例如:

buffer = new byte[length]; 
int totalRead = 0; 
int bytesLeft= 0; 

while (totalRead < length) 
{ 
    bytesLeft = length - totalRead; 
    int bytesRead = in.read(buffer, totalRead, bytesLeft); 

    if (bytesRead < 0) 
     throw new IOException("Data stream ended prematurely"); 

    totalRead += bytesRead; 
    System.out.println("Bytes left to read: " + bytesLeft); 
} 
0

這是一個相當古老的問題,但我會後我的解決方案,因爲它可能幫助別人:

其實是有一個方便的CountingInputStream在Apache的百科全書IO http://commons.apache.org/proper/commons-io/apidocs/org/apache/commons/io/input/CountingInputStream.html

它從java.io.FilterInputStream中衍生包裝,所以你基本上可以將其套在任何標準輸入流。

在你的情況下,假設DataInputStream類變量表示你一起工作流:

CountingInputStream counter = new CountingInputStream(dataInputStream); 
dataInputStream = new DataInputStream(counter); 
... 
counter.getByteCount() //this returns num of bytes read from dataInputStream