Week 2 (Arrays)

Topics

  • Arrays
  • Strings
  • Command-Line Arguments

This week can also be an opportune time to introduce some practice with debugging, especially as via debug50. We’ve included some shorts below that might help serve as inspiration for introducing debug50, or for sharing with students directly.

Programming Exercises

Below are a few example programming exercises that engage students in hands-on practice on the week’s topics. Keep in mind that class might not be long enough to include all exercises, so be sure to pick just a few!

Less Comfortable

  • Character-by-Character
    • Write a program print.c that takes a string as input and prints it character-by-character.
    • Topics
      • Accessing characters in a string
      • Simple for loops
      • Format codes
      • Libraries and the CS50 Manual Pages
    • Modifications
      • Encourage students to print their string using the %c format code and the %i format code. Ask: How does this change what they see on the screen? Why?
    • Sample Usage
      $ ./print
      Input: Hello
      Hello
      
    • Sample Solution
      #include <cs50.h>
      #include <stdio.h>
      #include <string.h>
      
      int main(void)
      {
          string text = get_string("Input: ");
          int length = strlen(text);
          for (int i = 0; i < length; i++)
          {
              printf("%c", text[i]);
          }
          printf("\n");
      }
      
  • Reverse
    • Write a program reverse.c that takes a string as input, and reverses it.
    • Topics
      • Accessing characters in a string
      • Writing more complex for loops
    • Sample Usage
      $ ./reverse
      Text: This is CS50.
      Reverse: .05SC si sihT
      
    • Sample Solution
      #include <cs50.h>
      #include <ctype.h>
      #include <stdio.h>
      #include <string.h>
      
      int main(void)
      {
          string s = get_string("Text: ");
      
          // Loop through string in reverse order
          for (int i = strlen(s) - 1; i >= 0; i--)
          {
              printf("%c", s[i]);
          }
      
          printf("\n");
      }
      
  • Alphabetical
    • Write a program alphabetical.c that prints “Yes” if a lowercase string’s characters are in alphabetical order, and “No” if they are not.
    • Topics
      • ASCII values
      • Character comparison
      • for loops
      • return and return values
    • Sample Usage
      $ ./alphabetical
      Input: abcdefg
      Yes
      
      $ ./alphabetical
      Input: gfedcba
      No
      
    • Sample Solution
      #include <cs50.h>
      #include <stdio.h>
      #include <string.h>
      
      int main(void)
      {
          string text = get_string("Input: ");
          int length = strlen(text);
      
          for (int i = 1; i < length; i++)
          {
              if (text[i] < text[i - 1])
              {
                  printf("No\n");
                  return 0;
              }
          }
          printf("Yes\n");
      }
      
  • Addition
    • Write a program addition.c that adds two numbers provided as command-line arguments.
    • Details
      • The program should accept two integers as command-line arguments.
      • The program should output both original numbers, and their sum. If the program is run as ./additional 2 8, for example, the output should be 2 + 8 = 10.
      • If the incorrect number of command-line arguments is provided, the program should display an error and return with exit code 1.
    • Topics
      • Exit codes
      • Command-line arguments
      • atoi to convert strings to integers.
    • Sample Usage
      $ ./addition 2 8
      2 + 8 = 10
      
      $ ./addition 2
      Usage: ./addition x y
      
    • Sample Solution
      #include <cs50.h>
      #include <stdio.h>
      #include <stdlib.h>
      
      int main(int argc, string argv[])
      {
          if (argc != 3)
          {
              printf("Usage: ./addition x y\n");
              return 1;
          }
      
          int x = atoi(argv[1]);
          int y = atoi(argv[2]);
      
          printf("%i + %i = %i\n", x, y, x + y);
      
      }
      
  • Palindrome
    • Write a program palindrome.c that takes a string as input, and determines whether it is a palindrome (the same backwards and forwards). This can often be a useful follow-up to reverse.c.
    • Details
      • (A more-comfortable student variant on this problem is to detect palindromes while ignoring spaces, to identify palindromes like taco cat.)
    • Topics
      • String manipulation
      • for loops
    • Sample Usage
      $ ./palindrome
      Text: racecar
      PALINDROME
      
      $ ./palindrome
      Text: jellyfish
      NOT PALINDROME
      
    • Sample Solution
      #include <cs50.h>
      #include <ctype.h>
      #include <stdio.h>
      #include <string.h>
      
      int main(void)
      {
          string s = get_string("Text: ");
      
          bool palindrome = true;
      
          // Check characters from start and end
          for (int i = 0, len = strlen(s); i < len / 2; i++)
          {
              if (s[i] != s[len - 1 - i])
              {
                  palindrome = false;
              }
          }
      
          // Print output
          if (palindrome)
          {
              printf("PALINDROME\n");
          }
          else
          {
              printf("NOT PALINDROME\n");
          }
      
      }
      
  • Initials
    • Write a program initials.c that takes a user’s full name as input, and outputs their initials.
    • Details
      • The program should accept a user’s name using get_string
      • Initials should all be printed as uppercase letters, even if the name contains lowercase letters
      • Students can assume that the user’s names will be separated by one space
    • Topics
      • Combining loops and conditions
      • Accessing string characters and manipulating strings
      • Using ctype.h functions like toupper
    • Sample Usage
      $ ./initials
      Name: David J. Malan
      DJM
      
    • Sample Solution
      #include <cs50.h>
      #include <ctype.h>
      #include <stdio.h>
      #include <string.h>
      
      int main(void)
      {
          string name = get_string("Name: ");
      
          // Keep track of whether to output next character
          bool output = true;
      
          // Loop over all characters in name
          for (int i = 0, len = strlen(name); i < len; i++)
          {
              // Check if we should output this character
              if (output == true)
              {
                  printf("%c", toupper(name[i]));
                  output = false;
              }
      
              // If we encounter a space, output the next character
              if (name[i] == ' ')
              {
                  output = true;
              }
          }
      
          printf("\n");
      }
      

