tken25
tken25

Reputation: 35

Code returning different outputs using goto

I'm writing a function that takes an input n and creates a 1D array of size (2n-1)^2 to simulate a square. I.e. for an input of n = 1, there is just one point, for an input of n = 2, it would look like

0 1 2
3 4 5
6 7 8

and for n = 3 it would look like

0 1 2 3 4
5 6 7 8 9
10 11 12 13 14
15 16 17 18 19
20 21 22 23 24

where each number is a point.

The function terminates when the current location is detected at being on an edge and the point attempts to move off of the square's grid.

The purpose of this is to simulate how many points are visited for squares of different sizes, from n=2^0 up to n=2^8 and to return the fraction of how many points are visited over the total amount of points in the square.

The function generates a random number and checks the modulus of it against 4, and if it returns 0, the location is moved up 1, if it returns 1, the location is moved right, 2 goes down, and 3 goes left.

#include <stdio.h>
#include <stdlib.h>
#include <math.h>

double two_d_random (int n) {
       int tot_points = (2 * n - 1)*(2 * n - 1);
       int value = (n*n)+((n-1)*(n-1))-1; //center
       int length = 2 * n - 1; //length of side
       int *array = (int *)malloc (sizeof (int) * tot_points);     
       int count = 0;
       array[value] = 1;

   while (1 == 1) {
          int r = rand () % 4;
          array[value] = 1;
          if (r == 0) {//UP
                 if ((value >= 0) && (value < length)) {
                       goto a;
                       }
                 else {
                     array[value] = 1;
                       value -= length;
                       }
                 }
          else if (r == 1) {//RIGHT
                 if ((value % length) == (2*n-2)){
                       goto a;
                       }
                 else {
                     array[value] = 1;
                       value += 1;
                       }
                 }
          else if (r == 2) {//DOWN
                 if ((value < tot_points) && (value >= (tot_points - length))) {
                       goto a;
                       }
                 else {
                     array[value] = 1;
                       value += length;
                       }
                 }
          else if (r == 3) {//LEFT
                 if (value % length == 0) {
                       goto a;
                       }
                 else {
                     array[value] = 1;
                       value -= 1;
                       }
                 }
          }

a:
   for (int i = 0; i < tot_points; i++) {
          if (array[i] == 1) {
                 count += 1;
                 }
          }

   free (array);
   return 1.0 * count / tot_points;


   }

int main ()
   {
   int trials = 1000;

   srand (12345);
   for (int n = 1; n <= 256; n *= 2)
          {
          double sum = 0.;
          for (int i = 0; i < trials; i++)
                 {
                 double p = two_d_random(n);
                 sum += p;
                 }
          printf ("%d %.3lf\n", n, sum / trials);
          }
   return 0;
   }

My current problem is that while I run it on my machine, I get a range of values I'm not expecting:

Current result

However, when a colleague runs it on their machine, they get the following which is what I expected:

Desired result

I realize this is a large amount to ask at one point. I also realize that I should not use goto. I've put a lot of time into this however and I've no idea how to fix this. Any help is greatly appreciated.

Upvotes: 2

Views: 61

Answers (1)

Kingsley
Kingsley

Reputation: 14906

You need to initialise your array. When calling malloc() it just returns a chunk of un-initialised memory. Either initialise it, or use calloc() instead, to get pre-zeroed memory.

double two_d_random( int n )
{
    int tot_points = ( 2 * n - 1 ) * ( 2 * n - 1 );
    int value = ( n * n ) + ( ( n - 1 ) * ( n - 1 ) ) - 1;      //center
    int length = 2 * n - 1;     //length of side
    int *array = (int *) malloc( sizeof( int ) * tot_points );
    int count = 0;

    // Initialise the array to zero
    for ( int i=0; i<tot_points; i++ )
    {
        array[i] = 0;
    }

    array[value] = 1;

    while ( 1 == 1 )
    {
        int r = rand() % 4;
        array[value] = 1;
        if ( r == 0 )

With this modification, I get results similar to what you reported as desired:

1 1.000
2 0.367
4 0.221
8 0.154
16 0.122
32 0.101
64 0.085
128 0.077
256 0.071

Upvotes: 1

Related Questions