0% found this document useful (0 votes)
9 views33 pages

CS3505 Lecture2

The lecture covers key concepts in software design, including separation of concerns and the Single Responsibility Principle. It introduces C++ input/output streams, variable scope, and function calling mechanisms, emphasizing the importance of proper memory management and the use of pointers and references. Additionally, it discusses the implications of using boolean parameters and the readability of function calls.

Uploaded by

liang19880404
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
9 views33 pages

CS3505 Lecture2

The lecture covers key concepts in software design, including separation of concerns and the Single Responsibility Principle. It introduces C++ input/output streams, variable scope, and function calling mechanisms, emphasizing the importance of proper memory management and the use of pointers and references. Additionally, it discusses the implications of using boolean parameters and the readability of function calls.

Uploaded by

liang19880404
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 33

CS 3505: Software Practice II

Lecture 2:
Separation of Concerns
Scope,
Pointers, References
Course Announcements
• First assignment out today
– Due next Thursday
• Help hours start tomorrow – see page
under Course Resources
• See instructions on installing Docker and
VSCode
– This is a great activity for a lively discussion
on Piazza
– Doing the steps yourself will help you
understand how this is set up
Some Design Discussion
• I have declared a function

int scoreAssignment(Assignment id,


bool withLatePenalty);

• Thoughts on its design?


Some Design Discussion
• What about?

int scoreAssignment(Assignment id);


int scoreAssignmentWithPenalty(Assignment id);
Some Design Discussion
• So while this is pretty readable

int scoreAssignment(Assignment id,


bool withLatePenalty);

• The call is a little opaque


scoreAssignment(id, false);
scoreAssignment(id, isLate); // better
Separation of Concerns
• An important concept in software is
“separation of concerns”
– each module/function/class should have one thing
to do
– Also, the Single Responsibility Principle
• when you get on a plane, do you want a pilot or a
plumber/pilot/chef flying the plane?
• The Clean Code book
– argues that bool parameters in
functions/methods indicate a lack
of separation.
– A “code smell”
Basic IO
• Programs run from the terminal have
– standard input
– standard output (default to terminal)
– standard error (default to terminal)
• These are streams
– a stream is serial access to a sequence of
characters
• file
• user
• network
• strings
IO Streams
• There are predefined streams in C++ that
match up with standard in/out/error
– std::cin
– std::cout
– std::cerr
• These can be piped or redirected on the
command line
$ ls -t > myFiles.txt redirects stdout to a file
$ sort < myFiles.txt turns a file into stdin
$ ls –lt | more stdout of ls to stdin of more
Using C++ streams
• You need to tell C++ that the program will
be using these streams
#include <iostream>
• #include will be discussed in much more
detail soon, but for now, it allows you to
use functionality from elsewhere
– sort of like import in Java
• only as a common purpose, not mechanism
Using C++ streams
#include <iostream>
• Then in main you can
std::cout << “hi” << std:endl;

• If you don’t want to type std:: in front add


using namespace std; # a bit of bad style
• Be more specific
using std::cout;
using std::endl;
IO Streams
• Programs can insert characters onto those
streams or extract from them
cout << “Hello”;
cin >> anIntegerVariable;
• The insertion operator << will convert base
types and classes with an overloaded <<
operator
cout << “The result is “ << myInt << endl;
cout << “Debug: “ << myObject << endl;
IO Streams
• >> is the extraction operator
int score;
cin >> score;
• cin extraction uses whitespace to
terminate extraction
– however std::cin does not send the input until
Enter is typed.
– Number extraction stops at a non-number
character
Insertion and Extraction
• If you try to extract an int from a part of a stream
that is not an int, it will fail
• You can test for success
if (cin >> myInt) {
do something with myInt
}
• Extraction also returns false at EOF, so this
approach can be used with a loop to read in
multiple values. EOF is often generated from
terminal input with control-d.
• See example code
Basic I/O
• This is just a very simple and error prone
way to do input/output in C++.
• More later
– read a line at a time
– parse the line by treating it as a stream
Scope of Variables
• Variables only exist in
their enclosing { } if (true) {
– parameters are int val = 3;
considered part of the }
function body scope val = 5; // NO
– This doesn’t mean objects __________________
cannot persist int val = 4;
• Duplicate names are if (true) {
resolved through most int val;
local scope. val = 1;
– Note that not just instance }
variable shadowing is cout << val << endl;
allowed
Variable Creation
value address
• What happens when 5 1000
you declare and initialize
a variable?
int var = 5;
– Space is reserved for the
type on the stack.
– This space has an
address
– The value is placed at
that address
Compiler Issues
• How does the compiler know where var is the
next time it sees it?
– A symbol table
• We will use a simplified version with name and type and
address
• real addresses are not assigned until later
• even then, those are virtual addresses in the process address
space

