Форматирование двумерного массива чисел

Проблема: у
меня есть 2-мерный массив, заполненный числами. Я должен вывести его так, чтобы он отображал: "*" между соседями с разными значениями и с " "если значения совпадают. Пример:

      *********
*1 1*3*4*
***** * *
*2 2*3*4*
*********

Я пробовал много вещей, например, создать другой массив с [Nx2][Mx2] размер или System.out.format, но, в конце концов, он никогда не форматируется так, как мне нравится. Любые предложения, как я могу это решить?

      private static void changeColumn(int[][] secondLayerArr, int n, int m) {
    String[][] finalLayerArr = new String[n * 2 - 1][m];
    int finalLayerRow = -2;
    //second layer output
    for (int i = 0; i < n; i++) {
        finalLayerRow += 2;

        for (int j = 0; j < m; j++) {
            if (j < m - 1) {
                if (secondLayerArr[i][j] != secondLayerArr[i][j + 1]) {
                    finalLayerArr[finalLayerRow][j] = (secondLayerArr[i][j]) + "*";
                    //  System.out.print(secondLayerArr[i][j] + "*");
                } else {
                    finalLayerArr[finalLayerRow][j] = (secondLayerArr[i][j]) + " ";
                    //  System.out.print(secondLayerArr[i][j]);
                }
            } else {
                finalLayerArr[finalLayerRow][j] = (secondLayerArr[i][j]) + "*";
                //System.out.print(secondLayerArr[i][j]+"*");
            }
        }
    }
    printColumn(finalLayerArr);
}
      public static void changeRow(String[][] finalLayerArr) {
    for (int i = 0; i < finalLayerArr[0].length; i++) {
        System.out.print("***");
    }
    System.out.println();

    for (int i = 0; i < finalLayerArr.length; i++) {
        System.out.print("*");
        for (int j = 0; j < finalLayerArr[0].length; j++) {
            if (finalLayerArr[i][j] == null) {
                if (finalLayerArr[i - 1][j].equals(finalLayerArr[i + 1][j])) {
                    finalLayerArr[i][j] = " ";
                } else {
                    finalLayerArr[i][j] = "*";
                }
            }
            System.out.printf("%2s", finalLayerArr[i][j], "");
        }
        System.out.println();
    }
}

Он показывает что-то вроде результата, который я хочу, но не отформатирован, как в таблице.

3 ответа

Решение

Вы можете перебрать каждую строку, которая не является последней, а затем каждую букву, которая не является последней в этом массиве, и проверять, равна ли она первой и правой. Если это так, распечатайте соответствующую вещь.

Что-то в этом роде:

      public class FormattingArray {
    public static void printFormattedInts(int[][] unformattedInts) {

        // getting maximum digits per number

        int maxDigits = 0;

        for (int[] intArray : unformattedInts) {
            for (int num : intArray) {
                if (lengthOfInt(num) > maxDigits) {
                    maxDigits = lengthOfInt(num);
                }
            }
        }


        // printing first line (purely aesthetic)

        System.out.print("*".repeat(unformattedInts[0].length * maxDigits + unformattedInts[0].length + 1));

        System.out.println();

        // printing each row


        for (int row = 0; row < unformattedInts.length - 1; row ++) {
            String lowerRow = "*"; // the row to print below this one

            System.out.print("*");

            for (int i = 0; i < unformattedInts[row].length - 1; i ++) {

                if (lengthOfInt(unformattedInts[row][i]) < maxDigits) {
                    System.out.print("0".repeat(maxDigits - (lengthOfInt(unformattedInts[row][i]))));
                }

                System.out.print(unformattedInts[row][i]);

                if (unformattedInts[row][i] == unformattedInts[row][i + 1]) {
                    System.out.print(" ");
                } else {
                    System.out.print("*");
                }

                if (unformattedInts[row][i] == unformattedInts[row + 1][i]) {
                    lowerRow += " ".repeat(maxDigits);
                    lowerRow += "*";
                } else {
                    lowerRow += "*".repeat(maxDigits + 1);
                }

            }

            if (lengthOfInt(unformattedInts[row][unformattedInts[row].length - 1]) < maxDigits) {
                System.out.print("0".repeat(maxDigits - (lengthOfInt(unformattedInts[row][unformattedInts[row].length - 1]))));
            }

            System.out.print(unformattedInts[row][unformattedInts[row].length - 1]);

            System.out.println("*");

            // doing last char

            if (unformattedInts[row][unformattedInts[row].length - 1] == unformattedInts[row + 1][unformattedInts[row].length - 1]) {
                lowerRow += " ".repeat(maxDigits);
                lowerRow += "*";
            } else {
                lowerRow += "*".repeat(maxDigits + 1);
            }

            System.out.println(lowerRow);
        }

        // doing last row

        System.out.print("*");

        for (int i = 0; i < unformattedInts[unformattedInts.length - 1].length - 1; i ++) {

            if (lengthOfInt(unformattedInts[unformattedInts.length - 1][i]) < maxDigits) {
                System.out.print("0".repeat(maxDigits - lengthOfInt(unformattedInts[unformattedInts.length - 1][unformattedInts[0].length - 1])));
            }

            System.out.print(unformattedInts[unformattedInts.length - 1][i]);

            if (unformattedInts[unformattedInts.length - 1][i] == unformattedInts[unformattedInts.length - 1][i + 1]) {
                System.out.print(" ");
            } else {
                System.out.print("*");
            }

        }

        if (lengthOfInt(unformattedInts[unformattedInts.length - 1][unformattedInts[unformattedInts.length - 1].length - 1]) < maxDigits) {
            System.out.print("0".repeat(maxDigits - lengthOfInt(unformattedInts[unformattedInts.length - 1][unformattedInts[unformattedInts.length - 1].length - 1])));
        }

        System.out.print(unformattedInts[unformattedInts.length - 1][unformattedInts[unformattedInts.length - 1].length - 1]);

        System.out.println("*");

        System.out.print("*".repeat(unformattedInts[0].length * maxDigits + unformattedInts[0].length + 1));

        System.out.println();
    }

    public static int lengthOfInt(int num) {
        return String.valueOf(num).length();
    }
}

