【问题标题】:How to read text from a file and replace the missing data? [closed]如何从文件中读取文本并替换丢失的数据? [关闭]
【发布时间】:2021-05-23 14:48:04
【问题描述】:

假设我在一个文件中有这个矩阵,首先我想从一个文件中读取它,然后我想将 *(star) 更改为 (2x8x11/3 = 58.7):

| 1 2 3 |               | 1 2 3 |
| 4 * 6 |   ----------> | 4 58.7 6 |
| 7 8 9 |               | 7 8 9 |
| 10 11 12|             | 10 11 12|

这就是我所做的

//This method turns the Strings to a matrix (A[][])
//Right now It doesn't work properly because when I put * in my file it crashes because * is not a number 
public double[][] fixMatrix1(String fileName, int r, int c) {//r is row c is column
    double A[][]= new double [r][c];
    try {
        File file = new File(fileName);
        FileInputStream input = new FileInputStream(file);
        Scanner scan = new Scanner(input);
        while(scan.hasNext()) { //IMPORTANT From here I want to look at my file and see if there is any * inside. If so I want to change * to like 999 this way it becomes a number

                /*
                if(scan.nextLine() == "*") {
                  replace that * with 999
                }
                 Something like this (If this isn't clear I want to change that star and replace it with any number so I can take the matrix inside the file as a number matrix, not as a String version that printed on console)
                */

                for (int i = 0; i < r; i++) {
                    for (int j = 0; j < c; j++) {
                        A[i][j] = scan.nextDouble();
                 //With this for block I can fill my empty matrix with numbers in a file
            }
        }
    }
        scan.close();
        input.close();
    } 
    catch (FileNotFoundException e) {
        System.err.println(e.getMessage());
    }
    catch (IOException e) {
        System.err.println(e.getMessage());
    }
    //At the end return
    return A; //It will return my matrix(Right now I turned the String version of a matrix into a double version of a matrix which I can use this A[][] matrix in different methods to replace that * or 999 to another number
}
//From here I want to find that row and column of number that is 999 (which is the right row and column for *)
public void fixMatrix(double A[][], int row, int column) {
    for (int i = 0; i < row; i++) {
        for (int j = 0; j < column; j++) {
            if (A[i][j]==999) { //If any row and column has 999 in it take that row and column
                for (int j2 = 0; j2 < row; j2++) {
                    /*I want it to take that row and column which is 
                    | 2 |
                    | 999|
                    | 8 |
                    | 11|
                    and I want to multiply 2 8 11 and divide them by 3 (2*8*11/3) and give the result in the console like 58.7)
                    */
                    double a1 = A[j2][j]; 
                    System.out.println(a1);
                }
            } System.out.println();
        }
    }
    
}
public static void main(String[] args) {
    //Part 1
    Homework h1 = new Homework();
    
    h1.printMatrix(h1.fixMatrix1("corruptedMatrix.txt", 4, 3), 4, 3);

    /*Right now this gives me 
     | 1 2 3 |
     | 4 5 6 |
     | 7 8 9 |
     | 10 11 12|
     because in my file there is no * (It crashes when I put * in my file because it's not a number)
     */

【问题讨论】:

    标签: java matrix replace filereader missing-data


    【解决方案1】:

    这是使用 cmets 指导您的完整工作代码。

    import java.io.File;
    import java.io.FileInputStream;
    import java.util.Scanner;
    
    public class Homework {
      /**
       * This method reads the matrix from
       * the file as a Strings[][] in order 
       * to cater for the '*' (asterisk).
       */
      public String[][] readMatrix (String fileName, int rows, int columns) {
        String matrix[][]= new String [rows][columns];
        try {
          try (Scanner sc = new Scanner (new FileInputStream (new File (fileName)));) {
            /**
             * With this block, the matrix[][]
             * is filled with values from the
             * file.
             */
            while (sc.hasNext ())
              for (int i = 0; i < rows; i++)
                for (int j = 0; j < columns; j++)
                  matrix [i] [j] = sc.next ();
          }
        }
        catch (Throwable t) {
          System.out.println (t);
        }
        /**
         * Now the returned is the matrix
         * from file with an '*' (asterisk)
         * in it.
         * ie
         * |  1  2  3 |
         * |  4  *  6 | 
         * |  7  8  9 |
         * | 10 11 12 |
         */
        return matrix;
      }
      /**
       * This method replaces the '*'
       * with the average of the product
       * of the second column of the matrix.
       */
      public String[][] fixMatrix (String matrix[][], int rows, int columns) {
        // Loop through elements of matrix
        for (int i = 0; i < rows; i++)
          for (int j = 0; j < columns; j++) {
            /**
             * If value is an '*', replacw it...
             */
            if (matrix [i] [j].equals ("*")) {
              // The variable to store the product
              double product = 1;
              // Loop through each row, and multiply
              // the second value to get product.
              for (int k = 0; k < rows; k++)
                if (k != j)
                  product *= Integer.parseInt (matrix [k] [1]);
              // Now divide the product by 3
              // and round off the decimal
              // then convert it to String
              // and replace the '*' in
              // matrix with the value
              matrix [i] [j] = Double.toString (Math.round ((product / 3)));
              // No need to continue loop
              // so return the matrix
              return matrix;
            }
          }
        // This should not excecute
        return null;
      }
      /**
       * This method prints the matrix.
       */
      public void printMatrix (String[][] matrix, int rows, int columns) {
        for (int i = 0; i < rows; i++) {
          for (int j = 0; j < columns; j++)
          // Aligns the numbers to the right
            System.out.printf ("%4s ", matrix [i] [j]);
          System.out.println ();
        }
      }
      /**
       * This is the driver method.
       */
      public static void main (String[] args) {
        int rows = 4, columns = 3;
        Homework homeWork = new Homework ();
        homeWork.printMatrix (
          homeWork.fixMatrix (
            homeWork.readMatrix (
              "corruptedMatrix.txt", rows, columns), rows, columns), rows, columns);
      }
    }
    

    【讨论】:

    • 告诉我它是否解决了你的问题。
    • 你一定是上帝,非常感谢你
    • 好的。如果星星位于矩阵的不同位置,请将60 行中的product *= Integer.parseInt (matrix [k] [1]); 替换为product *= Integer.parseInt (matrix [k] [j]);
    • 是的,我试图解决这个问题,我修复了它来这里写它,你已经写了它,但我认为它也需要像 if (k != i) 而不是 if (k != j) 因为假设 * 是在 6 的位置,即 i=1 j=2 但如果我们说 if (k !=j) 这意味着 k 不能是 2 但 k 将从 0 开始... k=0 j=2 我们可以取 3 没问题k=1 j=2 我们不能取 6 因为 * 不是数字所以应该是 if (k != i) 我想
    【解决方案2】:

    您并没有完全说明您明确遇到问题的部分,但看起来它正在确定文件中的下一个标记是双精度还是“*”。如果您使用的是扫描仪,那么:

    • 在调用 nextDouble() 之前,使用hasNextDouble() 方法确定下一项是否为双精度数

    • 使用hasNext(),传入与“”匹配的regular expression,以确定下一个标记是否为“”:如下所示:

      如果 (scanner.hasNext("\*")) ...

    (阅读正则表达式以了解为什么需要反斜杠:本质上,“*”通常具有特殊含义,因此您需要对其进行转义。)

    此外,在您的中间结构中,我建议使用 Doubles 数组而不是 doubles:换句话说,Double 可以采用 null 的值,因此您不必使用“特殊”值如 999 表示“不存在”,并避免文件意外包含该值的风险。

    【讨论】:

      【解决方案3】:

      您可以采取不同的方法。

      这里有 2 个:

      1. 使用字符串矩阵并在相关时转换为数字/从数字转换。 Double.parseDouble(string) 将字符串转换为双精度。 String.valueOf(double)"" + double 会将双精度转换为字符串。
      2. 不要使用*,而是使用一个永远不会在此处使用的数字。例如,如果该矩阵永远不会有负数,您可以使用负数而不是 *。

      编辑: 看来我没有正确理解这个问题。

      if(scan.nextLine() == "*") {
        replace that * with 999
      }
      

      可以替换为

      String nextLine = scan.nextLine().replace("*", "999")
      

      这样你在 * 的位置得到 999。 将 hasNext() 替换为 hasNextLine() 并在 hasNextLine() 循环中,您可以执行类似

      int j = 0;
      for (String num : nextLine.split(" ")) {
          A[i][j] = Double.parseDouble(num);
          j++;
      }
      i++;
      

      此外,您应该使用 .equals() 来比较字符串。由于它们是对象,== 只比较它们的引用,而不是它们的内容。

      【讨论】:

      • 是的,我尝试过Double.parseDouble(string),但它不起作用,因为读取方法不会像 1 然后 2 然后 3 那样逐个读取它同时读取 1 2 3 并给出“ 1 2 3" 像这样,所以Double.parseDouble(string) 不能把它变成双:/
      • @Lucky,我已经编辑了答案
      猜你喜欢
      • 2013-03-14
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-03-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多