简体   繁体   中英

Read numbers from txt.file and generate 2d array

For example we have file("Test2") which contains:

1 2 3 4 5
1 2 3 4 0
1 2 3 0 0
1 2 0 0 0
1 0 0 0 0
1 2 0 0 0
1 2 3 0 0
1 2 3 4 0
1 2 3 4 5 

And we want to read it from file. In this example the numbers of rows and columns is known!!!

   public class Read2 {
    public static void main(String[] args) throws FileNotFoundException {
        Scanner s = new Scanner(new FileReader("Test2"));
        int[][] array = new int[9][5];
        while (s.hasNextInt()) {
            for (int i = 0; i < array.length; i++) {
                String[] numbers = s.nextLine().split(" ");
                for (int j = 0; j < array[i].length; j++) {
                    array[i][j] = Integer.parseInt(numbers[j]);
                }
            }
        }
        for (int[] x : array) {
            System.out.println(Arrays.toString(x));
        }
         // It is a normal int[][] and i can use their data for calculations.
        System.out.println(array[0][3] + array[7][2]);
    }
} 

// Output
[1, 2, 3, 4, 5]
[1, 2, 3, 4, 0]
[1, 2, 3, 0, 0]
[1, 2, 0, 0, 0]
[1, 0, 0, 0, 0]
[1, 2, 0, 0, 0]
[1, 2, 3, 0, 0]
[1, 2, 3, 4, 0]
[1, 2, 3, 4, 5]
7//result from sum

My question is: if i have a file with x=rows and y=columns(unknown size) and i want to read numbers from file and put them is 2d array like in previous example. What type of code should i write?

Using try with resources will close the file once the stream has been processed.

  • use Files.lines to return a stream.
  • split the lines on some delimiter to expose the ints. One or more spaces is the chosen delimiter here.
  • then simply convert to an int and package in an int[][] array.
  • upon any exception, null is returned.
public static int[][] readInts(String fileName) {
    try (Stream<String> lines = Files.lines(Path.of(fileName))) {
        
        return lines.map(line->Arrays.stream(line.split("\\s+"))
                        .mapToInt(Integer::valueOf)
                        .toArray())
                .toArray(int[][]::new);
        
    } catch (IOException ioe) {
        ioe.printStackTrace();
    }
    return null;
}

Note: The above presumes that each row of the array is on a separate line in the file. Lines containing different counts of integers would also work.

Here is a solution using the stream API:

var arr = new BufferedReader(new FileReader("PATH/TO/FILE")).lines()
                .map(s -> s.split("\\s+"))
                .map(s -> Stream.of(s)
                        .map(Integer::parseInt)
                        .toArray(Integer[]::new))
                .toArray(Integer[][]::new);

Just as @Andy Turner said, use List<List<Integer>> , since List does not compulsively demand its length while initialing. Code is this:

public class Read2 {

    public static void main(String[] args) throws FileNotFoundException {
        Scanner s = new Scanner(new FileReader("Test2"));
        List<List<Integer>> list = new ArrayList<>();
        // scan digits in every line
        while (s.hasNextLine()) {
            String str = s.nextLine();
            String[] strSplitArr = str.split(" ");
          list.add(Arrays.stream(strSplitArr)
              .map(Integer::parseInt)
              .collect(Collectors.toList()));
        }
        for (List<Integer> integersInOneLine : list) {
            System.out.println(integersInOneLine.stream()
                      .map(Object::toString)
                      .collect(Collectors.joining(", ", "[", "]")));
            System.out.println();
        }
    }
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM