Skip to Content
Course content

43: Understanding Memory Addresses

Click on the "Edit" button in the top corner of the screen to edit your slide content.

Up until now, we've treated variables like magic boxes. You give a variable a name, you put a value in it, and C remembers it for you. But as a software engineer, "magic" is a dangerous way to think. In reality, your variables aren't boxes—they are specific locations in your computer's RAM. Every single byte of memory has a unique numeric address, like a house number on a very long street.

Defining our game state variables

To see this in action, let's build a tiny snippet of a game save system. I want to track two things: a player's health and their current gold count. I'll keep it simple with two integers.

int health = 100;
int gold = 50;

At this point, the compiler has set aside two chunks of memory for these values. You know them as health and gold, but the CPU sees them as hex codes like 0x7ffeefbff5c8. This is where the "address-of" operator, the ampersand (&), comes in. It tells C: "Don't give me the value inside the box; give me the address of the box itself."

Peeking under the hood with the & operator

I want to print these addresses to the console so we can actually see where they live. I'll use the %p format specifier, which is specifically designed for pointers (addresses).

printf("Health value: %d\n", health);
printf("Health address: %p\n", (void*)&health);

printf("Gold value: %d\n", gold);
printf("Gold address: %p\n", (void*)&gold);

I added the (void*) cast there because %p expects a generic void pointer. It's a habit that prevents compiler warnings on stricter systems. When you run this, you'll see two long hexadecimal strings. These are the exact coordinates in your RAM where your game data is sitting.

A quick detour into a common mistake

When I first started doing this, I thought, "Wait, an address is just a number. Why can't I just print it as a decimal integer to make it easier to read?" I tried something like this:

// My mistake: trying to treat a memory address as a standard integer
printf("Health address as decimal: %d\n", &health);

I quickly realized why that's a bad idea. First, the compiler started screaming warnings at me because a memory address (usually 64-bit on modern machines) is way too large to fit into a standard 32-bit int. The value got truncated, and the number I saw was completely useless. Memory addresses aren't "numbers" in the way we think of counts or measurements; they are identifiers. Always use %p for addresses. Don't try to force them into int or long variables unless you're doing very specific low-level memory manipulation.

Visualizing the memory gap

One thing that always fascinated me when I first learned this was seeing how the compiler arranges these variables. If you look at the output of our game state addresses, you'll notice they are very close to each other, but not identical. Since an int usually takes up 4 bytes, you'll likely see a difference of 4 (or sometimes 8, depending on padding) between the two addresses.

This layout is the foundation for everything we'll do with pointers. Once you stop seeing health as a name and start seeing it as "the value located at address 0x7ffe...", the rest of C's memory management starts to make a lot more sense.




📋 Practical Task

The Variable Distance Mapper

Create a program that declares three different variables of different types: a char, an int, and a double. Print the memory address of each variable using %p. Once you've done that, observe the hexadecimal addresses and determine which variables are stored closest to each other and how the size of the data type (1 byte for char, 4 for int, 8 for double) reflects the "gap" between their addresses in memory.

Rating
0 0

There are no comments for now.

to be the first to leave a comment.