Search code examples
javamatrixadjacency-matrix

Program counting adjacent elements in a 2D array gives inconsistent results


I have a piece of program that i have to fill. It is supposed to count adjacent numbers in a 5 by 5 binary matrix. For example a matrix like this:

0 1 1 1 0 
1 0 0 0 1 
1 0 0 0 0 
1 0 0 1 0 
0 1 0 1 0 

Should return 8, you can only move horizontally or vertically.

Here is the code that generates these said matrices and it can't have any modifications after i'm done.

import java.util.Random;

public class Test {

public static void main(String[] args) {
    final Random r = new Random();


    for (int kerrat = 0; kerrat < 10; kerrat++) {
        int[][] alkioTaulukko = new int[5][5];

        System.out.println("Matriisin");
        for (int i = 0; i < alkioTaulukko.length; i++) {
            System.out.print("");
            for (int j = 0; j < alkioTaulukko[i].length; j++) {
                alkioTaulukko[i][j] = r.nextInt(2);
                System.out.print("" + alkioTaulukko[i][j] + " ");
            }
            System.out.println("");
        }

        System.out.print("suurimman yhtenäisen alueen koko on ");
        System.out.println(laskeSuurinAlue(alkioTaulukko));
        System.out.println("");
    }

}

}

And finally here is my solution to the problem.

static int  laskeSuurinAlue(int[][] matriisi) {

    int vierekkaiset = 0;

    int rivi = matriisi.length;
    int palkki = matriisi[0].length;

    for (int r = 0; r < rivi; r++)
    {
        for (int p = 0; p < palkki; p++)
        {
            if ((p+1 < palkki) && (matriisi[r][p] == matriisi[r][p+1]))//loops through the rows
                vierekkaiset++;

            if ((r+1 < rivi) && (matriisi[r][p] == matriisi[r+1][p]))//loops through the columns
                vierekkaiset++;
        }
    }
    return vierekkaiset;
}

What happens is that my solution always brings up too big results and i'm failing to see any pattern between each run. However if i use a smaller matrix like this:

int[][] array = {{1, 0, 1}, {0, 1, 1}, {0, 1, 0}};

The result is correctly 4.

And if i use a bigger one like this:

int[][] arr = {{1,0,1,1,0},
            {0,0,1,0,0},
            {0,0,1,0,1},
            {1,1,1,0,1},
            {0,0,1,0,0}
    };

The result is always 20.

Finally here is my code at its current state:

    import java.util.Random;

    import static java.util.Arrays.deepToString;

    public class Test {
    public static void main(String[] args) {
    final Random r = new Random();
    int[][] array = {{1, 0, 1}, {0, 1, 1}, {0, 1, 0}};
    int[][] arr = {{1,0,1,1,0},
            {0,0,1,0,0},
            {0,0,1,0,1},
            {1,1,1,0,1},
            {0,0,1,0,0}
    };
    for (int kerrat = 0; kerrat < 10; kerrat++) {
        int[][] alkioTaulukko = new int[5][5];

        System.out.println("Matriisin");
        for (int i = 0; i < alkioTaulukko.length; i++) {
            System.out.print("");
            for (int j = 0; j < alkioTaulukko[i].length; j++) {
                alkioTaulukko[i][j] = r.nextInt(2);
                System.out.print("" + alkioTaulukko[i][j] + " ");
            }
            System.out.println("");
        }

        System.out.print("suurimman yhtenäisen alueen koko on ");
        System.out.println(laskeSuurinAlue(arr));//Change to arr,array or alkioTaulukko to run the code with different matrices
        System.out.println(deepToString(arr));
        System.out.println("");

    }

}


static int  laskeSuurinAlue(int[][] array) {


    int counter = 0;

    int rowLimit = array.length;
    int colLimit = array[0].length;

    for (int r = 0; r < rowLimit; r++)
    {
        for (int c = 0; c < colLimit; c++)
        {
            if ((c+1 < colLimit) && (array[r][c] == array[r][c+1]))
                counter++;

            if ((r+1 < rowLimit) && (array[r][c] == array[r+1][c]))
                counter++;
        }
    }
    return counter;
}

}

Solution

  • You're couting the same entry more than once. Use this code

    static int  laskeSuurinAlue(int[][] array) {
        int counter = 0;
    
        int rowLimit = array.length;
        int colLimit = array[0].length;
    
        for (int r = 0; r < rowLimit; r++)
        {
            for (int c = 0; c < colLimit; c++)
            {
                if (array[r][c] == 0) {
                    continue;
                }
    
                int sum = array[r][c];
                sum += (r + 1 < rowLimit) ? array[r+1][c] : 0;
                sum += (c + 1 < colLimit) ? array[r][c+1] : 0;
                sum += (r - 1 >= 0 ) ? array[r-1][c] : 0;
                sum += (c - 1 >= 0) ? array[r][c-1] : 0;
    
                if (sum > 1) {
                    counter++;
                }
            }
        }
        return counter;
    }