More Comfortable

  • Anagram
    • This problem is a more comfortable problem, and works best when students already have familiarity with arrays and strings.
    • Write a program anagram.c that takes two words as input, and determines whether the words are anagrams of one another.
    • Details
      • If two words are an exact match (the strings are identical, ignoring case), the program should output EXACT MATCH.
      • If either word contains non-alphabetic characters, the program should output Alphabetic characters only and return 1.
      • Otherwise, if two words consist of only alphabetic characters, the program should check to see if the letters in the first word can be rearranged (ignoring case) to form the second word. If so, the program should print ANAGRAM; if not, the program should print NOT ANAGRAM.
    • Sample Usage
      $ ./anagram
      Word 1: listen
      Word 2: silent
      ANAGRAM
      
      $ ./anagram
      Word 1: program
      Word 2: silent
      NOT ANAGRAM
      
      $ ./anagram
      Word 1: program
      Word 2: program
      EXACT MATCH
      
      $ ./anagram
      Word 1: this
      Word 2: cs50
      Alphabetic characters only.
      
    • Sample Solution
      #include <ctype.h>
      #include <cs50.h>
      #include <stdio.h>
      #include <string.h>
      #include <strings.h>
      
      #define ALPHASIZE 26
      
      int main(void)
      {
          string s1 = get_string("Word 1: ");
          string s2 = get_string("Word 2: ");
      
          if (!strcasecmp(s1, s2))
          {
              printf("EXACT MATCH\n");
              return 0;
          }
      
          int characters[ALPHASIZE] = {0};
      
          for (int i = 0, len = strlen(s1); i < len; i++)
          {
              if (isalpha(s1[i]))
              {
                  characters[tolower(s1[i]) - 'a']++;
              }
              else
              {
                  printf("Alphabetic characters only.");
                  return 1;
              }
          }
      
          for (int i = 0, len = strlen(s2); i < len; i++)
          {
              if (isalpha(s2[i]))
              {
                  characters[tolower(s2[i]) - 'a']--;
              }
              else
              {
                  printf("Alphabetic characters only.");
                  return 1;
              }
          }
      
          for (int i = 0; i < ALPHASIZE; i++)
          {
              if (characters[i])
              {
                  printf("NOT ANAGRAM\n");
                  return 0;
              }
          }
      
          printf("ANAGRAM\n");
      }
      

Discussion Questions

One technique to promote participation in class is a quick, 2–3 minute discussion question. Letting students posit their own reasoning, even if they’re not entirely sure of an answer, can help reinforce material from lecture. One model for introducing these questions is the “Think, Pair, Share” approach, in which students take 30 seconds to think of their own answer and 60 seconds to share their answer with a partner. Afterwards, you can call on random pairs to share their thinking with the larger group. It’s also best to follow up with your own answer, too!

  • What are some examples of programs we’ve seen that take command-line arguments?
  • Why are command-line arguments useful? Why not just let a user configure the program after it’s already started running?

Debugging Shorts

This week can also be an opportune time to introduce a discussion of debugging, especially as via debug50. These shorts help explain debug50’s “Step Over” and “Step Into” functions, and can be shared directly with students or taken as inspiration for your class.

Annotated Sample Slides

Here you’ll find sample slides to adopt or adapt when teaching Week 2.

Some slides contain speaker notes to illustrate why the sample slides take a certain approach to illustrating a concept or leading an exercise. You’re welcome to modify these slides as you see fit, though do try to keep some of the same elements of active learning that have been included in these samples.

Past versions of sample slides are also available under the “Additional Slide Resources” dropdown.