Name Type Address

var int 1000


Variable Creation
value address
• Add another variable 5 1000

10 1004
int var = 5;
int count = 10;

• Additional variables
grow the stack
– an area of memory for
each process
– Usually a stack is
shown growing up
Function Calling
value address
• Function calls need to 5 1000
store
10 1004
– Where to return when
done with the function
– Parameters
– Local variables
• Added as a stack
frame
Function Calling
value address
int A(int param1) { 1000
1
int local1 = 5;
return local1; 0x1F0B 1004

} 1 1008
5 100C
int main() {
int mVar = 1;
mVar = A(mVar);

return 0;
}
Function Calling
value address
int A(int param1) { 1000
1
int local1 = 5;
return local1; 0x1F0B 1004

} 1 1008
5 100C
int main() {
int mVar = 1;
mVar = A(mVar);

return 0;
}
Leaving a Function
int A(int param1) { value address
int local1 = 5; 1 1000
return local1;
0x1F0B 1004
}
1 1008
• Value in local1 is copied to
a temporary return int 5 100C
– often the compiler gets rid of
this overhead
• Destructor is called on local
objects in frame
• Stack frame is ‘popped’
• Execution returns to calling
address
Function Calling
int A(int param1) { • Functions in C++ use
int local1 = 5; a pass-by-value
return local1; mechanism by default
} • Changes to value
stored in param1 in
int main() { A() are not
int mVar = 1; propagated back to
mVar = A(mVar); the argument mVar
return 0;
}
Break
Looking at Addresses
• Ampersand is overloaded as a unary operator
– the address-of operator
&localvar
• Returns the address of localvar

int mLocal = 1;
cout << "mLocal address is: " <<
&mLocal << endl;
Storing Addresses
• Store addresses in a pointer
type variable int var = 5;
• Type is base type with an * int* varA = &var;
– Like int* p
– Also see it as int *p
• A pointer holds a memory
address
– That is all you need to know to
be successful with pointers
• Sketch out compiler table and
memory diagrams
Sketch

int var = 5;
int* varA = &var;
One Use
• Pointers can be used to void A(int* param1)
make arguments {
mutable. …
– the pointer is constant, }
the thing it points to can
change

int mLocal = 1;
A(&mLocal);
Dereference a Pointer
• Can access the thing the pointer is pointing at
with *
– Dereference operator

int A(int* param1) {


*param1 = *param1 * 2;
return 1;
}
Sketch
int A(int* param1) {
*param1 = *param1 * 2;
return 1;
}

int mLocal = 1;
A(&mLocal);
C++ References
References are a safer way to int& ref = val;
“point” at another object
– Use in parameter list
– Don’t change calling syntax int A(int& v) {
v++;
Reference type mechanism }
can depend on compiler
– Reference variable might only
exist during compilation int main() {
– Might be made as a pointer
int x = 4;
A(x);
}
Uses of & and *
Character\Use Operator Type Modifier
* dereference (*val) pointer (int*)
& address-of (&val) reference (int&)

You might also like