Handout: Lecture 4 In-Class Exercises¶
Today is all at the keyboard. Part A is integer arrays; Part B is strings
(arrays of char). These are the building blocks for HW1 - Build Your Own
String Library, released today - but none of them is an HW1 function. They drill
the underlying moves (walking to the '\0', char arithmetic, using a letter as an
index) so HW1 is a matter of combining tools you have already used.
Try each one yourself first; we will discuss in class, and the solutions are in a separate document afterward. Compile with warnings on:
Reminders that will keep you out of trouble today:
- Array indices run
0ton - 1. There is no bounds checking - stepping outside that range is undefined behavior. - A string is a
chararray ending in'\0'. Loop until you hit the'\0'; you do not need to know the length up front. - A
charis a small integer (ASCII):'A'is65,'a'is97, and they differ by32. You may use<stdio.h>, but solve the character logic yourself (no<ctype.h>) - that is the HW1 mindset.
Set up¶
Part A - Integer arrays¶
Exercise A1 - Largest and smallest¶
Read (or hard-code) an array of integers and print the largest and smallest value, found in a single pass.
- Stretch: also report the index at which the largest value occurs.Exercise A2 - A sum function (and an average)¶
Write a function that sums an integer array, then one that averages it.
int sum(int a[], int n); /* total of the n elements */
double average(int a[], int n); /* mean as a real number */
averageshould reusesum. Mind the Lecture 3 integer-division trap: to get a real average you must convert to floating point, e.g.(double) sum(a, n) / n.- Notice you must pass
nin: the function receives only a reference to where the array starts, with no way to recover the count fromaitself.
- Stretch: split this across
stats.c/stats.h/main.cand build it with aMakefile, the way we did in Lecture 2.
Part B - Strings¶
Exercise B1 - Count uppercase and lowercase¶
Read a word and count how many characters are uppercase letters and how many are lowercase letters.
- Read a single word with
scanf("%s", word);- it stops at the first space. - Walk the string until
'\0'. For each character, use the range testsc >= 'A' && c <= 'Z'andc >= 'a' && c <= 'z'.
- Stretch: also count digits (
c >= '0' && c <= '9') and "other" characters, and check that the four counts add up to the word length.
Exercise B2 - Redact the letters (modify in place)¶
Read a word and overwrite every letter with a #, leaving digits and
punctuation untouched, then print the result. The point is writing back into the
same array - word[i] = '#'; - while you walk it.
- Test for a letter with the two range checks from B1, joined by
||. - This is the in-place transform shape you will reuse all over HW1 (case conversion, the cipher): walk the string, decide per character, and assign back. Here the decision is trivial on purpose so you can focus on the mechanics.
- Test the awkward cases: a word of only punctuation and a word with no letters at all.
Stretch - take it further¶
These drill three moves HW1 leans on - using a letter as an array index, searching a string, and scanning an array for a maximum - without being HW1 functions themselves.
- Letter-frequency histogram. Read a word and count how many times each
letter
a-zappears, case-insensitively, using anint counts[26]indexed byc - 'a'. Print only the letters that actually occur. Thec - 'a'trick that turns a letter into a0..25index is exactly the mapping the HW1 cipher uses. - Find a character. Write
int index_of(char s[], char target)that returns the index of the first occurrence oftarget, or-1if it is not present. A plain walk that returns early - the search shape behind many string routines. - Most common letter. Extend exercise 1: after filling
counts, scan those 26 numbers (the way A1 scanned for a maximum) and report which letter appears most often.