简体   繁体   中英

How do I remove a row and a column from a jagged 2d array?

Say I have an array that looks something like this:

{{1,3,5,7},{2,4,6,8,10,12},{2,3,5,7,11,13,17}}

How should I go about creating a new array in Java that is exactly the same as this one, except one row and one column has been removed?

I can perform this task with an even-sized array, but jagged arrays are giving me some trouble. I thought about first creating a new array with unspecified column count, but where do I go from there?

/**
 * Creates a new array that is a copy of the input matrix,
 * except that one row and one column have been altered.
 * Precondition: the row index is between 0 (inclusive)
 * and the number of rows of matrix (not inclusive)
 *
 * @param matrix the input two dimensional array
 * @param row    the index of the row to remove
 * @param col    the index of the column to remove
 */
public static int[][] removeRowAndCol(int[][] matrix, int row, int col) {
    int[][] altered = new int[(matrix.length - 1)][];
    int x = 0;
    for (int i = 0; i < matrix.length; i++) {
        if (matrix[i].length < col + 1 && i != row) {
            altered[x] = new int[matrix[i].length];
            for (int j = 0; j < altered[x].length; j++) {
                altered[x][j] = matrix[i][j];
            }
            if (x < matrix.length - 1) {
                x++;
            }
        } else if (matrix[i].length > col && i != row) {
            altered[x] = new int[matrix[i].length - 1];
            int y = 0;
            for (int z = 0; z < matrix[i].length - 1; z++) {
                if (z != col) {
                    altered[x][y] = matrix[i][z];
                    y++;
                } else {
                    z--;
                }
            }
            if (x < matrix.length - 1) {
                x++;
            }
        }
    }
    return altered;
}

when running a test case such as:

removeRowAndCol(new int[][]{{1, 2}, {3, 4}}, 1, 1)

the method returns {{1}} which is correct.

However, with something like this:

int[][] array = {{1,2,3,4},{11,12,13,14,15,16},{21,22,23,24},{31,32,33}};
removeRowAndCol(array, 0, 0)
removeRowAndCol(array, 2, 3)

the method would freeze.

Can somebody take a look at the code and tell me what I did wrong?

A bidimensional array, jagged or not, is more an array of array than anything else. You have to create each row by hand and thus, you can choose any size for each individual row.

import java.util.Arrays;

public class Temp {
    public static void main(String[] args) {
        int[][] jagged = {{1, 2, 3}, {4, 5, 6, 7, 8}, {9, 10, 11, 12, 13, 14, 15, 16}};
        System.out.println("Jagged: " + Arrays.deepToString(jagged));
        System.out.println("Smaller 1: " + Arrays.deepToString(removeRowAndCol(jagged, 0, 0)));
        System.out.println("Smaller 2: " + Arrays.deepToString(removeRowAndCol(jagged, 1, 1)));
        System.out.println("Smaller 3: " + Arrays.deepToString(removeRowAndCol(jagged, 2, 2)));
    }

    private static int[][] removeRowAndCol(int[][] jagged, int i, int j) {
        int[][] smaller = new int[jagged.length - 1][];

        // WARN: outofbounds checks are not implemented!
        for (int smallerI = 0; smallerI < smaller.length; smallerI++) {
            int sourcedI = smallerI;
            if (smallerI >= i) {
                sourcedI++;
            }

            smaller[smallerI] = new int[jagged[sourcedI].length - 1];

            for (int smallerJ = 0; smallerJ < smaller[smallerI].length; smallerJ++) {
                int sourcedJ = smallerJ;
                if (smallerJ >= j) {
                    sourcedJ++;
                }
                smaller[smallerI][smallerJ] = jagged[sourcedI][sourcedJ];
            }
        }

        return smaller;
    }
}

Which outputs:

Jagged: [[1, 2, 3], [4, 5, 6, 7, 8], [9, 10, 11, 12, 13, 14, 15, 16]]
Smaller 1: [[5, 6, 7, 8], [10, 11, 12, 13, 14, 15, 16]]
Smaller 2: [[1, 3], [9, 11, 12, 13, 14, 15, 16]]
Smaller 3: [[1, 2], [4, 5, 7, 8]]

You can use streams to rearrange the rows of the 2d array and the array itself without one row and one column. It doesn't matter if this array is jagged or rectangular. And you can get rid of the unnecessary condition that the row and column to be removed should be present.

Try it online!

/**
 * Creates a new array that is a copy of the input matrix,
 * except that one row and one column were removed if present.
 *
 * @param matrix the input two-dimensional array.
 * @param row    the index of the row to remove.
 * @param col    the index of the column to remove.
 * @return new two-dimensional array.
 */
public static int[][] removeRowAndCol(int[][] matrix, int row, int col) {
    return IntStream
            // iterate over the indexes
            // of rows of the matrix
            .range(0, matrix.length)
            // filter out the row to remove
            .filter(i -> i != row)
            // rearrange the remaining rows
            .mapToObj(i -> IntStream
                    // iterate over the indexes
                    // of columns of the matrix
                    .range(0, matrix[i].length)
                    // filter out the column to remove
                    .filter(j -> j != col)
                    // take the cell value
                    .map(j -> matrix[i][j])
                    // rearrange the row
                    .toArray())
            // rearrange the matrix
            .toArray(int[][]::new);
}
public static void main(String[] args) {
    int[][] arr1 = {{1,2},{3,4}};
    int[][] arr2 = {{1,3,5,7},{2,4,6,8,10,12},{2,3,5,7,11,13,17}};
    int[][] arr3 = {{1,2,3,4},{11,12,13,14,15,16},{21,22,23,24},{31,32,33}};

    System.out.println(Arrays.deepToString(removeRowAndCol(arr1, -1, 1)));
    System.out.println(Arrays.deepToString(removeRowAndCol(arr2, 2, 3)));
    System.out.println(Arrays.deepToString(removeRowAndCol(arr3, 3, -1)));
}

Output:

[[1], [3]]
[[1, 3, 5], [2, 4, 6, 10, 12]]
[[1, 2, 3, 4], [11, 12, 13, 14, 15, 16], [21, 22, 23, 24]]

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