Solved

C - Generating 5x5 array

Posted on 2006-11-04
7
1,044 Views
Last Modified: 2008-02-01
Using C, I am trying to generate a 5x5 array filled with random numbers from 0.0 to 1.0 (including 0.0 and 1.0).  Each row should add up to 1, which is a markov table.  The output should look similar as follows:
Row 1 [ 0.3 0.4 0.1 0.0 0.2 ]
Row 2 [ 0.0 1.0 0.0 0.0 0.0 ]
Row 3 [ 0.8 0.0 0.0 0.2 0.0 ]
Row 4 [ 0.1 0.6. 0.2 0.0 0.1]
Row 5 [ 0.9 0.0 0.0 0.0 0.0 ]

I was going to fill the table with random numbers, then normalize them (divide each by the row's sum).  I was able to generate the random numbers, but am getting a segmentation fault or mismatches from storing in the array and printing it later.  Here is the code (compiled by CC).

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

/*
 * MAIN FUNCTION - Generate Random Markov Table
 */
int main() {

/* Set Random Seed from System Time for rand() */
srand(time(NULL));

/* Create Markov array */
int MAXROW = 4;
int MAXCOL = 4;
float arrMarkov[MAXROW][MAXCOL];

/* Fill Markov array with Random numbers */
int row;
int col;
float rnum;
for (row = 0; row <= MAXROW; row++) {
    printf("Row %i [", row);
    for (col = 0; col <= MAXCOL; col++) {
        rnum = (float)(rand() % 11) / 10;
        arrMarkov[row][col] = rnum;
        printf("%f ", rnum);
    }
    printf("]\n");
}

/* Print array */
printf("\n");
for (row = 0; row <= MAXROW; row++) {
    printf("Row %i [", row);
    for (col = 0; col <= MAXCOL; col++) {
        printf("%f ", arrMarkov[row][col]);
    }
    printf("]\n");
}

return 0;
}
0
Comment
Question by:deadite
  • 2
  • 2
  • 2
  • +1
7 Comments
 
LVL 84

Accepted Solution

by:
ozo earned 125 total points
ID: 17875130
float arrMarkov[MAXROW+1][MAXCOL+1];
0
 
LVL 84

Expert Comment

by:ozo
ID: 17875145
#define MAXROW  4
#define MAXCOL 4
float arrMarkov[MAXROW+1][MAXCOL+1];
0
 
LVL 8

Author Comment

by:deadite
ID: 17875267
ozo,

that worked!  The only question I have is why?  Shouldn't C array elements start at 0, so declaring an array[4] should have the elements array[0] [1] [2] [3] [4] right?
Thanks
0
Is Your Active Directory as Secure as You Think?

More than 75% of all records are compromised because of the loss or theft of a privileged credential. Experts have been exploring Active Directory infrastructure to identify key threats and establish best practices for keeping data safe. Attend this month’s webinar to learn more.

 
LVL 13

Expert Comment

by:marchent
ID: 17875362
>>elements array[0] [1] [2] [3] [4] right?
no, it should be
elements array[0] [1] [2] [3]

~marchent~
0
 
LVL 1

Assisted Solution

by:Mathematix
Mathematix earned 80 total points
ID: 17875485
The problems causing the memory exceptions to be raised are your conditionals and declarations. Remember that arrays are zero-indexed, so if you declare:

int MAXROW = 4;
int MAXCOL = 4;
float arrMarkov[MAXROW][MAXCOL];

you have declared a 4x4 2D array (or 'matrix' as you prefer to call it), and the first element is

arrMarkov[0][0];

and the last

arrMarkov[4][4];

A quick lesson in inequalities. I don't know how well versed you are in mathematix, but you should be aware of the following for inequalities:

< has the logical opposite >= and vice-versa.
> has the logical opposite <= and vice-versa.
= has the logical opposite != and vice-versa.

These are simple rules that are critical when evaluating logical expressions in programming. Your first error is:

for (row = 0; row <= MAXROW; row++)

From the rules above I am sure that you can already see the error, since = is not the logical opposite of <=. This means that the expression will only evaluate false at MAXROW + 1 which is two elements out of the array boundaries. In fact MAXROW + 1 will never be reached, as the expeption will be raised as soon as to try to access arrMarkov[5][n]. Why? Recall that arrays are zero-indexed so the index values are only allowed to fall in the following ranges (where 'r' is the row index and 'c' is the column index):

arrMarkov[0 <= r < MAXROW][0 <= c < MAXCOL];

That is, for your definition the index values should fall between 0 and 3 because MAXROW = 4 and MAXCOL = 4.

Your corrected for-loops should be:

for (row = 0; row < MAXROW; row++)  and
for (col = 0; col < MAXCOL; col++)

and given that you want a 5x5 matrix, you should amend your definitions of MAXCOL and MAXROW to the following:

#define MAXROW  5
#define MAXCOL 5

SOME NOTES ON PROGRAMMING PRACTICE
============================

------------------------------------------------------
The solution

for (row = 0; row < MAXROW; row++)  and
for (col = 0; col < MAXCOL; col++)

can also be expressed as

for (row = 0; row != MAXROW; row++)  and
for (col = 0; col != MAXCOL; col++)

As per my inequalies expressed earlier. Don't use the '!=' version! Why? Because '!=' is not equal to '<'. '!=' checkes against a single value, so if you are incrementing row or col by an odd value the '!=' version of the conditional will always evaluate true if both MAXCOL and MAXROW are 4. The '<' version will evaluate false when a value >= MAXROW or MAXCOL is encountered and exit the loop.

------------------------------------------------------

#define MAXROW  5
#define MAXCOL 5

This declaration is also very bad, since the preprocessor does not perform type checking. Change to:

const int MAXROW = 5;
const int MAXCOL = 5;

------------------------------------------------------

float arrMarkov[MAXROW+1][MAXCOL+1];

Avoid arithmentic as 'indexes' to arrays. Why?

1. Depending on the situation, performing arithmetic within array indices forces the compiler to create a temp variable, perform the arithmetic, then apply the temp variable's value to the index, then destroy the temp variable. This is inefficient and not necessary.

2. Array indices should always be checked before an array is indexed. Therefore if you perform arithmentic within an index you could end up with an out-of-bounds index that would avoid those horrible exceptions and hard to find bugs.

------------------------------------------------------

Change

printf("\n");

to

putchar('\n');

printf() should be used when you wish to print a string (that is, an array of type 'char' in C), and putchar() when you wish to send a single character to standard output.

------------------------------------------------------

I hope this clarifies matters. :)
0
 
