从文件中读取双精度浮点数

5

我正在尝试从文件中读取一些数字(双精度)并使用以下代码将它们存储到ArrayList和数组中(是的,我需要两者):

try {
    Scanner scan = new Scanner(file).useDelimiter("\\s*\\n");

    while(scan.hasNextDouble())
    {
        tmp.add(scan.nextDouble());
    }

    Double[][] tmp2 = new Double[tmp.size()/2][2];
    int tmp3 = 0;
    for(int i = 0; i < tmp.size()/2; i++)
    {
        for(int j = 0; j < 2; j++)
        {
            tmp2[i][j] = tmp.get(tmp3);
            tmp3++;
        }
    }

} catch (FileNotFoundException e1) {
    e1.printStackTrace();
}

我将要读取的文件是:

0.0 0.0
0.023 0.023
0.05 0.05
0.2 0.2
0.5 0.5
0.8 0.8
0.950 0.950
0.977 0.977
1.0 1.0

但是我的代码不起作用,hasNextDouble()函数没有找到任何东西,我做错了什么?
编辑:好的,所以我对源代码进行了一些编辑(从Object[][]更改为Double[][]),并在将值插入ArrayList后将其插入数组中,但它仍然不起作用——'while'循环没有执行一次。

是的,我尝试过使用"."和",",但都没有起作用。 - Mateusz Dymczyk
我确信你在处理 tmp 变量时出了问题。在你的代码开始之前,它的类型是什么,里面有什么? - Carl Smotricz
正如其名称所示,它是一个临时变量,仅在那里使用。唯一更好的名称应该是:“一个临时数组,用于存储从文件中获取的数据,然后将其放入表格中”。 - Mateusz Dymczyk
你确定Scanner正在读取正确的文件吗? - Anthony Forloney
@Zenzen:这是个编程恐怖故事,伙计。 :-) - CesarGon
显示剩余2条评论
4个回答

4

我尝试将代码缩减以便仅测试Scanner。以下代码可与您的数据文件一起使用:

public static void main(String[] args) {
    Scanner scan;
    File file = new File("resources\\scannertester\\data.txt");
    try {
        scan = new Scanner(file);

        while(scan.hasNextDouble())
        {
            System.out.println( scan.nextDouble() );
        }

    } catch (FileNotFoundException e1) {
            e1.printStackTrace();
    }

}

我得到了以下(预期的)输出:
0.0
0.0
0.023
0.023
0.05
0.05
0.2
0.2
0.5
0.5
0.8
0.8
0.95
0.95
0.977
0.977
1.0
1.0

尝试以下方法,确保你引用的是正确的文件。


1
添加了分隔符,但没有任何变化。我添加了两个System.out.println来查看问题所在,位于“while”之前的那个是正常的,但是while循环中的那个不打印。 - Mateusz Dymczyk
@Bill:我很难相信这个。我刚刚运行了代码,没有做任何更改,Scanner 没有任何问题读取输入。 - Carl Smotricz
我把它包装成了一个main()函数,并在前面定义了tmp和file。 - Carl Smotricz
好的,那就是我正在努力解决的部分。我刚刚看到了你对这个问题的评论。 - Bill the Lizard
我不知道为什么(稍后会检查),但它有效,谢谢。 - Mateusz Dymczyk

2

我遇到了同样的问题(扫描仪不工作),解决方案似乎非常简单。你只需要为它设置一个区域设置。

  // use US locale to be able to identify doubles in the string
  scanner.useLocale(Locale.US);

这里摘自:http://www.tutorialspoint.com/java/util/scanner_nextdouble.htm

Scanner类中的nextDouble()方法将下一个输入标记解释为双精度值并返回。该方法通过调用next()方法获取输入,然后将其转换为双精度值。如果输入无法转换为双精度值,则抛出InputMismatchException异常,并且扫描器不会移动。

以下是使用nextDouble()方法的示例:

import java.util.Scanner;

public class MyClass {
  public static void main(String[] args) {
    Scanner scanner = new Scanner(System.in);
System.out.println("Enter a double value: "); double num = scanner.nextDouble();
System.out.println("The double value entered is " + num); } }

1
以下是我对你的代码进行修改后运行的版本。它立即因为数组索引异常而崩溃了。
所以:你能给我们提供更多的框架吗?我的代码和你的有什么不同?
import java.io.File;
import java.io.FileNotFoundException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Scanner;

public class Zenzen {

   private static ArrayList<Double> tmp = new ArrayList<Double>();

   private static File file = new File("Zenzen.dat");

   public static void main(String[] args) {

      Scanner scan;
      try {
         scan = new Scanner(file);
         Object[][] tmp2 = new Object[tmp.size() / 2][2];
         int tmp3 = 0;

         while (scan.hasNextDouble()) {
            tmp.add(scan.nextDouble());
            System.out.println(Arrays.deepToString(tmp.toArray())); // debug print
            for (int i = 0; i < tmp.size() / 2; i++) {
               for (int j = 0; j < 2; j++) {
                  tmp2[i][j] = tmp.get(tmp3);
                  tmp3++;
               }
            }
         }

      } catch (FileNotFoundException fnfe) {
         fnfe.printStackTrace();
      }
   }
}

[0.0]
[0.0, 0.0]
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: 0
    at Zenzen.main(Zenzen.java:26)

哦,是的,我之前声明了tmp2数组太早了,我已经改过了。 - Mateusz Dymczyk

0

先尝试设置分隔符:

scan.useDelimiter("\\s+");

JavaDoc

{{链接1:JavaDoc}}


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接