4

I am trying to execute this code and I am also providing the valid argument but still I am getting error at line no. 34 and 35 that local variable fin and fout might not have been initialized. How to solve thisenter code here

 package maxbj.myTest.p1;
import java.io.*;
public class CopyFile {
public static void main(String[] args)throws IOException {

    int i;
    FileInputStream fin;
    FileOutputStream fout;

    try{
        //trying to open input file
        try{
            fin=new FileInputStream(args[0]);
        }catch(FileNotFoundException e){
            System.out.println("Input file not found");
            return;
        }

        //trying to open output file
        try{
            fout=new FileOutputStream(args[1]);
            return;
        }catch(FileNotFoundException e){
            System.out.println("Output file cannot be opened or created");
            return;
        }       
    }catch(ArrayIndexOutOfBoundsException e){
        System.out.println("Array index out of bound exception");
    }

    //code to copy file
    try{
        do{
            i=fin.read();
            if(i!=-1) fout.write(i);
        }while(i!=-1);
    }catch(IOException e){
        System.out.println("File Error");
    }
    fin.close();
    fout.close();
}
}

PS- This code is from the book "JAVA COMPLETE REFRENCE"

Bijay Singh
  • 819
  • 4
  • 14
  • 33
  • @SotiriosDelimanolis That would not be a fix, only a work-around. A fix would make sure that there are no paths where `fin` remains uninitialized - a relatively simple thing to do. – Sergey Kalinichenko Apr 24 '13 at 15:57

2 Answers2

3

The compiler is right (and the book is wrong, they should have tried compiling their code before publishing): there is a path through the code when fin remains uninitialized by the time the code reaches the fin.read() line.

Specifically, if ArrayIndexOutOfBoundsException gets thrown in the first outer try/catch block, the fin variable will not be assigned. Adding return to the outer catch block should fix this problem:

try {
    ...
} catch(ArrayIndexOutOfBoundsException e){
    System.out.println("Array index out of bound exception");
    return; // <<== Here
}

With the return statement in place, control will never reach the fin.read() unless fin has been initialized, fixing the compile-time error.

Sergey Kalinichenko
  • 714,442
  • 84
  • 1,110
  • 1,523
  • @SotiriosDelimanolis You are probably right, good chances are that the OP has missed the `return` statement. – Sergey Kalinichenko Apr 24 '13 at 15:58
  • @Sotirios Delimanolis and @ dasblinkenlight Am really sorry about my mistake. I made a mistake I wrote "return" after initializing fout inside try block. But I realised my mistake only after posting here and am really sorry for my mistake. – Bijay Singh Apr 24 '13 at 15:58
  • @BijaySingh That's OK, everybody makes mistakes! If this was indeed the problem, consider accepting the answer by clicking the check mark. This would let others know that you are no longer looking for an improved answer, and earn you a badge on stack overflow. – Sergey Kalinichenko Apr 24 '13 at 16:00
  • 1
    @BijaySingh Make sure you understand why the error happened, though. – Sotirios Delimanolis Apr 24 '13 at 16:01
1

A simple way around this is to perform anything which requires fin and fout within the try block. This way you will never be trying to use the streams when they have failed on opening.

try
{
    fout = new FileOutputStream(...);
    fin = new FileInputStream(...);

    // Code goes here

    fout.close();
    fin.close();
}
catch(FileNotFoundException e)
{
    // Error code - e should contain the file name/path
}

Also, it is always good practice to initialise variables when you declare them:

FileOutputStream fout = null;
FileInputStream fin = null;

However, this way (just initialising to null) you programming logic will not cause compiler errors, but if not handled correctly you may get NullPointerExceptions if you try block throws.

Ed Mackenzie
  • 679
  • 6
  • 16