UPI Study › Courses › C++ Programming › Free lessons › Lesson 8.5 Free with a free account
How Arguments Travel
C++ Programming · Chapter 8: FunctionsSection 8.5 · lesson 55 of 84video coming soon
← How the Compiler Manages Variable StorageNext lesson: Function Overloading in Action →
In this lesson
Copying versus linking, between caller and function.
- Predict what the caller sees after a by-value change
- Write reference and constant reference parameters
- Return several results; supply default arguments
- See why arrays and vectors travel differently
Transcript
Everything said in the video, section by section (1,307 words). Read along, or search it.
Opening Question
Copy or Link: A One-Character Choice
When you hand a value to a function, one of two things happens. The function gets its own copy, or it gets a link back to the caller's variable. Which one you choose decides whether the function can change what the caller holds, and how much work happens at every call. It's a single character of difference in the code, and a complete difference in behavior.
Analogy
Photocopy or Original Document
Lending a colleague a document can mean two things. You can photocopy it and give them the copy. They can scribble on it freely, and your original is untouched. Or you can hand them the original, and anything they write on it, you have too. Neither is better. They answer different requests, and the confusion comes from not saying which you meant.
Pass By Value
Parameters as Safe but Costly Copies
Written plainly, a parameter is a copy. The function is handed the value of the argument, stores it in a variable of its own, and works on that. Add bonus adds 10 to score, which changes the copy, and only the copy. Back in main, my score still prints 50. This has two consequences. The first is safety: a function taking values can't damage anything the caller owns. That's a real guarantee, and the reason by value is the default. The second is cost. Making the copy takes work proportional to the size of the thing. For a number, nothing at all. For a string holding a paragraph, or a vector of 10,000 elements, every call duplicates the entire contents, then throws the duplicate away.
Pass By Reference
One Box With Two Names
Put an ampersand after the type, and the parameter stops being a copy. It becomes another name for the caller's own variable, and every change reaches straight through. Now add bonus changes the caller's variable, and my score prints 60. One box, two names. Notice that the call site is identical. That's convenient, and it's also the one genuine hazard. Reading add bonus of my score tells you nothing about whether my score is about to change. Only the function's declaration says so. So a function that modifies what it's given should be named to make that obvious, and say so in its contract.
Limitation
References Need Something to Name
A reference needs something to refer to. Add bonus of the literal 50 is refused, because there's no box behind 50 for the parameter to name. By value has no such restriction.
Const Reference
Reading Without Copying or Changing
Most parameters are read, not written. For those, by value means paying for a copy you never needed, and a plain reference means advertising a permission you don't want. A constant reference takes the third option. No copy is made, and the function is forbidden from modifying it. Print report reads the title. An attempt to change it is refused at compile time, as shown. Clang's wording, no viable overloaded '=', means no assignment operator can be used on a const string.
Decision Rule
Two Questions for Every Parameter
Two questions decide every parameter you'll ever write. First, must the function change it? If yes, use a plain reference. If not, is it big to copy, like a string, a vector, or a large object? If yes, use a const reference: no copy, and no modification. If not, pass by value. It's the simplest, and cheap here.
Comparison
Three Forms Side by Side
Here are the three forms compared on what actually differs. By value makes a copy on every call. A reference and a const reference make none. By value can't change the caller's variable. A reference can, and that's the point of it. A const reference can't: the attempt is refused when building. A literal can be passed by value or by const reference, but not by plain reference, which needs a variable. And for a large object, by value costs a full copy every call, while both references cost nothing. So here's a working default. Small and read-only: pass by value. Large and read-only: pass by constant reference. Must be modified: pass by plain reference. That covers nearly every parameter.
Output Parameters
Returning Quotient and Remainder Together
A function returns one value. When a piece of work genuinely produces two, such as a quotient and a remainder, one route is to write the extra results into reference parameters. These are called output parameters. Divide takes a numerator and a divisor, and writes the quotient and the remainder into its last two parameters. Dividing 17 by 5 makes q 3, and r 2. Two habits keep this readable. Put the inputs first and the outputs last, consistently. And name the outputs in the contract, because a caller looking at the call can't tell which arguments are about to be overwritten. But output parameters are easily overused. A function returning a single value can be used inside an expression, or a condition. One that writes into parameters can't. If a function produces one thing, return it.
Default Arguments
Defaults Belong on Trailing Parameters
A parameter can be given a value to use when the caller doesn't supply one. The default goes on the declaration, if there is one, and isn't repeated on the definition. Area of, with 3 and 4.5, gives 13.5. Area of, with just 3, gives 3, because height defaults to 1. One rule governs the whole feature. Defaults must be the trailing parameters. Arguments are matched by position, so a parameter with a default can't be followed by one without. Try it the other way and the compiler refuses, as shown. A caller omitting the earlier one would leave it unable to tell which argument was which.
Common Mistake
Never Return a Reference to a Local
Returning a value is straightforward. The value is handed back to the caller, and it survives the function ending. Returning a reference to something the function owns is a different matter, because that thing doesn't survive. Make label creates a local string and returns a reference to it. The label ceases to exist as the return line completes. So the caller holds a name for something that's no longer there. Using it is undefined behavior: it may print rubbish, may appear to work, and may do something different tomorrow. Most compilers warn about this exact pattern, and it's a warning worth reading rather than switching off. Return by value instead.
Special Case
Arrays Link While Vectors Copy
Two familiar collections only make sense once copying and linking are separated, and they behave differently from each other. That's a genuine inconsistency in the language. An array parameter is never copied, whatever it looks like. The function works on the caller's own elements, and can change them. A vector without an ampersand is copied, every element, every call. Watch. Both are modified inside bump, with no ampersand on either. The array's first element becomes 99. The vector's stays 1: only its copy changed. Add the ampersand to the vector, and both change. A const vector reference is the normal way to hand a vector to a function that reads it.
Key Insight
Same Omission, Opposite Meanings
So the same omission means opposite things. Leaving the ampersand off an array parameter gives the function full access to your data. Leaving it off a vector parameter duplicates the whole collection. Read arrays as linked by default, and vectors as copied by default, and both stop being surprising.
Quick Check
Choosing Forms for Three Functions
Quick check. Pick the parameter form for three functions. The first prints a long string. The second adds points to an int the caller holds. The third squares an int and returns the result. Pause and predict. Printing a long string: a const reference, so no copy and no change. Adding to the caller's int: a plain reference, because the change must reach the caller. Squaring an int and returning the result: by value. It's small, and only read.
Key Takeaways
Choosing How Arguments Travel
To summarize. By value hands over a safe copy, paid for in proportion to its size. By reference, with an ampersand, lets the function change the caller's variable. A const reference makes no copy and allows no change, the default for large values. Put inputs first and outputs last, and keep defaults on the trailing parameters. Return by value, never a reference to a local.
About C++ Programming at UPI Study
C++ Programming (Computer Science 242) is a self-paced online course of 84 video lessons in 11 chapters, from your first program to decisions, loops, arrays, functions, classes, files, pointers and inheritance. It carries a NCCRS credit recommendation for 3 semester credits.
Every lesson transcript is free on pages like this one, and the videos are free with a free UPI Study account. Enrolling adds a practice quiz after each lesson, the graded work and final exam that earn the credit, lifetime access, and an official transcript on completion. UPI Study has helped over 130,000 students with college credits. ACE and NCCRS have over 2,100 cooperating colleges that will consider accepting credits; the final decision is with the universities.
Enroll now → Course details Download the syllabus Every course with PRO →
Why take it here
Why students take C++ Programming with UPI Study
Where the credit goes
Universities that work with NCCRS
C++ Programming carries a NCCRS credit recommendation. These universities work with NCCRS; some are UPI Study's signed partners. ACE and NCCRS have over 2,100 cooperating colleges that will consider accepting credits; the final decision is with the universities.
Thomas Edison State UniversitySigned partner
University of the PeopleSigned partner
Charter Oak State CollegeSigned partner
Strayer UniversitySigned partner
Columbia Southern UniversitySigned partner
Indiana TechSigned partner
Penn StateWorks with NCCRS
Southern New Hampshire UniversityWorks with NCCRS
SUNYWorks with NCCRS
+many more cooperating universitiesFind my college →Find my college → Not listed? Ask Athena in the corner of this page, or book a 15-minute call.
FAQ
Questions students ask us
About How Arguments Travel
What is the difference between pass by value and pass by reference in C++?
When should I use a const reference parameter in C++?
How can a C++ function return more than one value?
Why does changing a vector inside a function not change the original, but an array does?
About the C++ Programming course
How many college credits is C++ Programming?
How much does C++ Programming cost and what is included?
Which universities accept UPI Study credits?
How long does C++ Programming take?
How are the exams done?
How do my credits reach my college?
Ready for the full course? Earn 3 credits in C++ Programming.
84 video lessons, a quiz after each one, and the graded work that earns the credit. Recommended for credit by NCCRS.
3 credits · NCCRSEnroll →