Importing functions from other c file without a header - c

My assignment is to create a program that essentially tests the library I created in another c file. My issue is how I go about calling the library without the header. The library program is:
/*
Program: statlib.c
A Statistical library consisting of the following
seven functions: mean, variance, standard deviation,
sort, minimum value median, and max value.
*/
#include <math.h>
/* Calculates the mean value of the data in the list */
double mean(int totnum, double data[]) {
double meanval, sum;
int i;
sum = 0.0;
for(i=0; i<totnum; i++) {
sum += data[i];
}
meanval = sum/totnum;
return meanval;
}
// Calculate the variance of the data in the list
double variance(int totnum, double data[]) {
double meanval, sum, var;
int i;
meanval = mean(totnum, data);
sum = 0.0;
for(i=0; i<totnum; i++){
sum += (data[i] - meanval)*(data[i] - meanval);
}
var = sum/(totnum-1);
return var;
}
/* Calculate the standard deviation of data in the list */
double stdDeviation(int totnum, double data[]) {
double var, std;
var = variance(totnum, data);
std = sqrt(var);
return std;
}
/* Sorts the array data in ascending order. */
void sort(int totnum, double data[]) {
int i, j;
double temp;
/* find the smallest value in the reaming part of the array
in each iteratio staring with data[i]. */
for(i = 0; i < totnum-1; i++) {
/* compare with data[i] with data[j], swap their values */
for(j = i+1; j < totnum; j++) {
/* when data[i] > data[j], swap their values */
if(data[i] > data[j]) {
temp = data[i];
data[i] = temp;
}
}
}
}
/* Calculates the min value of an array. */
double minValue(int totnum, double data[]) {
double minval;
int i;
/* start at the intial value */
minval = data[0];
for(i = 1; i < totnum; i++) {
if(data[i] < minval) {
minval = data[i];
}
return minval;
}
}
/* Calculate the median of an array. Must be sorted first using the sort
function.*/
double median(int totnum, double data[]) {
double medianval;
if(totnum % 2) {
medianval = data[totnum/2];
}
else {
medianval = (data[totnum/2 -1] + data[totnum/2]/2.0);
}
return medianval;
}
/* Returns the maximum value of an array. */
double maxValue(int totnum, double data[]) {
double maxval;
int i;
maxval = data[0];
for(i = 1; i < totnum; i++) {
if(data[i] > maxval) {
maxval = data[i];
}
}
return maxval;
}
The program that I'm using to test the first program is:
/*
Program: teststatlib.c
This program tests my statlib.c program in order to
verify whether or not it is in working order.
*/
#include <stdio.h>
/* add code from statlib.c */
#pragma importf <statlib.c>
/* Declare extern functions so that the can be used */
extern double mean(int totnum, double data[]);
//extern double variance(int totnum, double data[]);
//extern double stdDeviation(int totnum, double data[]);
//extern void sort(int totnum, double data[]);
//extern double minValue(int totnum, double data[]);
//extern double median(int totnum, double data[]);
//extern double maxValue(int totnum, double data[]);
int main() {
int input[] = {30,90,100,84,72,40,34,91,80,62};
int totnum = sizeof(input)/sizeof(double);
printf("The unsorted array is %d.", input);
printf("The mean is ");
mean(totnum, input);
}

