2013-06-27 3 views
1

Я искал некоторые ответы, и я не могу найти лучшего.Лучший способ прочитать внутренний файл на Android?

Вот что я до сих пор для чтения внутренних файлов на Android:

 fis = openFileInput("MY_FILE"); 
     StringBuilder fileContent = new StringBuilder(""); 
     byte[] buffer = new byte[fis.available()]; 
     while (fis.read(buffer) != -1) { 
      fileContent.append(new String(buffer)); 
     } 
     MYVARIABLE = fileContent.toString(); 
     fis.close(); 

Его используют, чтобы оставить много пробелов, но я просто использовал метод Имеющеся только вернуть то, что мне нужно.

Есть ли более быстрый или более короткий способ написать это? Кажется, я не нашел хороших в руководстве API.

+0

Незначительные моменты: (1) с этим перемещением вам действительно не нужен прокси-объект (StringBuilder), (2) код не обрабатывает кодировку, поэтому, если кодировка содержимого файла UTF-8, то это возможно для получения поврежденных данных. –

+0

@Arhimed - вам не нужно использовать StringBuilder, но имейте в виду, что объединение строк в Java быстро становится дорогим, поскольку Java String является неизменным объектом. Это означает, что каждый раз, когда вы конкатенируете бит в конце, вы фактически (за кадром) должны копировать всю существующую часть в новый более длинный объект String, который может содержать как существующие, так и добавленные части. Поэтому делать это в цикле обычно избегают. –

+1

@Chris Stratton: в этой конкретной реализации нет конкатенации - все данные считываются в одном фрагменте. –

ответ

1

1). API для available() говорит, что не следует использовать для целей вам нужно:

Обратите внимание, что этот метод обеспечивает такую ​​слабую гарантию того, что это не очень полезно на практике.

Значение этого не может дать вам размер файла.

2). Когда вы читаете smth в ОЗУ, тогда возьмите под учетную запись, файл может быть длинным, поэтому старайтесь избегать дополнительных расходов. Для этого относительно небольшой (1 ~ 8 КБ) буфер используется для чтения из источника, а затем добавляется к результату. С другой стороны, использование слишком маленьких буферов (скажем, нескольких байтов) значительно замедляет чтение.

3). Чтение байтов отличается от чтения символов, потому что один символ может быть представлен более чем одним байтом (зависит от кодировки). Чтобы прочитать символы, используются классы spesific, которые знают о кодировании и умеют правильно преобразовывать байты в символы. Например, InputStreamReader является одним из таких классов.

4). Кодировка, используемая для чтения, должна быть кодировкой, которая использовалась для сохранения данных.

Принимая во внимание все сказанное выше, я использовал бы, как это л:

public static String getStringFromStream(InputStream in, String encoding) 
     throws IOException { 
    InputStreamReader reader; 
    if (encoding == null) { 
     // This constructor sets the character converter to the encoding 
     // specified in the "file.encoding" property and falls back 
     // to ISO 8859_1 (ISO-Latin-1) if the property doesn't exist. 
     reader = new InputStreamReader(in); 
    } else { 
     reader = new InputStreamReader(in, encoding); 
    } 

    StringBuilder sb = new StringBuilder(); 

    final char[] buf = new char[1024]; 
    int len; 
    while ((len = reader.read(buf)) > 0) { 
     sb.append(buf, 0, len); 
    } 

    return sb.toString(); 
} 

5). Обязательно всегда закрывайте InputStream, когда будете работать с ним.

Уверен, существует несколько способов чтения текста из файла на Java/Android. Это связано главным образом с тем, что Java API содержит несколько поколений API ввода-вывода. Например, классы из java.nio были созданы, чтобы быть более эффективными, однако обычно нет сильной причины их использования (не попадайте в преждевременную оптимизацию sin).

+0

Спасибо за это задумчивое и подробное объяснение :) – CynthiaDDurazo