2013-03-27 2 views
1

Вся идея программы - прочитать файл по строкам и сохранить каждое слово в токере массива []. Я пытаюсь напечатать элементы в маркере [] на консоли, используя для цикла. Но он говорит, что переменный токен не инициализирован.Почему я не могу напечатать что-то в маркерном марке [] в этой java-программе

import java.io.*; 

public class ReadFile{ 
    public static void main(String args[]){ 
     String[] token; 
     int i; 

      try{ 
       // Open and read the file 
       FileInputStream fstream = new FileInputStream("a.txt"); 
       BufferedReader br = new BufferedReader(new InputStreamReader(fstream)); 
       String strLine; 
       //Read file line by line and storing data in the form of tokens 
       while((strLine = br.readLine()) != null){ 
        token = strLine.split(" "); 
       } 
       in.close();//Close the input stream 
      } 
      catch (Exception e){//Catch exception if any 
       System.err.println("Error: " + e.getMessage()); 
      } 

        // Why can't I do this printing part? 
      for(i=0;i<=token.length;i++){ 
       System.out.println(token[i]); 
      }`` 
     }// close main() 
}// close Class 
+2

Предположим, что при открытии файла создается исключение. Вы поймаете его и продолжите ... но «токен» не установлен. Аналогично, если есть пустой файл, он никогда не войдет в тело вашего цикла while. Кстати, учитывая, что вы переписываете «токен» на каждой итерации, вы на самом деле собираетесь распечатать содержимое последней строки файла ... –

+0

Просто обратите внимание, что вам не нужен DataInputStream здесь вы можете передать fstream непосредственно в InputStreamReader. –

+0

Пожалуйста, не используйте DataInputStream для чтения текстового файла. Вам это не нужно, поэтому, пожалуйста, удалите его, так как люди могут скопировать этот код. –

ответ

0

проверить этот код, вы поймете, где проблема.

import java.io.*; 
import java.util.*; 
public class ReadFile{ 
public static void main(String args[]){ 
ArrayList<String[]> tokenlist = new ArrayList<>(); 
int i; 

try{ 
    // Open and read the file 
    FileInputStream fstream = new FileInputStream("health.txt"); 
    BufferedReader br = new BufferedReader(new InputStreamReader(fstream)); 
    String strLine; 
    //Read file line by line and storing data in the form of tokens 
    while((strLine = br.readLine()) != null){ 
     String[] token = strLine.split(" "); 
     tokenlist.add(token); 
    } 
    //in.close();//Close the input stream 
} 
catch (Exception e){//Catch exception if any 
    System.err.println("Error: " + e.getMessage()); 
} 

     // Why can't I do this printing part? 
for(int count=0; count<tokenlist.size();count++){ 
    String[] token = tokenlist.get(count); 
    for(i=0;i<token.length;i++){ 
     System.out.println(token[i]); 
    } 
} 

}// close main() 
} 
+0

Пожалуйста, не используйте DataInputStream для чтения текстового файла. Вам это не нужно, поэтому, пожалуйста, удалите его, так как люди могут скопировать этот код. –

+1

@PeterLawrey исправлено. – Ankit

2

Когда вы находитесь внутри метода, такие как основные, объявление переменных не инициализируются, вы должны предоставить им начальное значение самостоятельно.

например:

String [] Массив = новый String [0];

или даже

String [] Массив = NULL;

+0

Массив нулевой длины ничего не распечатает. Это нормально*. Массив 'null' вызовет' NullPointerException' при попытке выполнить итерацию по нему. Это * не * хорошо. – Makoto

+0

Нет, это значение инициализации, цель состоит в том, чтобы переназначить его позже ... Поскольку этот элемент получает свое значение в попытке, безопасным вариантом является новый String [0]; –

+0

Большое спасибо.! Это работает..!! – CodeDevotion

1

Следующий код:

public class ReadFile{ 
    public static void main(String args[]){ 
    String[] token; 
    int i; 
    try{ 
     // Open and read the file 
     FileInputStream fstream = new FileInputStream("a.txt"); 
     DataInputStream in = new DataInputStream(fstream); 
     BufferedReader br = new BufferedReader(new InputStreamReader(in)); 
     String strLine; 
     //Read file line by line and storing data in the form of tokens 
     while((strLine = br.readLine()) != null){ 
      token = strLine.split(" "); 
     } 
     in.close();//Close the input stream 
    } 
    catch (Exception e){//Catch exception if any 
     System.err.println("Error: " + e.getMessage()); 
    } 

должен быть изменен на этот:

public class ReadFile{ 
    public static void main(String args[]){ 
    String[] token = null;//initialize token with null 
    int i; 
try{ 
     // Open and read the file 
     FileInputStream fstream = new FileInputStream("a.txt"); 
     BufferedReader br = new BufferedReader(new InputStreamReader(fStream));//Don't use DataInputStream as this class is good for reading primitives, length-prefixed strings e.t.c 
     StringBuilder sBuilder = new StringBuilder(); 
     String strLine; 
     //Read file line by line and storing data in the form of tokens 
     while((strLine = br.readLine()) != null){ 
      //token = strLine.split(" "); 
      sBuilder.append(strLine); 
     } 
     token = (sBuilder.toString()).split(" ");//Write this line here. 
     in.close();//Close the input stream 
    } 
    catch (Exception e){//Catch exception if any 
     System.err.println("Error: " + e.getMessage()); 
    } 

изменить также для контура конструкции:

for(i=0;i<=token.length;i++){//This will give ArrayOutOfBoundException 
     System.out.println(token[i]); 
    } 

К

if (token != null) 
for(i=0; i<token.length; i++){// condition should be checked for i < token.length 
     System.out.println(token[i]); 
    } 

ПРИМЕЧАНИЕ: Как рекомендовал @Peter Lawrey DataInputStream, следует использовать, в частности, для чтения примитивов.

+0

Создание еще одной строки, чтобы разбить ее снова, кажется довольно расточительным, возможно, вместо массива List использовать список хранения для хранения разделенных токенов в каждом цикле. –

+0

@ LeonardBrünings: Да, я тоже думал об этом. Но переходя по строке OP в вопросе 'сохраняйте каждое слово в токере массива []' Я решил сохранить метод split для получения слов вместо 'ArrayList' –

+0

a List of String [] then? –

1

Это вопрос объема.

В объем main(). token определяется, но не инициализируется. Если вы хотите использовать token на этом уровне видимости, вы должны его инициализировать.

В рамках попытки ... catch block, token инициализируется. Любопытно, что его значение будет иметь значение только для последней строки, так как split() создает новый String[] каждый раз, и вы переназначаете его на token.