CS50 Week 2

July 8, 2022

Week 2. Arrays, strings, and command-line arguments. This is where C starts to feel like a real language and not just "type printf and pray."

The lecture blew my mind a little. David Malan showed how strings in C are literally just arrays of characters with a \0 at the end. Like, there's no "string type" the way I'm used to from messing around with JavaScript. A string is just a char[] that happens to end with a null terminator. Once that clicked, a lot of weird C behavior suddenly made way more sense. Why you can't just compare two strings with ==, why you need strlen(), all of it.

Command-line arguments were also new to me. Up until now every program I wrote just used get_int or get_string from CS50's library. But this week we learned about argc and argv. Your main function can actually take inputs directly from the terminal! I spent a solid 20 minutes just running ./myprogram hello world and printing out argv[0], argv[1], argv[2] to see what showed up. Small thing, but it made me feel like I was doing Real Programming.

The problem sets this week were a big step up from Week 1. First up was Readability, where you had to calculate the reading level of a block of text using the Coleman-Liau index. This one was mostly about counting letters, words, and sentences in a string by looping through each character. I kept getting tripped up on edge cases. Like, does a period always end a sentence? What about abbreviations? I ended up printing out every single character with its index to figure out where my counts were going wrong. Classic printf debugging. But I got it working and it felt GREAT to see the correct grade level pop out!

Then came the harder problem set: Substitution. You take a 26-character key as a command-line argument, and then your program encrypts text by substituting each letter according to that key. Sounds straightforward, right? It was NOT. I had to validate the key (exactly 26 characters, all alphabetic, no repeats), handle uppercase vs lowercase, leave non-alphabetic characters alone, and actually do the substitution.

I got stuck for almost an hour on the uppercase/lowercase thing. My encrypted output kept coming out all lowercase no matter what. I was pulling my hair out. Turns out I was converting everything to lowercase at the start of my substitution step and then never converting it back. The fix was like two lines of code. Check if the original character was uppercase with isupper(), do the substitution on the lowercase version, then convert back with toupper() if needed. TWO LINES. After an hour! The debugger saved me again here. Stepping through character by character, I could literally watch my uppercase 'H' become a lowercase 'f' and go "wait... why is that lowercase now?"

The jump from Week 1 to Week 2 is real. Week 1 was mostly about getting comfortable with syntax and basic logic. Week 2 expects you to think about how data is actually stored and manipulated in memory. Arrays aren't just a concept anymore. You're indexing into them, iterating over them, doing math on individual elements. It's a different kind of thinking.

One thing I'm noticing: the debugging skills I built grinding through Credit last week are actually paying off! I'm reaching for the debugger faster instead of just staring at my code hoping the bug reveals itself. I'm writing printf statements to check intermediate values without even thinking about it. That feels like progress.

I'm spending less time completely lost and more time actually problem-solving. Still slow, still looking things up, but the ratio is shifting. Onwards to Week 3!