Надеюсь это поможет :)

Прокрутите 2d-массив, сначала перебирая количество массивов внутри массива, а затем перебирая каждый отдельный.

Внутри отдельных массивов проверьте, является ли это первым элементом в массиве. Если да, выведите *. Затем проверьте, равен ли предыдущий и т. Д.

Для «выхода» «между соседними строками [которые имеют один и тот же элемент]» мы можем сохранить звездную строку внутри StringBuilder и распечатать ее в конце.

      int[][] arr = {{1, 1, 3, 4}, {2, 2, 3, 4}};
int lineLength = arr[0].length * 2 + 1;
for (int i = 0; i < lineLength - 1; i++) {
    System.out.print("*");
}
System.out.println();
for (int i = 0; i < arr.length; i++) {
    int[] current = arr[i];
    int before = 0;
    StringBuilder str = new StringBuilder();
    for (int j = 0; j < current.length; j++) {
        int rn = current[j];
        if (j == 0) {
            System.out.print("*");
            System.out.print(rn);

        } else {
            if (before == rn) {
                System.out.print(" ");
                System.out.print(rn);
            } else {
                System.out.print("*");
                System.out.print(rn);
            }
        }
        if (i != arr.length - 1 && arr[i + 1][j] == rn) {
            str.append("* ");
        } else {
            str.append("**");
        }
        before = rn;
    }
    if (i != arr.length - 1) {
        System.out.println();
        System.out.println(str.toString());
    }
}
System.out.println();
for (int i = 0; i < lineLength - 1; i++) {
    System.out.print("*");
}

Какие отпечатки:

      ********
*1 1*3*4
**** * *
*2 2*3*4
********

Это заняло слишком много времени.

Вы можете составить массив строк, состоящий из чисел из первого массива и их соседних элементов, то есть пробелов и звездочек. При необходимости отформатируйте их, добавив ведущие нули и соответствующее количество соседних элементов. Для каждой строки создайте два массива строк, то есть элементы с их горизонтальными соседями и промежуточный массив с вертикальными соседями, а также начальные и конечные строки звездочек. Затем расплющите их по вертикали и соедините элементы рядов в одну нитку по горизонтали.

Попробуйте онлайн!

      int[][] arr1 = {
        {1, 1, 3, 3, 4, 6, 5, 6, 8, 75},
        {2, 2, 2, 3, 4, 5, 5, 5, 8, 8},
        {3, 3, 5, 5, 6, 7, 7, 5, 2, 8}};

// numbers format, digits count
int s = 2;

// formatted array representation
// with neighbouring elements
String[] arr2 = IntStream
        // iterate over indices of the rows of the
        // array, plus leading row of asterisks
        .range(-1, arr1.length)
        // for each row create two arrays of strings:
        // horizontal neighbours and vertical neighbours
        .mapToObj(i -> {
            // assume the lengths of the rows are identical
            int length = arr1[0].length * s * 2 - s + 2;
            String[] asterisks = new String[length];
            Arrays.fill(asterisks, "*");
            if (i == -1)
                // leading row of asterisks
                return Stream.of(null, asterisks);
            else
                // iterate over indices of the elements of the rows,
                // add asterisks between neighbours with different
                // values and spaces if values are the same
                return Stream.of(IntStream.range(0, arr1[i].length)
                            // horizontal neighbours
                            .mapToObj(j -> {
                                // formatted representation
                                // of the element of the row,
                                // with a leading zeros if necessary
                                String val = String.format(
                                        "%0" + s + "d", arr1[i][j]);
                                if (j == 0)
                                    // leading asterisk
                                    val = "*" + val;
                                if (j == arr1[i].length - 1)
                                    // trailing asterisk
                                    val += "*";
                                else
                                    // neighbour element
                                    val += arr1[i][j] == arr1[i][j + 1] ?
                                            " ".repeat(s) : "*".repeat(s);
                                return val;
                            }).toArray(String[]::new),
                        // second array
                        (i == arr1.length - 1) ?
                            // trailing row of asterisks
                            asterisks :
                            // vertical neighbours
                            IntStream.range(0, arr1[i].length)
                                .mapToObj(j -> {
                                    String val = "";
                                    if (j == 0)
                                        // leading asterisk
                                        val = "*";
                                    // neighbour element
                                    val += (arr1[i][j] == arr1[i + 1][j] ?
                                            " ".repeat(s) : "*".repeat(s));
                                    if (j == arr1[i].length - 1)
                                        // trailing asterisk
                                        val += "*";
                                    else
                                        // intermediate asterisks
                                        val += "*".repeat(s);
                                    return val;
                                }).toArray(String[]::new));
        }).flatMap(Function.identity())
        // skip first null
        .skip(1)
        // Stream<Stream<String>>
        .map(Arrays::stream)
        // join each row into one string
        .map(stream -> stream.collect(Collectors.joining()))
        .toArray(String[]::new);

// output
Arrays.stream(arr2).forEach(System.out::println);

Выход:

      ****************************************
*01  01**03  03**04**06**05**06**08**75*
*************  **  ******  ******  *****
*02  02  02**03**04**05  05  05**08  08*
*****************************  ******  *
*03  03**05  05**06**07  07**05**02**08*
****************************************
Другие вопросы по тегам