LVL 8

Author Comment

by:deadite
ID: 17875783
DUH,

writing programs for 30+ hrs really does affect your mind!  I see exactly where my error was now.   Also, I had another typo up there in my explanation question... obviously there will not be a [4] element since the array is 0 indexed.  Thank you all for pointing out the obvious...
0
 
LVL 1

Expert Comment

by:Mathematix
ID: 17876758
> writing programs for 30+ hrs really does affect your mind!  I see exactly where my error was now.

Don't worry, mate. It happens. Glad you've worked it out. :)
0

Featured Post

Is Your Active Directory as Secure as You Think?

More than 75% of all records are compromised because of the loss or theft of a privileged credential. Experts have been exploring Active Directory infrastructure to identify key threats and establish best practices for keeping data safe. Attend this month’s webinar to learn more.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

RIA (Rich Internet Application) tools are interactive internet applications which have many of the characteristics of desktop applications. The RIA tools typically deliver output either by the way of a site-specific browser or via browser plug-in. T…
Displaying an arrayList in a listView using the default adapter is rarely the best solution. To get full control of your display data, and to be able to refresh it after editing, requires the use of a custom adapter.
An introduction to basic programming syntax in Java by creating a simple program. Viewers can follow the tutorial as they create their first class in Java. Definitions and explanations about each element are given to help prepare viewers for future …
In this seventh video of the Xpdf series, we discuss and demonstrate the PDFfonts utility, which lists all the fonts used in a PDF file. It does this via a command line interface, making it suitable for use in programs, scripts, batch files — any pl…

864 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

25 Experts available now in Live!

Get 1:1 Help Now