2009-12-17 17 views
7

तो मेरे पास कुछ कोड है जो फ़ाइल से बाइट्स की एक निश्चित मात्रा को पढ़ता है और परिणामस्वरूप बाइट सरणी देता है (यह मूल रूप से नेटवर्क को भेजने के लिए फाइलों को खंडित करने के लिए उपयोग किया जाता है (अंत में) बेस 64-एन्कोडेड एएससीआई टेक्स्ट)।जावा: बाइट सरणी को "ट्रिम" कैसे करें?

यह ठीक काम करता है, सिवाय इसके कि जब फ़ाइल का अंतिम हिस्सा उत्पन्न होता है, तो यह पूर्णांक नहीं होता है। इसलिए, परिणामस्वरूप बाइट सरणी पूर्ण नहीं है। हालांकि, यह एक स्थिर आकार है, जिसका अर्थ है कि फ़ाइल को फिर से इकट्ठा किया गया है, अंत में अतिरिक्त डेटा (0 शायद हो सकता है) का एक पूरा समूह है।

मैं इसे कैसे बना सकता हूं ताकि फ़ाइल के आखिरी हिस्से के लिए बाइट [] वास्तव में केवल उस डेटा को शामिल कर सके जिसमें इसकी आवश्यकता हो? कोड इस तरह दिखता है:

private byte[] readData(File f, int startByte, int chunkSize) throws Exception { 
    RandomAccessFile raf = new RandomAccessFile(f, "r"); 
    raf.seek(startByte); 
    byte[] data = new byte[chunkSize]; 
    raf.read(data);   
    raf.close(); 
    return data; 
} 

तो अगर chunkSize फ़ाइल में शेष बाइट्स से बड़ा है, एक पूर्ण आकार बाइट [] लौटे हो जाता है, लेकिन इसके केवल डेटा के साथ आधा भरा।

उत्तर

3

बाइट पढ़ने की संख्या निर्धारित करने के लिए आपको RandomAccessFile.read() का वापसी मूल्य देखना होगा। यदि यह chunkSize से अलग है, तो आपको सरणी को एक छोटे से कॉपी करना होगा और उसे वापस करना होगा।

private byte[] readData(File f, int startByte, int chunkSize) throws Exception { 
    RandomAccessFile raf = new RandomAccessFile(f, "r"); 
    raf.seek(startByte); 
    byte[] data = new byte[chunkSize]; 
    int bytesRead = raf.read(data); 
    if (bytesRead != chunkSize) { 
     byte[] smallerData = new byte[bytesRead]; 
     System.arraycopy(data, 0, smallerData, 0, bytesRead); 
     data = smallerData; 
    } 
    raf.close(); 
    return data; 
} 
+1

बजाय System.arraycopy के ऊपर पद से Arrays.copyOf का उपयोग करते हुए की लंबाई के बराबर (जो एक अपवाद फेंक दिया), यह पूरी तरह से काम किया! धन्यवाद! –

+0

ठीक किया गया, मेरे तुलना में एक टाइपो था, '== 'नहीं' = 'का उपयोग किया जाना चाहिए था। – notnoop

+0

@ एरिन ड्रमॉन्ड: 'System.arraycopy()' द्वारा निकाला गया अपवाद क्या था? – Asaph

2

RandomAccessFile.read() रिटर्न बाइट की संख्या पढ़ा, तो आप सरणी कॉपी कर सकते हैं अगर जरूरत:

private byte[] readData(File f, int startByte, int chunkSize) throws Exception { 
    RandomAccessFile raf = new RandomAccessFile(f, "r"); 
    raf.seek(startByte); 
    byte[] data = new byte[chunkSize]; 
    int read = raf.read(data); 
    raf.close(); 
    if (read == data.length) return data; 
    else 
     return Arrays.copyOf(data, read); 
} 

आप जावा पूर्व 6 का उपयोग कर रहे हैं, तो आप Arrays.copyOf लागू करने की आवश्यकता अपने आप को:

byte[] r = new byte[read]; 
System.arraycopy(data, 0, r, 0, read); 
return r; 
0

आप शेष बाइट्स की गणना करने के लिए फ़ाइल के आकार का भी उपयोग कर सकते हैं।

private byte[] readData(File f, int startByte, int chunkSize) throws Exception { 
    RandomAccessFile raf = new RandomAccessFile(f, "r"); 
    raf.seek(startByte); 
    int size = (int) Math.min(chunkSize, raf.length()-startByte); 
    byte[] data = new byte[size]; 
    raf.read(data); 
    // TODO check the value returned by read (throw Exception or loop) 
    raf.close(); 
    return data; 
} 

इस तरह आप अतिरिक्त ऐरे नहीं बनाते हैं और प्रतिलिपि की आवश्यकता नहीं है। शायद एक बड़ा प्रभाव नहीं है।
एक महत्वपूर्ण बिंदु आईएमओ: read द्वारा लौटाए गए मान की जांच करें, मुझे लगता है कि यह शेष बाइट्स से कम हो सकता है। जावाडोक कहता है:

पढ़े गए बाइट की संख्या, अधिक से अधिक, है ख

संबंधित मुद्दे