当前位置: 首页 > 面试题库 >

Java Scanner(File)行为异常,但是Scanner(FIleInputStream)始终与同一个文件一起使用

尹昂雄
2023-03-14
问题内容

我的扫描仪行为异常。使用Scanner(FileInputStream)构造函数时,它将与我正在使用的一组特定文件一起使用,但不适用于Scanner(File)构造函数

Scanner s = new Scanner(new File("file"));
while(s.hasNextLine()) {
    System.out.println(s.nextLine());
}

结果: 无输出

情况2: Scanner(FileInputStream)

Scanner s = new Scanner(new FileInputStream(new File("file")));
while(s.hasNextLine()) {
    System.out.println(s.nextLine());
}

结果: 文件内容输出到控制台。

输入文件是一个包含单个类的Java文件。

我以编程方式(在Java中)仔细检查了以下内容:

  • 该文件存在,
  • 可读性强
  • 并且具有非零的文件大小。

通常Scanner(File)在这种情况下对我有用,我不确定为什么现在不行。


问题答案:

hasNextLine()调用findWithinHorizo​​n(),后者依次调用findPatternInBuffer(),在匹配项中搜索定义为.*(\r\n|[\n\r\u2028\u2029\u0085])|.+$

奇怪的是,通过两种方式(使用FileInputStream或通过File)构造扫描器,如果文件包含(独立于文件大小)文件(例如0x0A行终止符),则findPatternInBuffer返回正匹配;但是如果文件包含的字符超出了ASCII码(即>
= 7f),则使用FileInputStream返回true,而使用File返回false。

非常简单的测试用例:

创建一个仅包含字符“ a”的文件

# hexedit file     
00000000   61 0A                                                a.

# java Test.java
using File: true
using FileInputStream: true

现在使用hexedit将文件编辑为:

# hexedit file
00000000   61 0A 80                                             a..

# java Test.java
using File: false
using FileInputStream: true

在测试Java代码中,除了问题中已经存在的内容外,没有什么其他:

import java.io.*;
import java.lang.*;
import java.util.*;
public class Test {
    public static void main(String[] args) {
        try {
                File file1 = new File("file");
                Scanner s1 = new Scanner(file1);
                System.out.println("using File: "+s1.hasNextLine());
                File file2 = new File("file");
                Scanner s2 = new Scanner(new FileInputStream(file2));
                System.out.println("using FileInputStream: "+s2.hasNextLine());
        } catch (IOException e) {
                e.printStackTrace();
        }
    }
}

所以,事实证明这是一个字符集问题。实际上,将测试更改为:

 Scanner s1 = new Scanner(file1, "latin1");

我们得到:

# java Test 
using File: true
using FileInputStream: true


 类似资料:
  • 我创建了一个内容为“Hello”的文本文件,我试图从文件中读取这些字符,并再次将其写回相同的文件。 我尝试使用调试器来找出问题,调试器显示在while循环的第一次迭代时被分配。然后,我在检查文件内容时一步一步地执行代码,发现在执行语句之后,“hello”关键字就从文件中删除了。 我最初认为这是由于和指向同一个文件,所以为了执行安全,JVM对文件进行了某种程度的“锁定”? 所以我试着交换这两行: 结

  • 我有一个烧瓶服务器运行在http://127.0.0.1:5000和一个vuejs前端运行http://localhost:8080我已经做了api,并用postman测试了它,一切都如预期的那样工作:( > 将请求发布到/登录- (将请求发送至/登录)- 烧瓶API代码: 登录。vue: 指数vue 当我使用邮递员登录时,我得到的响应为;当我使用邮递员获取url/索引时,我得到响应。数据但当我使

  • 我在使用hibernate和Oracle db执行限制条件时遇到问题。 简化的标准是: 这给了我NullPointerExceltion。我明白,我需要把setEscape处理(假)为了忽略括号{}在{宠物},但我不知道如何做到这一点,因为我正在使用标准。 如果有人能帮助我,我会很高兴的。 这是生成的异常: java.lang.oracle.jdbc.driver.T4C8Oall.getNumR

  • 我正在尝试用文件键上传一个HEIC文件。我应该指定哪种文件类型? 现在我有这个: 我在文件里找不到任何关于这个的东西,我的实验也不起作用。 下面是我试图上传的测试文件: https://github.com/tigranbs/test-heic-images/raw/master/image1.heic

  • 目前,我正在java中建立一个Firebase云火力恢复,使用IntelliJ作为SDK。在Firebase留档中,据说需要服务帐户密钥,这是一个json文件。我使用FileInputStream方法获得这个json文件,当我得到执行程序的文件时,我没有任何问题,但是当我将其导出为JAR库时,使用该JAR的项目没有找到服务帐户密钥,然后它无法与我的Firebase连接。 现在,我可以连接到Fire

  • 我通常在设置配置文件后使用AWS CLI命令,使用环境变量,使用文件。这很有效。 我目前正在尝试通过环境变量设置访问权限。为此,我在文件-我从凭证文件中复制了和条目,并将它们放在我的文件中,名称为和。 环境变量正在被正确设置,然而,当我试图访问AWS资源时(在这种情况下,我试图在桶上运行一个S3命令,所以区域并不重要),我得到了消息 这对我来说很奇怪,因为钥匙是完全一样的。为了确认这一点,我切换到