COMP1911 23T2 Introduction to Programming
  1. Write a function to find the factorial of a given integer. Because factorial grows very quickly we want our result to be a long long.

    Use the function your wrote to write a program that prompts the user for a positive integer less than 45 (otherwise it will overflow our long long variable) and prints out the factorial of that number.

    Add error checking, so that if the user does not enter an integer the program prints "Invalid input" and exits. You should also print "Invalid input" and exit if the user enters a negative number or a number of 45 or more.

    Sample solution for factorialFunction.c
    
    #include <stdio.h>
    #include <stdlib.h>
    
    #define MAX 45
    
    //Note this will overflow for large n over 44
    long long factorial(int n);
    
    int main(void) {
        int num;
        printf("Welcome to Factorial Calculator\n");
        printf("Enter a positive integer less than %d: ", MAX);
        
        if(scanf("%d",&num) == 1 && num >= 0 && num < MAX){
            printf("%d! is %lld\n",num,factorial(num));
            return EXIT_SUCCESS;
        } else {
            printf("Invalid input\n");
            return EXIT_FAILURE;
        }   
    }
    
    //Note this will overflow for large n over 44
    long long factorial(int n){
        long long fact = 1;
        int i;
        
        i = 1;
        while (i <=n ){
            fact = fact * i;
            i = i + 1;
        }
        return fact;
    }
    
    
  2. Another student wrote the following code to read in a number and print out its reciprocal.
    // This program allows a user to enter a number
    // and prints out its reciprocal (ie. 1 divided by the number)
    
    void reciprocal(double x);
    
    int main(void){
    
        double x;
        printf("Enter a number ");
        
        scanf("%lf",&x);
        reciprocal(x);
        
        printf("The reciprocal is %lf\n",x);
        return EXIT_SUCCESS;
    }
    
    void reciprocal(double x){
        if ( x != 0 ){
            x = 1.0/x;
        }
    }
    

    However the function did not seem to work as intended and gave incorrect output as shown below

    Enter a number 3
    The reciprocal is 3.000000
    
    What is wrong with the code? How can we modify the code to make our function work as intended and in this case get
    Enter a number 3
    The reciprocal is 0.333333
    
    The main function passes a copy of its variable, x into the reciprocal function. So when the reciprocal function modifies x, it is modifying its own local copy, so any changes are lost when the function ends.

    We can modify the function to return the value it calculates to the main function.

    // This program allows a user to enter a number
    // and prints out its reciprocal (ie. 1 divided by the number)
    
    double reciprocal(double x);
    
    int main(void){
    
        double x;
        printf("Enter a number ");
        
        scanf("%lf",&x);
        x = reciprocal(x);
        
        printf("Reciprocal is %lf\n",x);
        return EXIT_SUCCESS;
    }
    
    double reciprocal(double x){
        double result;
        if ( x != 0 ){
            result = 1.0/x;
        }
        return result;
    }
    
    
  3. What is an array?
    An array is a collection of elements with the same data type. Each element is accessed providing the name of the array and an index. The index range is from 0 through to N-1, where N is the number of elements in the array. This is also known as zero-based indexing.
  4. Give an expression that sums the first and third element of an array called numbers?
    numbers[0] + numbers[2]
    Note third element is accessed using numbers[2] since C uses zero based indexing.
  5. If an array is declared as int numbers[20]; and your program assigns a value to each element in the array, what is the problem with the statement x = numbers[20]; ?
    Because arrays use zero-based indexing, accessing the element indexed 20 is accessing the 21st item in the array. This will access a value that is not within the boundaries of the array.

    Behaviour of a program that does this is undefined and it is possible, for example, that it will cause the program to terminate. Sometimes it will retrieve the value of another variable.

  6. How would you declare a variable squares to be an array of integers with 15 elements?
        int squares[15];
    

    Write a C code fragment to store, in each element of this array, the square of the index of that element, e.g., squares[5] would contain the value 25.

    Here is a complete program instead of a fragment.
    #include <stdio.h>
    
    #define ELEMENTS    15
    
    int main(void) {
        int squares[ELEMENTS];
        int i;
    
        // Fill the array with values
        // equal to the square of each index
        i = 0;
        while (i < ELEMENTS) {
            squares[i] = i * i;
            i = i + 1;
        }
        // Let's print the array to check
        i = 0;
        while (i < ELEMENTS) {
            printf("squares[%d] has the value %d\n", i, squares[i]);
            i = i + 1;
        }
        return 0;
    }
    
    
  7. This C code:
        int x;
        int a[6];
    
        x = 10;
        a[3 * 2] = 2 * 3 * 7;
        printf("%d\n", x);
    
    mysteriously printed 42. How could this happen when x is clearly assigned only the value 10?

    How can you easily detect such errors before they have mysterious effects?

    The C code assigns to 42 to a[6] an array element that does not exist.

    The result of this is undefined.

    In this case the value 42 has apparently been assigned to the variable x. Silently changing another variable is a common consequence of use of an an illegal array index. Subtler and more confusing behaviour are also quite possible.

    If you are using a CSE machine you can compile the program with dcc. It will give you a warning in this example and will

    produce a program which will stop immediately with a clear error message if an invalid array index is used. For example:

    
    dcc arrayExample.c
    arrayExample.c:8:5: warning: array index 6 is past the end of the array (which contains 6 elements) [-Warray-bounds]
        a[3 * 2] = 2 * 3 * 7;
        ^ ~~~~~
    arrayExample.c:5:5: note: array 'a' declared here
    EXPLANATION: Careful, on line 8 of `arrayExample.c`, it looks like you're trying to access location 6 of `a`, which doesn't exist; `a` isn't that long.
     Keep in mind that arrays are 0-indexed.
    
    
    If you decide to ignore the warnings and run the program anyway:
    ./a.out
    =================================================================
    
    
    arrayExample.c:8:5: runtime error: index 6 out of bounds for type 'int [6]'
    
    Execution stopped here in main() in arrayExample.c at line 8:
    
        x = 10;
    --> a[3 * 2] = 2 * 3 * 7;
        printf("%d\n", x);
        return 0;
    
    
    Values when execution stopped:
    
    a = {1633968431, 825193325, 829645615, 791753017, 1818391920, 1751081833}
    x = 10
    3 * 2 = 6
    a[3 * 2] = 795635060
    
    
    
  8. Write a C program which reads numbers until non-numeric data is entered and then prints the middle number.

    So if 9 numbers were entered the program should print the 5th number entered. And if 27 numbers were entered the program should print the 14th number entered.

    If an even number of numbers is entered there are two middle numbers, print the first of them.

    For example if 8 numbers are entered, prints the 4th.

    You can assume at most 10,000 numbers will be entered.

    Sample solution for middle.c
    #include <stdio.h>
    
    #define MAX_NUMBERS 100000
    
    int main(void) {
        int numbers[MAX_NUMBERS];
        int howMany, value, middleIndex;
        howMany = 0;
        while (howMany < MAX_NUMBERS && scanf("%d",&value) == 1) {
            numbers[howMany] = value;
            howMany = howMany + 1;    
        }
        howMany = howMany - 1;
        middleIndex = howMany / 2;
        printf("%d\n", numbers[middleIndex]);
        return 0;
    }
    
    
    • Which Tim Tam rules potentially apply to this dice roll 6 6 6 6 6 6 and what scores do they produce.
      total: 6+6+6+6+6+6 = 36
      match-2: 2*6+19 = 31
      match-3: 3*6 + 21 = 39
      match-4: 4*6 + 23 = 47
      match-5: 5*6 + 25 = 55
      match-6: 6*6 + 27 = 63
      The actual output would be:
      Rule match-6(6) - score 63.
      
    • What about this dice roll 1 1 2 2 3 9
      total: 1 + 1 + 2 + 2 + 3 + 9 = 18
      match-2(1,1):  2*1 + 19 = 21
      match-2(2,2):  2*2 + 19 = 23
      sequence-2 (1,2): 2*2+17 = 21
      sequence-2 (2,3): 2*3+17 = 23
      sequence-3 (1,2,3): 3*3+18 = 27
      sum-2(1,1): 1 + 1 + 22 = 24
      sum-2(1,2): 1 + 3 + 22 = 26
      sum-5(1,1,2,2,3): 1 + 9 + 49 = 59
      The actual output would be:
      Rule sum-5(1+1+2+2+3=9) - score 59.
      
    • Assignment 1 has 20% marks based on style. What are some things you can do to get good marks for this?
      • Header comment
      • Consistent indentation
      • Good variable names
      • Appropriate use of #define
      • Use of arrays to store dice rolls etc
      • Use of while loops to access elements of arrays
      • Note: You will lose marks if you don't create and use at least one user defined function. Ideally you wil create more, but this is the minimum for this assignment, Each function should have a prototype above the main function and be implemented below the main function. You should have a comment before each function prototype exlaining the purpose and one before the function implementation that may add more detail about how the function was implemented. If the function is very simple, both comments may be the same.
      • If you don't create many functions and end up with a really long main, you will need to comment each section of code that performs a particular task.
  9. What would the following fragment of code print out
    int x,y;
    int numValuesRead = scanf("%d %d",&x,&y);
    printf("I read in %d values : x = %d y = %d\n",numValuesRead,x,y);
    
    with the following inputs
    1. 3 4 I read in 2 values: x = 3 y = 4
    2. three 4 I read in 0 values: x = 5748373443 y = 1828381
      Note: the value it prints out for x and y will be garbage values
    3. 3.1 4 I read in 1 values: x = 3 y = -463771
      Note: the value it prints out for y will be a garbage values
    4. ctrl^d I read in -1 values: x = -13241241 y = 12341324
      Note: the value it prints out for x and y will be garbage values
    5. 3
      ctrl^d I read in 1 values: x = 3 y = 12341324
      Note: the value it prints out for y will be a garbage value
  10. A student has written this program to read ints until the end-of-input. It counts how many numbers it reads categorized by their last digit: Consider the following code
    #include <stdio.h>
    
    #define N 10
    
    int main(void) {
        int digitCount[N];
        int x, lastDigit;
    
        while (scanf("%d", &x) == 1) {
            lastDigit = x % N;
            digitCount[lastDigit] = digitCount[lastDigit] + 1;
        }
    
        lastDigit = 0;
        while (lastDigit < N) {
            printf("%d numbers with last digit %d read\n", digitCount[lastDigit], lastDigit);
            lastDigit = lastDigit + 1;
        }
    
        return 0;
    }
    
    
    It works on the students laptop:
    gcc -Werror -Wall -O -o last_digit last_digit.c
    ./last_digit
    42 121 100 11
    <ctrl-d>
    1 numbers with last digit 0 read
    2 numbers with last digit 1 read
    1 numbers with last digit 2 read
    0 numbers with last digit 3 read
    0 numbers with last digit 4 read
    0 numbers with last digit 5 read
    0 numbers with last digit 6 read
    0 numbers with last digit 7 read
    0 numbers with last digit 8 read
    1 numbers with last digit 9 read
    
    
    print counts of how many numbers read with each possible last digit.

    But when run at uni fails

    dcc -o last_digit last_digit.c
    ./last_digit
    42 121 100 11
    <ctrl-d>
    778121076 numbers with last digit 0 read
    7632239 numbers with last digit 1 read
    -2032569224 numbers with last digit 2 read
    32727 numbers with last digit 3 read
    0 numbers with last digit 4 read
    0 numbers with last digit 5 read
    -2032409578 numbers with last digit 6 read
    32727 numbers with last digit 7 read
    -21600000 numbers with last digit 8 read
    32767 numbers with last digit 9 read
    
    
    Why doesn't the code work at uni .

    Why doesn't dcc detect an error?

    The student had not initialized array digitCount.

    Their program used values elements of digitCount which had not previously had values stored in them.

    This is illegal C and can hence produce *any* output.

    On the student's laptop by chance the bytes used for the array already had zeros in them. This is not uncommon and leads to illegal C seeming to be correct. But changing compiler flags, machine, or even time of day can affect this.

    dcc checks (among other things) that array indices are valid but doesn't check that array elements have been initialized.

    dcc --valgrind checks that array elements have been initialized (but not that indices are valid)

    The student's program can be fixed by adding a loop to initialize the elements of the array digitCount to 0.

    A less obvious problem is that entering a negative number will produce an (illegal) negative array index (also fixed below).

    Fix the code (make sure you understand how it works - its a common & useful programming pattern).

    Sample solution
    #include <stdio.h>
    
    #define N 10
    
    int main(void) {
        int digitCount[N];
        int x, lastDigit;
    
        lastDigit = 0;
        while (lastDigit < N) {
            digitCount[lastDigit] = 0;
            lastDigit = lastDigit + 1;
        }
    
        while (scanf("%d", &x) == 1) {
            lastDigit = x % N;
            if (lastDigit < 0) {
                lastDigit = - lastDigit;
            }
            digitCount[lastDigit] = digitCount[lastDigit] + 1;
        }
    
        lastDigit = 0;
        while (lastDigit < N) {
            printf("%d numbers with last digit %d read\n", digitCount[lastDigit], lastDigit);
            lastDigit = lastDigit + 1;
        }
    
        return 0;
    }
    
    
  11. Write a C program occur.c which reads 6 numbers then reads another number and prints how many times that number occurred in the first 6. For example:
    ./occur
    Enter 6 numbers: 1 3 1 3 1 9
    Enter a number: 1
    1 occurred 3 times in the 6 numbers read
    
    Make sure you make you make it very easy to change how many numbers the program reads. Note: For now let's do this without creating any functions.
    Sample solution for occur.c
    #include <stdio.h>
    
    #define N_NUMBERS 6
    
    int main(void) {
        int x[N_NUMBERS], i, j, match, count;
        printf("Enter %d numbers: ", N_NUMBERS);
        i = 0;
        while (i< N_NUMBERS) {
            scanf("%d", &x[i]);
            i = i + 1;
        }
        count = 0;
        printf("Enter a number: ");
        scanf("%d", &match);
        j = N_NUMBERS - 1;
        while (j >= 0) {
            if (x[j] == match) {
                count = count + 1;
            }
            j = j - 1;
        }
        printf("%d occurred %d times in the %d numbers read\n", match, count, N_NUMBERS);
        return 0;
    }
    
    
  12. Repeat the previous question, but break it down into functions. It should behave the same way.
    Sample solution for occurFunctions.c
    #include <stdio.h>
    
    #define N_NUMBERS 6
    
    void readData(int data[],int size);
    int findOccurrences(int data[], int size, int key);
    
    int main(void) {
        int x[N_NUMBERS], match, count;
       
        printf("Enter %d numbers: ", N_NUMBERS);
        readData(x,N_NUMBERS);
       
        printf("Enter a number: ");
        scanf("%d", &match);
        
        count = findOccurrences(x,N_NUMBERS,match);    
        printf("%d occurred %d times in the %d numbers read\n", match, count,
                                                                N_NUMBERS);
        return 0;
    }
    
    void readData(int data[],int size){
        int i = 0;
        while (i< size) {
            scanf("%d", &data[i]);
            i = i + 1;
        }
    }
    
    int findOccurrences(int data[], int size, int key){
        int count = 0;
        int j = size - 1;
        while (j >= 0) {
            if (data[j] == key) {
                count = count + 1;
            }
            j = j - 1;
        }
        return count;
    }
    
    
    
  13. Write a function with this prototype
    int arrayLength(int nums[])
    
    which returns the number of elements in the array nums.
    You can not write such a function in C.

    It is not possible for a C function to determine the length of an array it has been passed.

    Programmers usually do one of 3 things.

    1. Pass the array length as another parameter to the function.
    2. Pass an array of a specific length to the function - e.g. always pass arrays of 20 elements
    3. Use a special value in an array element to mark the finish of the array - e.g. '\0' for strings. (Note: we will see strings next week in lectures)
  14. Write a function with this prototype
    int testAllInitialised(int nums[], int size)
    
    which returns 1 if all elements of array nums are initialized, otherwise returns 0.
    You can not write such a function in C.

    It is not possible at runtime in C to determine if a variable has been initialized

    C programmers must take care to ensure that all variables, including array elements, are appropriately initialized.

  15. Write a function
    void sqrtIndex( double a[], int n )
    
    which takes an array a[] of n double values and sets each values to be the square root of their index.

    Hint: Use the math.h library function double sqrt(double) . How would you compile this if you were using gcc?

    Sample solution for sqrtIndex including a main function for testing.
    #include <stdio.h>
    #include <math.h>
    #define MAX_NUMBERS 100
    
    void sqrtIndex( double a[], int n );
    
    
    int main(void) {
        int i;
        double numbers[MAX_NUMBERS];
       
        sqrtIndex(numbers,MAX_NUMBERS);
    
        i = 0;
        while (i < MAX_NUMBERS) {
           printf("%lf ",numbers[i]);
           i = i + 1;
        }
        printf("\n");
        return 0;
    }
    
    
    
    void sqrtIndex( double a[], int n ) { 
      int i;
      
      i = 0;
      while( i < n ) {
        a[i] = sqrt(i);
        i = i + 1;
      }
      
    }
    
    
    
    You would compile with gcc using
    gcc -Wall -Werror -O -o sqrtIndex sqrtIndex.c -lm
    
    If you were using dcc you would compile as usual.
  16. Write a C function that returns 1 if an array of ints is in non-decreasing (ie increasing but potentially with duplicates) order, 0 otherwise,

    It should have this prototype:

    int nonDecreasing(double array[], int length)
    
    Sample solution for nonDecreasing that includes a main function for testing.
    #include <stdio.h>
    
    #define MAX_NUMBERS 100000
    
    int nonDecreasing(int array[], int length);
    
    int main(void) {
        int numbers[MAX_NUMBERS];
        int n_numbers, number_read;
    
        n_numbers = 0;
        number_read = 1;
        while (number_read == 1 && n_numbers < MAX_NUMBERS) {
            number_read = scanf("%d", &numbers[n_numbers]);
            n_numbers = n_numbers + 1;
        }
    
        if (nonDecreasing(numbers, n_numbers-1)) {
            printf("The numbers are in non-decreasing order\n");
        } else {
            printf("The numbers are not in non-decreasing order\n");
        }
        return 0;
    }
    
    int nonDecreasing(int array[], int length) {
      int i;
    
      i = 1;
      while (i < length) {
         if (array[i - 1] > array[i]) {
            return 0;
         }
         i = i + 1;
      }
    
      return 1;
    }
    
    
    
  17. Write a C function dotProduct, that calculates the dot-product of two vectors of integers. Assume it has the following prototype
    int dotProduct(int vector1[VECTOR_LENGTH], int vector2[VECTOR_LENGTH])
    

    Reminder you calculate the dot product by multiplying corresponding elements and summing the result. For example the dot product of vector 1,3,1,3,2 and 2,1,2,1,2 would be 14

    Sample solution for dotProduct.c.
    #include <stdio.h>
    
    #define VECTOR_LENGTH 10
    
    int dotProduct(int vector1[VECTOR_LENGTH], int vector2[VECTOR_LENGTH]);
    
    int main(void) {
        int vector1[VECTOR_LENGTH];
        int vector2[VECTOR_LENGTH];
        int i;
    
        printf("Enter vector 1 of %d positive numbers: ", VECTOR_LENGTH);
        i = 0;
        while (i < VECTOR_LENGTH) {
            scanf("%d", &vector1[i]);
            i = i + 1;
        }
    
        printf("Enter vector 2 of %d positive numbers: ", VECTOR_LENGTH);
        while (i < VECTOR_LENGTH) {
            scanf("%d", &vector2[i]);
            i = i + 1;
        }
    
    
        printf("Their dot-product is %d.\n", dot_product(vector1, vector2));
        return 0;
    }
    
    int dotProduct(int vector1[VECTOR_LENGTH], int vector2[VECTOR_LENGTH]) {
        int i, dotProduct;
    
        dotProduct = 0;
        i = 0;
        while (i < VECTOR_LENGTH) {
            dotProduct = dotProduct + vector1[i] * vector2[i];
            i = i + 1;
        }
    
        return dotProduct;
    }
    
    
    1. What is the effect of each of the following statements? What are the initial values in the arrays?
      int nums1[10];
      
      Creates an array of 10 integers without any initialisation. Each element will contain undefined values.
      int nums2[] = {0,1,2,3,4,5,6,7,8,9};
      
      Creates an array of 10 integers, and initialises the array with the given numbers.
      int nums3[10] = {0,2,4,6,8,-2};
      
      Creates an array of 10 integers, and initialises the first six elements with the given numbers and the rest with 0's.
      int nums4[10] = {0};
      
      Creates an array of 10 integers, and initialises the array with ten 0's
      int nums5[2][10] = {{0,1,2,3,4,5,6,7,8,9},
                          {10,20,30,40,50,60,70,80,90,100}};
      
      Creates a 2 dimensional array of size 2x10. You can think of it as having 2 rows and 10 columns. The array at nums5[0] contains 0,1,2,3,4,5,6,7,8,9. The array at nums5[1] contains 10,20,30,40,50,60,70,80,90,100
       int nums6[][10] = {{0},{9},{1}};
      
      Creates a 2 dimensional array of size 3x10. You can think of it as having 3 rows and 10 columns. The array at nums6[0] contains 0,0,0,0,0,0,0,0,0,0. The array at nums6[1] contains 9,0,0,0,0,0,0,0,0,0. The array at nums6[2] contains 1,0,0,0,0,0,0,0,0,0.
  18. What would the output of the following fragment of code be - given the array definitions above?
    int i;
    printf("%d\n",nums2[3]);  prints 3
    printf("%d\n",nums3[5]);  prints -2
    printf("%d\n",nums5[0][1]);  prints 1
    printf("%d\n",nums5[1][0]);  prints 10
    nums1[0] = nums2[1] + 10 ;
    printf("%d\n",nums1[0]);     prints 11
    i = 0;
    printf("%d\n",nums1[i]);     prints 11
    
  19. What is wrong with the following piece of code - given the above array definitions?
    printf("%d\n",nums2[10]);    This is an error.
    The indexes in nums2 go from 0..9.
    By using an index of 10 we are trying to go past the end of the array
    printf("%d\n",nums5[2][0]); This is an error.
    The first index in nums5 goes from 0..1.
    By using an index of 2 we are trying to go past the end of the array
    printf("%d\n",nums5[1][10]); This is an error.
    The second index in nums5 goes from 0..9.
    By using index of 10 we are trying to go past the end of the array
    
  20. How many ints can the array matrix below hold?
    #include <stdio.h>
    
    #define N_ROWS 12
    #define N_COLUMNS 15
    
    int main(void) {
        int matrix[N_ROWS][N_COLUMNS];
    
    The array can hold 12*15 = 180 ints
    Write a function with the following prototype
    void initialiseMatrix(int matrix[N_ROWS][N_COLUMNS]);
    
    that uses nested while loops to set every element of matrix. Each element should be set to the product of its two indices.

    Write a function with the following prototype

    void printMatrix(int matrix[N_ROWS][N_COLUMNS]);
    
    that uses nested while loops to print the elements of matrix plus sums of each row and sums of each column.

    Write a main program that uses these functions

    The output of your code should look like this:

    ./a.out
        0    0    0    0    0    0    0    0    0    0    0    0    0    0    0 |    0  
        0    1    2    3    4    5    6    7    8    9   10   11   12   13   14 |  105
        0    2    4    6    8   10   12   14   16   18   20   22   24   26   28 |  210
        0    3    6    9   12   15   18   21   24   27   30   33   36   39   42 |  315
        0    4    8   12   16   20   24   28   32   36   40   44   48   52   56 |  420
        0    5   10   15   20   25   30   35   40   45   50   55   60   65   70 |  525
        0    6   12   18   24   30   36   42   48   54   60   66   72   78   84 |  630
        0    7   14   21   28   35   42   49   56   63   70   77   84   91   98 |  735
        0    8   16   24   32   40   48   56   64   72   80   88   96  104  112 |  840
        0    9   18   27   36   45   54   63   72   81   90   99  108  117  126 |  945
        0   10   20   30   40   50   60   70   80   90  100  110  120  130  140 | 1050
        0   11   22   33   44   55   66   77   88   99  110  121  132  143  154 | 1155
    ---------------------------------------------------------------------------
        0   66  132  198  264  330  396  462  528  594  660  726  792  858  924
    
  21. In lectures we wrote the following code but we only wrote code to check that all rows added up to the magic number. Complete the code to check the columns and the two major diagonals as well.
    // Read  SIZE x SIZE numbers and test if
    // they form a magic square http://en.wikipedia.org/wiki/Magic_square
    //
    //
    // Andrew Taylor - andrewt@cse.unsw.edu.au
    // 10/4/13
    
    /*
    //  Lo Shu Square
    // 4  9  2
    // 3  5  7
    // 8  1  6
    //
    // Magic square of primes
    //  17  89  71
    // 113  59   5
    //  47  29 101
    */
    
    #include <stdio.h>
    
    #define SIZE 3
    
    void readSquare(int square[SIZE][SIZE]);
    void printSquare(int square[SIZE][SIZE]);
    int sumFirstRow(int square[SIZE][SIZE]);
    int checkMagic(int square[SIZE][SIZE], int magicValue);
    
    int main(void) {
        int square[SIZE][SIZE];
        int row,col;
        int magicValue;
        int isMagic = 1;
        
        // read potential magic square
        printf("Enter %d numbers please:\n", SIZE*SIZE);
        readSquare(square);
        
        // print potential magic square
        printf("Numbers are:\n");
        printSquare(square);
        
        // Find magic value
        magicValue = sumFirstRow(square);
        
        
        isMagic = checkMagic(square,magicValue);
       
        
        if(isMagic == 1){
            printf("It is magic\n");
        } else {
            printf("It is NOT magic\n");
        }
        return 0;
    }
    
    
    void readSquare(int square[SIZE][SIZE]){
        int row,col;
        row = 0;
        while(row < SIZE){
            col = 0;
            while(col < SIZE){
                 scanf("%d",&square[row][col]);
                 col = col + 1;
            }    
            row = row + 1;
        }
    
    }
    
    void printSquare(int square[SIZE][SIZE]){
        int row,col;
        row = 0;
        while(row < SIZE){
            col = 0;
            while(col < SIZE){
                 printf("%d ",square[row][col]);
                 col = col + 1;
            }   
            printf("\n"); 
            row = row + 1;
        }
    
    }
    
    int sumFirstRow(int square[SIZE][SIZE]){
        int col;
        int sum = 0;
        
        col = 0;
        while(col < SIZE){
           sum = sum + square[0][col];
           col  = col + 1;
        }
        return sum;
    }
    
    
    int checkMagic(int square[SIZE][SIZE], int magicValue){
        int row,col;
        int isMagic = 1;
        int sumRow;
       
        //Check all other rows. We have already checked the first.
        row = 1;
        while(row < SIZE){
            //check the sum of the row
            col = 0;
            sumRow = 0;
            while(col < SIZE){
               sumRow = sumRow + square[row][col];
               col = col + 1;
            }
            if(sumRow != magicValue){
               isMagic = 0;
            }
            row = row + 1;
        }
        return isMagic;
    }
    
    
    Sample solutions for magic_square.c including a main function for testing and a few different implementations of checkMagic.
    // Read  SIZE x SIZE numbers and test if
    // they form a magic square http://en.wikipedia.org/wiki/Magic_square
    //
    //
    // Andrew Taylor - andrewt@cse.unsw.edu.au
    // 10/4/13
    
    /*
    //  Lo Shu Square
    // 4  9  2
    // 3  5  7
    // 8  1  6
    //
    // Magic square of primes
    //  17  89  71
    // 113  59   5
    //  47  29 101
    
    //If you change SIZE to 12 it should work for 
    1  120  121  48  85  72  73  60  97  24  25  144
    142  27  22  99  58  75  70  87  46  123  118  3
    11  110  131  38  95  62  83  50  107  14  35  134
    136  33  16  105  52  81  64  93  40  129  112  9
    8  113  128  41  92  65  80  53  104  17  32  137
    138  31  18  103  54  79  66  91  42  127  114  7
    5  116  125  44  89  68  77  56  101  20  29  140
    139  30  19  102  55  78  67  90  43  126  115  6
    12  109  132  37  96  61  84  49  108  13  36  133
    135  34  15  106  51  82  63  94  39  130  111  10
    2  119  122  47  86  71  74  59  98  23  26  143
    141  28  21  100  57  76  69  88  45  124  117  4
    
    */
    
    #include <stdio.h>
    
    #define SIZE 3
    
    void readSquare(int square[SIZE][SIZE]);
    void printSquare(int square[SIZE][SIZE]);
    int sumFirstRow(int square[SIZE][SIZE]);
    int checkMagic(int square[SIZE][SIZE], int magicValue);
    
    int main(void) {
        int square[SIZE][SIZE];
        int row,col;
        int magicValue;
        int isMagic = 1;
        
        // read potential magic square
        printf("Enter %d numbers please:\n", SIZE*SIZE);
        readSquare(square);
        
        // print potential magic square
        printf("Numbers are:\n");
        printSquare(square);
        
        // Find magic value
        magicValue = sumFirstRow(square);
        
        
        isMagic = checkMagic(square,magicValue);
       
        
        if(isMagic == 1){
            printf("It is magic\n");
        } else {
            printf("It is NOT magic\n");
        }
        return 0;
    }
    
    
    void readSquare(int square[SIZE][SIZE]){
        int row,col;
        row = 0;
        while(row < SIZE){
            col = 0;
            while(col < SIZE){
                 scanf("%d",&square[row][col]);
                 col = col + 1;
            }    
            row = row + 1;
        }
    
    }
    
    void printSquare(int square[SIZE][SIZE]){
        int row,col;
        row = 0;
        while(row < SIZE){
            col = 0;
            while(col < SIZE){
                 printf("%d ",square[row][col]);
                 col = col + 1;
            }   
            printf("\n"); 
            row = row + 1;
        }
    
    }
    
    int sumFirstRow(int square[SIZE][SIZE]){
        int col;
        int sum = 0;
        
        col = 0;
        while(col < SIZE){
           sum = sum + square[0][col];
           col  = col + 1;
        }
        return sum;
    }
    
    //This could be broken down into smaller functions
    //or done with less loops.
    int checkMagic(int square[SIZE][SIZE], int magicValue){
        int row,col,i;
        int isMagic = 1;
        int sum;
       
        //Check all other rows. We have already checked the first.
        row = 1;
        while(row < SIZE){
            //check the sum of the row
            col = 0;
            sum = 0;
            while(col < SIZE){
               sum = sum + square[row][col];
               col = col + 1;
            }
            if(sum != magicValue){
               isMagic = 0;
            }
            row = row + 1;
        }
        
        //Check columns
        col = 0;
        while (col < SIZE) {
            sum = 0;
            row = 0;
            while (row < SIZE) {
                sum = sum + square[row][col];
                row = row + 1;
            }
            if (sum != magicValue) {
                isMagic = 0;
            }
            col = col + 1;
        }
        
        //Check diagonals
        sum = 0;
        i = 0;  
        while ( i < SIZE ) {
            sum = sum + square[i][i];    
            i = i + 1;
        }
        
        if (sum != magicValue) {
            isMagic = 0;
        }
        
        sum = 0;
        i = 0;
        while ( i < SIZE ) {
            sum = sum + square[SIZE-i-1][i];      
            i = i + 1;
        }
        
        if (sum != magicValue) {
            isMagic = 0;
        }
        
        return isMagic;
    }
    
    
    // This version is broken down into more functions
    // Read  SIZE x SIZE numbers and test if
    // they form a magic square http://en.wikipedia.org/wiki/Magic_square
    //
    //
    // Andrew Taylor - andrewt@cse.unsw.edu.au
    // 10/4/13
    
    /*
    //  Lo Shu Square
    // 4  9  2
    // 3  5  7
    // 8  1  6
    //
    // Magic square of primes
    //  17  89  71
    // 113  59   5
    //  47  29 101
    
    //If you change SIZE to 12 it should work for 
    1  120  121  48  85  72  73  60  97  24  25  144
    142  27  22  99  58  75  70  87  46  123  118  3
    11  110  131  38  95  62  83  50  107  14  35  134
    136  33  16  105  52  81  64  93  40  129  112  9
    8  113  128  41  92  65  80  53  104  17  32  137
    138  31  18  103  54  79  66  91  42  127  114  7
    5  116  125  44  89  68  77  56  101  20  29  140
    139  30  19  102  55  78  67  90  43  126  115  6
    12  109  132  37  96  61  84  49  108  13  36  133
    135  34  15  106  51  82  63  94  39  130  111  10
    2  119  122  47  86  71  74  59  98  23  26  143
    141  28  21  100  57  76  69  88  45  124  117  4
    
    */
    
    #include <stdio.h>
    
    #define SIZE 3
    
    void readSquare(int square[SIZE][SIZE]);
    void printSquare(int square[SIZE][SIZE]);
    int sumFirstRow(int square[SIZE][SIZE]);
    int checkMagic(int square[SIZE][SIZE], int magicValue);
    int checkRows(int square[SIZE][SIZE], int magicValue);
    int checkCols(int square[SIZE][SIZE], int magicValue);
    int checkDiagonals(int square[SIZE][SIZE], int magicValue);
    
    int main(void) {
        int square[SIZE][SIZE];
        int row,col;
        int magicValue;
        int isMagic = 1;
        
        // read potential magic square
        printf("Enter %d numbers please:\n", SIZE*SIZE);
        readSquare(square);
        
        // print potential magic square
        printf("Numbers are:\n");
        printSquare(square);
        
        // Find magic value
        magicValue = sumFirstRow(square);
        
        
        isMagic = checkMagic(square,magicValue);
       
        
        if(isMagic == 1){
            printf("It is magic\n");
        } else {
            printf("It is NOT magic\n");
        }
        return 0;
    }
    
    
    void readSquare(int square[SIZE][SIZE]){
        int row,col;
        row = 0;
        while(row < SIZE){
            col = 0;
            while(col < SIZE){
                 scanf("%d",&square[row][col]);
                 col = col + 1;
            }    
            row = row + 1;
        }
    
    }
    
    void printSquare(int square[SIZE][SIZE]){
        int row,col;
        row = 0;
        while(row < SIZE){
            col = 0;
            while(col < SIZE){
                 printf("%d ",square[row][col]);
                 col = col + 1;
            }   
            printf("\n"); 
            row = row + 1;
        }
    
    }
    
    int sumFirstRow(int square[SIZE][SIZE]){
        int col;
        int sum = 0;
        
        col = 0;
        while(col < SIZE){
           sum = sum + square[0][col];
           col  = col + 1;
        }
        return sum;
    }
    
    int checkMagic(int square[SIZE][SIZE], int magicValue){
         
       return checkRows(square,magicValue) && checkCols(square,magicValue) &&
              checkDiagonals(square,magicValue);
    }
    
    
    int checkRows(int square[SIZE][SIZE], int magicValue){
        int row,col;
        int isMagic = 1;
        int sum;
        //Check all other rows. We have already checked the first.
        row = 1;
        while(row < SIZE){
            //check the sum of the row
            col = 0;
            sum = 0;
            while(col < SIZE){
               sum = sum + square[row][col];
               col = col + 1;
            }
            if(sum != magicValue){
               isMagic = 0;
            }
            row = row + 1;
        }
        return isMagic;
    
    }
    
    int checkCols(int square[SIZE][SIZE], int magicValue){
        int row,col;
        int sum;
        int isMagic = 1;
        col = 0;
        while (col < SIZE) {
            sum = 0;
            row = 0;
            while (row < SIZE) {
                sum = sum + square[row][col];
                row = row + 1;
            }
            if (sum != magicValue) {
                isMagic = 0;
            }
            col = col + 1;
        }
        return isMagic;
    }
    
    int checkDiagonals(int square[SIZE][SIZE], int magicValue){
        int i;
        int sum;
        int isMagic = 1;
        sum = 0;
        i = 0;  
        while ( i < SIZE ) {
            sum = sum + square[i][i];    
            i = i + 1;
        }
        
        if (sum != magicValue) {
            isMagic = 0;
        }
        
        //Check other diagonal
        sum = 0;
        i = 0;
        while ( i < SIZE ) {
            sum = sum + square[SIZE-i-1][i];      
            i = i + 1;
        }
        
        if (sum != magicValue) {
            isMagic = 0;
        }
        return isMagic;
    }
    
    
    // This version restructured to use less while loops but
    // may be harder for a beginner to read
    // Read  SIZE x SIZE numbers and test if
    // they form a magic square http://en.wikipedia.org/wiki/Magic_square
    //
    //
    // Andrew Taylor - andrewt@cse.unsw.edu.au
    // 10/4/13
    
    /*
    //  Lo Shu Square
    // 4  9  2
    // 3  5  7
    // 8  1  6
    //
    // Magic square of primes
    //  17  89  71
    // 113  59   5
    //  47  29 101
    
    //If you change SIZE to 12 it should work for 
    1  120  121  48  85  72  73  60  97  24  25  144
    142  27  22  99  58  75  70  87  46  123  118  3
    11  110  131  38  95  62  83  50  107  14  35  134
    136  33  16  105  52  81  64  93  40  129  112  9
    8  113  128  41  92  65  80  53  104  17  32  137
    138  31  18  103  54  79  66  91  42  127  114  7
    5  116  125  44  89  68  77  56  101  20  29  140
    139  30  19  102  55  78  67  90  43  126  115  6
    12  109  132  37  96  61  84  49  108  13  36  133
    135  34  15  106  51  82  63  94  39  130  111  10
    2  119  122  47  86  71  74  59  98  23  26  143
    141  28  21  100  57  76  69  88  45  124  117  4
    
    */
    
    #include <stdio.h>
    
    #define SIZE 3
    
    void readSquare(int square[SIZE][SIZE]);
    void printSquare(int square[SIZE][SIZE]);
    int sumFirstRow(int square[SIZE][SIZE]);
    int checkMagic(int square[SIZE][SIZE], int magicValue);
    
    int main(void) {
        int square[SIZE][SIZE];
        int row,col;
        int magicValue;
        int isMagic = 1;
        
        // read potential magic square
        printf("Enter %d numbers please:\n", SIZE*SIZE);
        readSquare(square);
        
        // print potential magic square
        printf("Numbers are:\n");
        printSquare(square);
        
        // Find magic value
        magicValue = sumFirstRow(square);
        
        
        isMagic = checkMagic(square,magicValue);
       
        
        if(isMagic == 1){
            printf("It is magic\n");
        } else {
            printf("It is NOT magic\n");
        }
        return 0;
    }
    
    
    void readSquare(int square[SIZE][SIZE]){
        int row,col;
        row = 0;
        while(row < SIZE){
            col = 0;
            while(col < SIZE){
                 scanf("%d",&square[row][col]);
                 col = col + 1;
            }    
            row = row + 1;
        }
    
    }
    
    void printSquare(int square[SIZE][SIZE]){
        int row,col;
        row = 0;
        while(row < SIZE){
            col = 0;
            while(col < SIZE){
                 printf("%d ",square[row][col]);
                 col = col + 1;
            }   
            printf("\n"); 
            row = row + 1;
        }
    
    }
    
    int sumFirstRow(int square[SIZE][SIZE]){
        int col;
        int sum = 0;
        
        col = 0;
        while(col < SIZE){
           sum = sum + square[0][col];
           col  = col + 1;
        }
        return sum;
    }
    
    //This is more efficient but maybe harder to understand
    int checkMagic(int square[SIZE][SIZE], int magicValue){
        int i,j;
        int sumRow ;
        int sumCol;
        int sumDiagonal =0;
        int sumDiagonal2 = 0;
        
        i = 0;
        while(i < SIZE){
            //check the sum of the row
            j = 0;
            sumRow = 0;
            sumCol = 0;
            while(j < SIZE){
               sumRow = sumRow + square[i][j];
               sumCol = sumCol + square[j][i];
               j = j + 1;
            }
            if(sumRow != magicValue || sumCol != magicValue ){
               return 0;
            }
            sumDiagonal = sumDiagonal + square[i][i];
            sumDiagonal2 = sumDiagonal2 + square[i][SIZE-i-1];
            i = i + 1;
        }
        
        if(sumDiagonal != magicValue || sumDiagonal2 != magicValue ){
            return 0;
        }    
        return 1;
    }