OOP Lecture 2
OOP Lecture 2
March 7, 2023
Pointers
Memory management
Modular programming
Abstract data types
#d e f i n e NULL 0
// s i n c e C++11
#d e f i n e NULL n u l l p t r
float ∗x = 0;
float ∗x = NULL ;
float ∗x = nullptr ;
float ∗x { n u l l p t r };
a pointer that does not point to valid data: the data might have been
erased from memory;
the memory pointed to has undefined contents;
Dereferencing such a pointer will lead to undefined behaviour!
a void pointer is a pointer that has no associated data type with it;
it can hold the address of a variable of any type; used in malloc,
calloc;
used to implement generic functions (e.g. qsort);
void pointer cannot be dereferenced;
the C standard does not allow pointer operations on void pointers.
s h o r t a r r [ 5 ] = {20 , 30 , 40 , 50 , 60};
printf(”%d”, a[i]);
printf(”%d”, *(a+i));
printf(”%d”, a+i);
printf(”%d, *a);
a++;
Definition
<return type> (∗ <name>)(<parameter types>)
E.g.:
double (∗ operation) ( double , double ) ;
Declaration:
void (∗func pointer)(int);
Initialization:
func pointer = my int func; // where my void my int func(int v) is a
function you wrote , or
func pointer = my int func
Invocation:
func pointer(arg), or
(*func pointer)(arg)
callback functions: void create button( int x, int y, const char ∗text,
void (∗callback func));
qsort - http://www.cplusplus.com/reference/cstdlib/qsort/
void (*(*f[])())()
Let’s decipher it!
void (*(*f[])())()
f-f
f[] is an array
*f[] of pointers
(*f[])() to functions
*(*f[])() returning pointers
(*(*f[])())() to functions
void (*(*f[])())(); returning void
Stack Heap
very fast access variables can be accessed
don’t have to explicitly globally
de-allocate variables no limit on memory size
space is managed efficiently by (relatively) slower access
CPU, memory will not become no guaranteed efficient use of
fragmented space, memory may become
local variables only fragmented over time
limit on stack size you must manage memory
(OS-dependent) variables can be resized using
variables cannot be resized realloc()
Heap
Stack for variables that can change
is the preferred way to allocate size dynamically
variables : it’s easier, less for variables you need to persist
memory errors and faster throughout the lifetime of your
functions with variables that application
only persist within the lifetime when you need to allocate a
of the function large block of memory (e.g.
store a texture of 15Mb)
Goals:
The code of a C/C++ program is split into several source files .h and
.c/.cpp:
.h files - contain the function declarations (the interfaces);
.c/.cpp files - contain the function implementations.
The header file is a contract between the developer and the client of the
library that describes the data structures and states the arguments and
return values for function calls.
The compiler enforces the contract by requiring the declarations for all
structures and functions before they are used (this is why the header file
must be included).
Diana Borza - [email protected] Object Oriented Programming - Lecture 2 March 7, 2023 32 / 39
Modular programming - advantages
code reuse;
programs can be designed more easily a small team deals with only a
small part of the entire code;
code is short, simple and easy to understand;
the .c/.cpp files can be compiled separately (for error checking and
testing);
errors can easily be identified, as they are localized to a subroutine or
function;
the scoping of variables can easily be controlled.
Directive Meaning
opens the header file and insert its contents in the
#include header
current file; <>(search in systems directory) vs ””
file
(search in current directory, then system directo-
ries)
any occurrence of identifier in the code is replaced
#define identifier
by replacement
replacement
Directive Meaning
the code between the two directives is compiled
#ifdef macro, ...
only if the specified macro has been defined.
,#endif
the code between the two directives is compiled
#ifndef macro, ...
only if the specified macro has been not defined;
,#endif
together with #define can be used as include
guard
the current file will be included only once in a single
#pragma once
compilation (not standard, but widely supported)
Any program entity that satisfies the requirements from the ADT
definition is considered to be an implementation of the ADT.