I find your question confusing because you didn't state your problem very well. In fact you never asked a question. Maybe I can still be a little helpful.
A few things that you can fix:
sizeof(input) not sizeof(input[])
the second to last print line does not do what you want. If you remove the [] then it will compile and print the address of the array (which is not what I think you want). You probably want to print each element of the array and you should consider doing it in a for loop. What you have looks very python-esk, but is not how we do things in c.
in your last line, you call mean() as if you expect it print something. I think you want to combine the last two lines to printf("The mean is %f\n", mean(totnum,input));
input needs to be declared as an array of type double. (also, you'll need to change sizeof(int) to sizeof(double) in the line below that)
I managed to compile and run your program in linux with the command gcc teststatlib.c statlib.c. I don't recognize #pragma importf <statlib.c> and that makes me suspect you might be using a development environment that I'm not familiar with.

Related

Small Triangles, Large Triangles code not working

So, I had been trying to write the code for the Small Triangles, Large Triangles problem of C in Hackerrank. Before, I state what problem I'm facing, I'll attach the question-
I only wrote the sort_by_area, swap and area functions here. The rest of it was given and unchangeable. The code I've written is getting executed properly but the structures aren't getting sorted correctly. Here is the expected output & my output-
I just cannot figure out why it is getting such weirdly swapped. If anyone could help, would mean a lot.
My code is-
#include <stdlib.h>
#include <math.h>
struct triangle
{
int a;
int b;
int c;
};
typedef struct triangle triangle;
void sort_by_area(triangle* tr, int n) {
int i, j, swapped;
for (i = 0; i < n-1; i++)
{
swapped = 0;
for (j = 0; j < n-i-1; j++)
{
if (area(tr[j].a, tr[j].b, tr[j].c) > area(tr[j+1].a, tr[j+1].b, tr[j+1].c))
{
swap(&tr[j], &tr[j+1]);
swapped = 1;
}
}
if (swapped == 0)
break;
}
}
void swap(struct triangle **xp, struct triangle **yp)
{
struct triangle *temp = *xp;
*xp = *yp;
*yp = temp;
}
int area(int a, int b, int c){
int p=(a+b+c)/2;
int q=p*(p-a)*(p-b)*(p-c);
return sqrt(q);
}
int main()
{
int n;
scanf("%d", &n);
triangle *tr = malloc(n * sizeof(triangle));
for (int i = 0; i < n; i++) {
scanf("%d%d%d", &tr[i].a, &tr[i].b, &tr[i].c);
}
sort_by_area(tr, n);
for (int i = 0; i < n; i++) {
printf("%d %d %d\n", tr[i].a, tr[i].b, tr[i].c);
}
return 0;
}```
Enable all warnings
This quickly led to swap() swapping pointers and not data.
// Corrected - swap data
void swap(struct triangle *xp, struct triangle *yp) {
struct triangle temp = *xp;
*xp = *yp;
*yp = temp;
}
Function order
Move area(), swap() definitions before calling them.
Area
(int) sqrt(q) may return the same value for different qs.
Example: (int) sqrt(100), (int) sqrt(110), (int) sqrt(120)
All return 10. Sorting will not certainly sort according to area.
Simple return the square of the area. Mathematically, sorting by area squared same as area.
int area_squared(int a, int b, int c){
int p=(a+b+c)/2;
int q=p*(p-a)*(p-b)*(p-c);
// return sqrt(q);
return q;
}
Although one could code using double, let us stay with integers.
Watch out for a+b+c as odd as odd/2 forms a truncated quotient.
Perhaps return the square of the area, scaled each side by 2?
int area_squared2(int a, int b, int c){
a *= 2; b *= 2; c *= 2;
// a+b+c is certianly even
int p=(a+b+c)/2;
int q=p*(p-a)*(p-b)*(p-c);
return q;
}
A remaining concern is int overflow. Consider long long math.
long long area_squared2LL(int a, int b, int c){
long long aa = a * 2LL;
long long bb = b * 2LL;
long long cc = c * 2LL;
long long pp = (aa+bb+cc)/2;
long long qq = pp*(pp-aa)*(pp-bb)*(pp-cc);
return qq;
}
Tip: Allocate by referenced data, not type
Easier to code right, review and maintain.
// triangle *tr = malloc(n * sizeof(triangle));
triangle *tr = malloc(sizeof *tr * n);
if (tr == NULL) {
// use tr
...
free(tr);
tr = NULL;
}

Cannot find a Calculation of Flexible Statistics main code body

I have a code where It wants to read which operation it wants to do and then calculate the numbers using the operation. I have the library code and header but the main code, I don't know what to implement within the body. I have a skeleton code however I'm drawing a blank on what else I need to do.
If this helps, the operation I'm trying to achieve is:
./statistics mean 10 20 30
and the answer should be: 20.0
Library Header:
#ifndef MY_LIBRARY_H
#define MY_LIBRARY_H
float OP_MEAN(int size, float * values);
float OP_MAX(int size, float * values);
float OP_SD(int size, float * values);
#endif
Library Code:
float OP_MEAN(int size, float * values)
{
int i;
float sum = 0.0;
for(i = 0; i < size; i++)
{
sum += values[i];
}
return sum/n;
}
float OP_MAX(int size, float * values)
{
int i;
float maximum = 0.0;
for(i = 0; i < size; i++)
{
if (values[i] > maximum)
{
maximum = values[i];
}
}
return maximum;
}
float OP_SD(int size, float * values)
{
float mean = OP_MEAN(size, values);
float sum = 0.0, un_sqrt_sd = 0.0;
int i;
for(i = 0; i < size; i++)
{
sum += pow(double(values[i] - mean), double(2));
}
un_sqrt_sd = (float) sum / (size - 1);
return (float) sqrt(double(un_sqrt_sd));
}
Main Code:
#include <stdio.h>
#include "my_lib.h"
// define the operations as enum here
enum operations{
OP_MEAN
OP_MAX
OP_SD
};
int main(int argc, char ** argv){
//parse command line arguments
enum operations op;
// 1. find the operator
if (strcmp(argv[1], "max") ...){ // check with man strcmp
op = OP_MAX;
}...
// 2. define an array with the necessary size
// 3. load numbers using my_atoi()
float (*fp)(int size, float * values); // declared function pointer variable
// use a switch to set the function pointer
switch(op_var){
case(OP_MAX):
fp = ... // set the function pointer
}
// invoke the function pointer
float result = fp(size, array)
printf("%.1f\n", result);
return 0;
}

Question about pthread and multithreading

So I created a program that calculates matrix multiplication sequentially then records the time, then calculates matrix multiplication using any number of pthreads entered in the command line numberOfThreads. But regardless of how many threads I enter it still giving me the same time each time. I'm currently on i7 Macbook so I'm not sure if thats why adding more threads doesn't optimize the calculations or If I just don't have the correct program.
Heres the code:
/*Program to generate two square 2D arrays of random doubles and
time their multiplication.
Program utlizies pthreads to efficiently perform matrix Multiplication
Compile by: gcc -o mmult -O3 mmultHW6.c -lpthread
Run by: ./mmult 1000 2
*/
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <math.h>
#include <pthread.h>
#define TRUE 1
#define FALSE 0
#define BOOL int
typedef struct {
int threadId;
int start_row;
int end_row;
int start_col;
int end_col;
} BLOCK;
// function prototypes
double ** allocate2DArray(int rows, int columns);
void print2DArray(int rows, int columns, double ** array2D);
void generateRandom2DArray(int rows, int columns,
double min, double max, double ** random2DArray);
BOOL equal2DArrays(int rows, int columns, double ** array1, double ** array2,
double tolerance);
void matrixMultiplication(int rows1, int columns1, double ** array1,
int rows2, int columns2, double ** array2,
double ** product);
void matrixMultiplicationAlt(int rows1, int columns1, double ** array1,
int rows2, int columns2, double ** array2,
double ** product);
void * threadMMult(void * rank);
int numberOfThreads;
double ** A;
double ** B;
double ** C;
double ** C_alt;
int rows, columns;
int main(int argc, char ** argv) {
long i, startTime, endTime,seqTime, paralellTime;
BLOCK * blocksOfWork;
int errorCode;
double tolerence;
pthread_t * threadHandles;
if (argc !=3) {
printf("Usage: %s <# of rows><# of Threads>\n", argv[0]);
exit(-1);
} // end if
sscanf(argv[1], "%d", &rows);
sscanf(argv[1], "%d", &numberOfThreads);
columns = rows;
// seed the random number generator
srand( time(NULL) );
A = allocate2DArray(rows, columns);
B = allocate2DArray(rows, columns);
C = allocate2DArray(rows, columns);
C_alt = allocate2DArray(rows, columns);
generateRandom2DArray(rows, columns, -1.0, +1.0, A);
generateRandom2DArray(rows, columns, -1.0, +1.0, B);
printf("after initializing matrices\n");
time(&startTime);
matrixMultiplicationAlt(rows, columns, A, rows, columns, B, C_alt);
time(&endTime);
seqTime = endTime-startTime;
printf("Matrix Multiplication Alt. time = %ld\n",seqTime);
time(&startTime);
threadHandles = (pthread_t *) malloc(numberOfThreads*sizeof(pthread_t));
blocksOfWork = (BLOCK *) malloc(numberOfThreads*sizeof(BLOCK));
for(i=0; i < numberOfThreads; i++){
blocksOfWork[i].threadId = i;
blocksOfWork[i].start_row = i * rows/numberOfThreads;
if (i == numberOfThreads -1){
blocksOfWork[i].end_row = rows - 1;
}
else{
blocksOfWork[i].end_row = (i+1)*rows/numberOfThreads -1;
}
}
for (i=0; i < numberOfThreads; i++) {
if (errorCode = pthread_create(&threadHandles[i], NULL, threadMMult,
&blocksOfWork[i]) != 0) {
printf("pthread %d failed to be created with error code %d\n", i, errorCode);
} // end if
} // end for
for (i=0; i < numberOfThreads; i++) {
if (errorCode = pthread_join(threadHandles[i], (void **) NULL) != 0) {
printf("pthread %d failed to be joined with error code %d\n", i, errorCode);
} // end if
} // end for
time(&endTime);
paralellTime = endTime-startTime;
printf("Parallel Matrix Multiplication time = %ld\n",paralellTime);
if (equal2DArrays(rows, columns, C, C_alt, 0.000001)) {
printf("Arrays match with tolerance of %.000001f\n", 0.000001);
} else {
printf("Arrays DON'T match with tolerance of %.000001f\n", 0.000001);
} // end if
return 0;
} // end main
void * threadMMult(void * arg){
BLOCK * block = (BLOCK *) arg;
int threadId = block->threadId;
int startRow = block->start_row;
int endRow = block->end_row;
int i, j, k, sum;
for(i=startRow; i<=endRow;i++){
for(j = 0; j<rows;j++){
C[i][j] = 0;
for(k=0; k<rows ; k++){
C[i][j] += A[i][k]*B[k][j];
//printf("%lu - C[%d][%d] += A[%d][%d] * B[%d][%d]\n",
//pthread_self(), i,j,i,k,k,j);
}
}
return 0;
}
}
//C[i][j] += A[i][k] * B_transpose[j][k];
/*******************************************************************
* Function matrixMultiplicationAlt passed two matrices and returns
* their product.
********************************************************************/
void matrixMultiplicationAlt(int rows1, int columns1, double ** array1,
int rows2, int columns2, double ** array2,
double ** product) {
int i, j, k;
double ** array2_transpose;
if (columns1 != rows2) {
printf("Matrices cannot be multiplied -- incompatible dimensions!\n");
exit(-1);
} // end if
// Transposes array2
array2_transpose = allocate2DArray(columns2, rows2);
for (i=0; i < rows2; i++) {
for (j=0; j < columns2; j++) {
array2_transpose[j][i] = array2[i][j];
} /* end for (j */
} /* end for (i */
// Matrix Multiplication uses array1 and array2_transpose
for (i=0; i < rows1; i++) {
for (j=0; j < columns2; j++) {
C_alt[i][j] = 0.0;
for (k=0; k < columns1; k++) {
C_alt[i][j] += array1[i][k]*array2_transpose[j][k];
} /* end for (k */
} /* end for (j */
} /* end for (i */
} // end matrixMultiplicationAlt
/*******************************************************************
* Function allocate2DArray dynamically allocates a 2D array of
* size rows x columns, and returns it.
********************************************************************/
double ** allocate2DArray(int rows, int columns) {
double ** local2DArray;
int r;
local2DArray = (double **) malloc(sizeof(double *)*rows);
for (r=0; r < rows; r++) {
local2DArray[r] = (double *) malloc(sizeof(double)*columns);
} // end for
return local2DArray;
} // end allocate2DArray
/*******************************************************************
* Function generateRandom2DArray is passed the # rows, the # columns,
* min. value, max. value, and returns random2DArray containing
* randomly generated doubles.
********************************************************************/
void generateRandom2DArray(int rows, int columns,
double min, double max, double ** random2DArray) {
int r, c;
double range, div;
for (r = 0; r < rows; r++) {
for (c = 0; c < columns; c++) {
range = max - min;
div = RAND_MAX / range;
random2DArray[r][c] = min + (rand() / div);
} // end for (c...
} // end for (r...
} // end generateRandom2DArray
/*******************************************************************
* Function print2DArray is passed the # rows, # columns, and the
* array2D. It prints the 2D array to the screen.
********************************************************************/
void print2DArray(int rows, int columns, double ** array2D) {
int r, c;
for(r = 0; r < rows; r++) {
for (c = 0; c < columns; c++) {
printf("%10.5lf", array2D[r][c]);
} // end for (c...
printf("\n");
} // end for(r...
} // end print2DArray
/*******************************************************************
* Function equal2DArrays is passed the # rows, # columns, two
* array2Ds, and tolerance. It returns TRUE if corresponding array
* elements are equal within the specified tolerance; otherwise it
* returns FALSE.
********************************************************************/
BOOL equal2DArrays(int rows, int columns, double ** array1, double ** array2,
double tolerance) {
int r, c;
for(r = 0; r < rows; r++) {
for (c = 0; c < columns; c++) {
if (fabs(array1[r][c] - array2[r][c]) > tolerance) {
return FALSE;
} // end if
} // end for (c...
} // end for(r...
return TRUE;
} // end equal2DArray
This is a bit suspicious:
sscanf(argv[1], "%d", &rows);
sscanf(argv[1], "%d", &numberOfThreads);
I am not sure where you are with the learning C thing, but “man 3 getopt” should show a much better way to pass runtime parameters into your program than accidentally re-using argv[1]....
The second problem that you have created is using two different mechanisms for performing matrix multiplication; one for the sequential version, and a separate one for the parallel one. Logically, you should be able to have one, fully parameterized function to perform the operation, then the fact that M parallel threads are invoking it with different data is transparent to the function itself. Since you didn’t, you left a question mark: is the lack of scale because one of your matrix multiply functions doesn’t work correctly?
Looking at your code, I have little faith that it does; you have utilized a barrage of mechanisms to implement this. The core is:
Mult(double *A, int Ar, int Ac, double *B, int Br, int Bc, double C, int Cr, int Cc) {
/ multiply C = A * B */
}
and whether it is N threads converging on a solution, or one thread trudging through the solution, they should be able to execute the same code.

C the value of an array getting modified sent by pointer after a void function

I am currently trying to make moving average with C, and I want to send my address to the function and calculate the moving average inside the function. However, whenever I get out of the for loop inside the function, the pointer which was originally pointing at the initial array changes and I have no idea how to solve the problem. Here is my code:
include <stdio.h>
#include <stdlib.h>
#define n 10
void monAvg(const float *in, float *out, int m);
int main(int argc, char *argv[])
{
float table_in[]={1,2,3,4,5,5,4,3,2,1};
float table_out[]={0};
if (argc != 2) {
printf ("Incorrect number of program arguments");
return 0;
}
if (atof(argv[1]) < 1 || atof(argv[1]) > n)) {
printf ("Invalid program argument value");
return 0;
}
monAvg(table_in, table_out, atof(argv[1]));
return 0;
}
void monAvg(const float *in, float *out, int m) {
float temp;
int i,j;
for (i = 0; i < (n - m + 1); i++) {
temp = 0;
for (j = i; j < i + m; j++) {
temp += *(in + j);
}
*(out + i) = temp/m;
}
}
Thank you in advance.
The problem is that you have undefined behavior: your output array has one item allocated, so processing the input of size above 1 causes writes past the allocated segment of table_out.
You can fix this by sizing the array explicitly:
float table_out[sizeof(table_in)/sizeof(table_in[0])]={0};
Note: Expression sizeof(table_in)/sizeof(table_in[0]) computes the number of elements in table_in. You can use it in place of hard-coded n, which must be kept in sync with the count of table_in in order for your code to work correctly.

Code Bug: Segmentation Fault [EVERYTIME]

I am writing this C/C++ program that is suppose to find the mean, median, and mode of a varied size array. Although, I keep getting a Segmentation Fault regardless of the input. What is wrong with my code? Any suggestions always appreciated! :)
Here is the code:
#include <stdio.h>
//#include <string.h>
//#include <math.h>
#include <stdlib.h>
Prototypes:
void sort(double*[],int);
static int min(double,double[],int);
double mean(double[],int);
double median(double[],int);
double mode(double[],int);
int numberOf(double,double[],int);
Main Function:
int main() {
int i;
scanf(" %d ",&i); //10
double arr[i]; //array that contains all the values and will be sortted
for (int j=0; j<i; j++) { //64630 11735 14216 99233 14470 4978 73429 38120 51135 67060
scanf(" %lf ",&arr[j]);
}
printf("%.1lf\n%.1lf\n%.0lf",mean(arr,i),median(arr,i),mode(arr,i));
return 0;
}
Sort Function:
The end result should update the array arr from the call in the Median Function. Changes the used values in the original array to -1 until that is the entire array.
void sort(double* arr[],int l) {
double arr2[l];
for (int i=0; i<l; i++) {
int j;
if (i)
j = min(arr2[i-1], *arr, l);
else
j = min(0, *arr, l);
arr2[i] = *arr[j];
*arr[j] = -1;
}
for (int i=0; i<l; i++) {
*arr[i] = arr2[i];
}
}
Min Function (helper function for the Sort Function):
Finds the minimum value amongst the array elements that is greater than or equal to minLookingTo
Returns the position the value is in.
static int min(double minLookingTo,double arr[],int l) {
int minP;
double minA = minLookingTo;
for (int i=0; i<l; i++) {
if (arr[i] == -1)
continue;
if (minLookingTo<=arr[i] && arr[i]<=minA) {
minP = i;
minA = arr[i];
}
}
return minP;
}
Mean Function:
Returns the mean of the inputted array with the length l
double mean(double arr[],int l){
double total = 0;
for (int i=0; i<l; i++) {
total += arr[i];
}
return total/l;
}
Median Function:
Uses the Sort Function. Assuming that works, returns the median.
double median(double arr[],int l){
sort(&arr,l);
double d = arr[(l/2)+1];
double dd = arr[(l/2)];
if (l%2!=0)
return d;
return (d+dd)/2;
}
Mode Function:
Uses the NumberOf Function to determine the array element with the maximum amount of repeats. Returns the lowest value of the highest (equal) repeats.
double mode(double arr[],int l){
int maxA;
int maxP;
for (int i=0;i<l;i++) {
int j = numberOf(arr[i],arr,l);
if (j>maxA) {
maxA = j;
maxP = i;
}
else if (j==maxA && arr[maxP]>arr[i])
maxP = i;
}
double d = arr[maxP];
return d;
}
NumberOf Function:
Helper function for the Mode Function. Returns the amount of elements with the looking value.
int numberOf(double looking,double arr[],int l) {
int amount = 0;
for (int i=0; i<l; i++)
if (looking == arr[i])
amount++;
return amount;
}
I tracked your segmentation fault to your sort() routine called by median(). Rather than fix sort(), I substituted qsort() from the library to convince myself that's the problem:
// Median Function:
// Uses the Sort Function. Assuming that works, returns the median.
int comparator(const void *p, const void *q) {
double a = *((double *) p);
double b = *((double *) q);
return (a > b) - (a < b); // compare idiom
}
double median(double array[], int length) {
// sort(array, length);
qsort(array, length, sizeof(double), &comparator);
double d = array[length / 2];
if (length % 2 != 0) {
return d;
}
double dd = array[(length / 2) - 1];
return (d + dd) / 2;
}
For the example list of numbers provided, after correcting the rest of the code, this returns a median of 44627.5
Other fixes:
You're missing a final newline here:
printf("%.1lf\n%.1lf\n%.0lf",mean(arr,i),median(arr,i),mode(arr,i));
You should probably initialize the variables in mode():
double mode(double array[], int length) {
int maxA = INT_MIN;
int maxP = -1;
for (int i = 0; i < length; i++) {
int j = numberOf(array[i], array, length);
if (j > maxA) {
maxA = j;
maxP = i;
} else if (j == maxA && array[maxP] > array[i]) {
maxP = i;
}
}
return array[maxP];
}
Your code has a series of errors. Some of them:
You don´t need (in this case) to use spaces in scanf. This is causing a reading error.
You don't need to pass an array address to a function in order to alter its values. Arrays are always passed by reference. So change your function from void sort(double*[],int); to void sort(double[],int);, make the necessary corrections inside the function and call it using sort(arr,l); instead of sort(&arr,l);
Your min() function declares an uninitialized variable minP, so this variable contains garbage from your memory. The for() loop isn't entering none of the both if() conditions, so your function ends and returns the still uninitialized variable minP. This random value is then used to access an index in your array: j = min(0, arr, l); min returns an random number and then arr2[i] = arr[j]; accessing forbidden memory region, which is causing your segmentation fault error. The same problem is occurring with the variables maxP and maxA in the mode() function.
You must always be careful when accessing your arrays to not go beyond its bounds and always be sure that variables will be initialized when using them. And as others have commented, I also highly recommend you to learn how to debug your programs, since this will help you to analyze its execution and trace bugs.

Resources