- Advice: Prefer
pass-by-const-ref
for anything larger than an int, unless you need to make a copy anyways, then perhaps usepass-by-value
(but not always) - Also:
inf f (int &n) {...}
int g (const int &n) {...}
- What would happen if I did
f(5)
? - There would be a compiler error, as we passed in an l-value but we’re expecting a a reference to the literal. If n changes, what does it mean to change 5?
- On the other hand,
g(5)
is fine as we’ve promised the compiler that g will not change the parameter
How can g(5)
work if n
must be bound to something with a memory address? The compiler creates a *** temporary location *** in memory to hold the 5
, and lets n
refer to that.
Dynamic Memory Allocation
In C++, we use:
Reminder:
- All local variables reside on the stack.
- Variables are deallocated when they go out of scope (stack is popped)
- Allocated memory exists on the heap
- Remains allocated until
delete
is called - If you don’t delete all allocated memory - memory leak
- Program will fail eventually
- We regard any memory leak in this class as an
error
Best way to check for memory leaks is using the tool valgrind
on your program
- e.g. If your program is called
prog
(in yourcwd
):valgrind ./prog
or replaceprog
with the path ifprog
is not incwd
- Don’t return references or pointers to local stack frame variables (common sense)
Initializing Array Forms
- It is important to match the correct form of delete with the the corresponding
new
- Every call to
new
should have a corresponding call todelete
- Every call to
new[]
, should have a corresponding call todelete[]
Returning by value/reference/pointer
If this is expensive, return a pointer
or a reference
instead.
Which should you pick in general? Depends on your needs, but return by value (unless you actually wanted to keep allocated data) because it won’t be as slow necessarily.
Meanings to C++ operators for own types
- We can give meanings to the
C++
operators for our own types
Operator Overloading
This is an example of overloading the +
and *
operators for my own structures
.
Two of the most useful operators to overload are the IO operators
Overloading input
and output
operators are very handy
Next Time:
- ** The Preprocessor ***
The preprocessor transforms the program before the compiler sees it!