我正在Eclipse上使用Java程序。程序从用户那里获取"txt"文件名,并打印出该"txt"文件中的行数("文件中有"x"行"(。如果"txt"文件不存在,则应打印出"该文件不存在">
我试图让程序继续循环,无论最后一个条目是否导致错误,都要求文件名,直到用户键入"完成"。
这是我正在编辑的代码。总共有2个班级。这是第一个(进程文件.java(:
// ProcessFile.java
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Scanner;
/**
*
* This class will ask the user for a text file
* name, open that file, and print all the lines
* of the file and how many lines there are.
*
*
*/
public class ProcessFile {
/**
* This method prompts the user to enter a
* file name and returns it.
*
* @return A String containing a file name.
*/
public static String getFileName()
{
Scanner in = new Scanner( System.in );
String fileName;
FileReader reader;
do
{
System.out.println( "Please enter a file name to open: " );
fileName = in.nextLine();
try
{
reader = new FileReader( fileName );
}
catch( FileNotFoundException e )
{
System.out.println( "That file does not exist." );
reader = null;
}
}
while ( reader == null );
in.close();
try
{
reader.close();
}
catch ( IOException e )
{
System.out.println( e );
}
return fileName;
}
/**
* This method takes an ArrayList of Strings and prints each
* element of the ArrayList, one per line, as well as the
* number of items in the ArrayList.
*
* @param lines
*/
public static void printInformation( ArrayList<String> lines )
{
for ( String line : lines )
System.out.println( line );
System.out.println( "There are " + lines.size() + " lines in the file." );
}
public static void main( String[] args )
{
String fileName;
FileManager fileInfo;
ArrayList<String> lines = new ArrayList<String>();
fileName = getFileName( );
fileInfo = new FileManager( fileName );
try
{
lines = fileInfo.readLines();
}
catch( FileNotFoundException e )
{
System.out.println( e );
}
printInformation( lines );
}
}
这是第二个类(文件管理器.java(:
// FileManager.java
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.util.ArrayList;
import java.util.Scanner;
/**
* This class will manage the interaction with the
* file for the ProcessFile class.
*
*
*/
public class FileManager
{
private String fileName;
public FileManager( String file )
{
fileName = file;
}
/**
* This function will read the file stored in
* fileName and return an ArrayList made up of
* the lines of the file.
*
* @return An ArrayList containing the file's lines.
*/
public ArrayList<String> readLines( ) throws FileNotFoundException
{
ArrayList<String> lines = new ArrayList<String>();
FileReader fileIn = new FileReader( fileName );
Scanner in = new Scanner( fileIn );
while ( in.hasNextLine() )
{
String line = in.nextLine();
lines.add( line );
}
in.close();
return lines;
}
}
对于"如果用户键入'完成',结束程序"部分,我查找了一些东西并将其包含在下面的代码中。不确定它是否正确,但是当我输入该部分时我没有收到任何错误。这是我所做的更改(我按更改的部分添加评论(:
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Scanner;
/**
*
* This class will ask the user for a text file
* name, open that file, and print all the lines
* of the file and how many lines there are.
*
*
*/
public class ProcessFile {
/**
* This method prompts the user to enter a
* file name and returns it.
*
* @return A String containing a file name.
*/
public static String getFileName() // Error: This method must return a result of type String
{
Scanner in = new Scanner( System.in );
String fileName;
FileReader reader;
int x = 1;
if (System.in.equals("Done") || System.in.equals("done")) // This is the part I wasn't sure of (the one I said I looked up)
{
System.exit(0);
}
else
{
while (x == 1)
{
System.out.println( "Please enter a file name to open: " );
fileName = in.nextLine();
try
{
reader = new FileReader( fileName );
}
catch( FileNotFoundException e )
{
System.out.println( "That file does not exist." );
}
in.close();
try
{
reader.close(); //Error: The local variable reader may not have been initialized
}
catch ( IOException e )
{
System.out.println( e );
}
return fileName;
}
}
}
/**
* This method takes an ArrayList of Strings and prints each
* element of the ArrayList, one per line, as well as the
* number of items in the ArrayList.
*
* @param lines
*/
public static void printInformation( ArrayList<String> lines )
{
for ( String line : lines )
System.out.println( line );
System.out.println( "There are " + lines.size() + " lines in the file." );
}
public static void main( String[] args )
{
String fileName;
FileManager fileInfo;
ArrayList<String> lines = new ArrayList<String>();
fileName = getFileName( );
fileInfo = new FileManager( fileName );
try
{
lines = fileInfo.readLines();
}
catch( FileNotFoundException e )
{
System.out.println( e );
}
printInformation( lines );
getFileName(); // <--- Return to the top and get the user input again.
}
}
我想我快要得到这个了。任何一点帮助将不胜感激。多谢。
**已编辑的代码 (@μTheory(
public static String getFileName()
{
Scanner in = new Scanner( System.in );
String fileName;
FileReader reader;
do
{
System.out.println( "Please enter a file name to open: " );
fileName = in.nextLine();
if ( in.equals("Done") || in.equals("done") )
{
in.close();
System.exit(0);
}
else
{
try
{
reader = new FileReader( fileName ); //Error: The local variable reader may not have been initialized.
}
catch( FileNotFoundException e )
{
System.out.println( "That file does not exist." );
}
}
in.close();
try
{
reader.close();
}
catch ( IOException e )
{
System.out.println( e );
}
return fileName;
}
while ( reader == null );
}
所以首先,System.in
指的是一个InputStream
,所以你对System.in.equals("Done");
的调用试图比较一个String
和一个InputStream
,并且显然会返回false。相反,请在if
语句之前调用fileName = in.nextLine();
,然后检查是否filename.equals("Done")
。并将您的 if 语句放入您的 while
循环中。
现在你已经创建了一个无限循环:while ( x == 1)
永远不会停止,因为你实例化了x=1
并且你永远不会改变循环中的值。
我建议你像以前编程的那样将循环更改为while( reader == null)
。并从您的while
陈述中取出并将它们放在行之后
in.close();
try
{
reader.close();//No more error
}
catch ( IOException e )
{
System.out.println( e );
}
return fileName;
那为什么呢? 因为当您reader
null
时,您无法关闭允许您调用循环的每次迭代fileName = in.nextLine();
Scanner
。当您的reader
不为空时,您想结束循环,因此您不能调用reader.close();
因为根据定义,您的reader
对象将为 null 并抛出NullPointerException
。
在调用System.exit(0);
关闭所有打开的流(例如Scanner
(之前考虑。
编辑:
public static String getFileName()
{
Scanner in = new Scanner( System.in );
String fileName;
FileReader reader;
do
{
System.out.println( "Please enter a file name to open: " );
fileName = in.nextLine();
if ( fileName.equals("Done") || fileName.equals("done") )
{
in.close();
System.exit(0);
}
else
{
try
{
reader = new FileReader( fileName ); //Error: The local variable reader may not have been initialized.
}
catch( FileNotFoundException e )
{
System.out.println( "That file does not exist." );
}
}
}
while ( reader == null );
in.close();
try
{
reader.close();
}
catch ( IOException e )
{
System.out.println( e );
}
return fileName;
}
所以这是正确的代码。你仍然不明白,你in.equals("Done")
试图比较你的in
obejct,这是Scanner
和String
的实例,正如我上面所说,这将不知不觉地返回错误。所以这就是为什么我用fileNmae
表示用户输入的行替换in
。
然后我提取了块:
in.close();
try
{
reader.close();
}
catch ( IOException e )
{
System.out.println( e );
}
return fileName;
正如我上面所说,在您的while
循环之外。如果仍在使用流或尚未实例化流,则无法关闭流。
您应该将不确定的部分替换为:
if(in.nextLine().equalsIgnoreCase("done")){
System.exit(1);
}
可以使用 equalsIgnoreCase 方法进行不区分大小写的比较。要从控制台读取,只需使用 Scanner.nextLine(( 或您认为适合 Scanner 类的任何其他方法。
如果您不想接受以下输入:
"DONE", "DoNe", etc
然后只需将输入字符串与
"Done" and "done"
如故。
从扫描仪获取用户输入并将其与"完成"进行比较,而不是System.in
本身。 System.in
只是一个流,而不是实际的输入,您需要从该流中读取才能进行比较。
Scanner s = new Scanner(System.in)
String inp = s.nextLine()
if(inp.equals("Done"))
{
//Code
}
而且,正如@DeiAndrei在他的回答中指出的那样,您可以使用equalsIgnoreCase
来比较它而不区分大小写。忘记了这一点,为了完整起见,添加了它。