C exercises: pointers, character arrays, I/O, and functions


These exercises are from exercise 10.3 on p. 424 and exercise 8.1 on p. 354, with minor modifications, of C How to Program (2nd ed.) by Dietel, H.M. & Dietel, P.J. (1988). Englewood Cliffs, NJ: Prentice Hall.

  1. Write a single statement or set of statements to accomplish each of the following:

    1. Define a structure called part containing an int variable partNumber, and char array partName whose values may be as long as 25 characters.

    2. Define Part to be a synonym for the type struct part.

    3. Use Part to declare variable a to be of type struct part, array b[10] to be of type struct part, and variable ptr to be of type pointer to struct part.

    4. Read a part number and a part name from the keyboard into the individual members of variable a.

    5. Assign the member values of variable a to element 3 of array b.

    6. Assign the address of array b to the pointer variable ptr.

    7. Print the members values of element 3 of array b to the display using the variable ptr and the structure pointer operator to refer to the members.


  2. Assume the following variables have been declared as shown.
    double number1 = 7.3, number2;
    char s1[100], s2[100];
    
    1. Declare the variable dPtr to be a pointer to a variable of type double.

    2. Assign the address of variable number1 to pointer variable dPtr.

    3. Print the value of the variable pointed to by dPtr to the display.

    4. Assign the value of the variable pointed to by dPtr to variable number2.

    5. Print the value of number2 to the display.

    6. Print the address of number1 to the display.

    7. Print the address stored in dPtr to the display.

    8. Is the value printed the equal to the address of number1?

    9. Copy the string stored in character array s1 into character array s2.

    10. Compare the string stored in character array s1 with the string in character array s2, and print the result to the display.

    11. Append the string in character array s2 to the string in character array s1. Will this cause a run-time error?

    12. Determine the length of the string stored in character array s1, and print the result to the display.
  3. These exercises are intended to test your use of structs, pointers, dynamic memory allocation and deallocation, functions and function pointers (as well as basic program I/O) to implement, use, and test basic data structures.

  4. Implement and demonstrate memory-safe use of a singly linked list as follows:
    1. Declare a struct that has two elements: an integer and a pointer to the same struct type.

    2. Use malloc to dynamically allocate four instances of that struct type and update their pointers to form a chain where each instance except for the last one points to the next one, and the last one points to nothing.

    3. Fill in the integer fields of those instances with four different values and then print out the instances integer values in order, from the beginning to the end of the list.

    4. Remove the second instance from the list, keeping the list intact (with the first element in the list now pointing to what used to be the third element in the list) and using free to dynamically deallocate the memory for the instance that you removed from the list, and then again print out the instances integer values in order, from the beginning to the end of the list, to confirm that the correct element was removed from the list.

  5. Write code to demonstrate various techniques for function invocation and use, as follows:

    1. Declare and define a function that takes an unsigned integer as its only input and returns a pointer to a dynamically allocated linked list (using the techniques from the exercises above) of all of the prime factors of that unsigned integer (for example: if the function was given 15 then the list should have two elements, a five and a three; if the function was given 12 then the list should have three elements, two twos and a three; if the function was given 0 or 1 then the list should be empty).

    2. Declare and define a function that takes a pointer to a dynamically allocated linked list (of the same type that the function from the previous exercise produces), prints out the integers in that list to the standard output stream, and then iterates through the list using free to dynamically deallocate the memory for each instance in the list.

    3. Write a program that takes a single command line argument, converts it into its equivalent unsigned integer representation (for example the string "11" should become the unsigned integer 11, the string "0" should become the unsigned integer 0, etc.), passes it into a call to the first function you implemented above, and then passes the pointer that was returned by that function into a call to the second function you implemented above - compile and run your program with different input values to confirm it can handle various cases correctly without crashing (e.g., due to problems with pointer initialization, memory management, etc.) and that it returns the correct values in each case.

    4. Declare function pointers of the appropriate types for each of the two functions your program uses, and reimplement your program using those pointers to invoke the functions instead of calling them directly - again compile and test your program to make sure it performs correctly (and produces the same outputs) as the original program did for each of your test cases.