TDDD38/726G82 - Advanced programming in C++
Introducon STL
Christoffer Holm
Department of Computer and informaon science
TDDD38/726G82 - Advanced programming in C++ Introducon STL - - PowerPoint PPT Presentation
TDDD38/726G82 - Advanced programming in C++ Introducon STL Christoffer Holm Department of Computer and informaon science 1 Introducon 2 IO 3 Sequenal Containers 1 Introducon 2 IO 3 Sequenal Containers 3 / 47
Department of Computer and informaon science
3 / 47
What is the STL?
3 / 47
What is the STL?
3 / 47
What is the STL?
3 / 47
What is the STL?
3 / 47
What is the STL?
4 / 47
5 / 47
Design principles of STL
5 / 47
Design principles of STL
5 / 47
Design principles of STL
5 / 47
Design principles of STL
5 / 47
Design principles of STL
5 / 47
Design principles of STL
6 / 47
Components
6 / 47
Components
6 / 47
Components
6 / 47
Components
6 / 47
Components
8 / 47
Streams
ios
istream ifstream istringstream iostream stringstream fstream
8 / 47
Streams
ios
istream ifstream istringstream iostream stringstream fstream std::cout std::cin
8 / 47
Streams
ios
istream ifstream istringstream iostream stringstream fstream Output Input
9 / 47
Streams
10 / 47
Stream operators template <typename T>
{ // write data to the device return os; } // ... cout << 1 << 2;
11 / 47
Stream operators
cout << 1 << 2;
11 / 47
Stream operators
(cout << 1) << 2;
11 / 47
Stream operators
11 / 47
Stream operators
cout << 2;
11 / 47
Stream operators
(cout << 2);
11 / 47
Stream operators
cout;
12 / 47
Chaining operators
13 / 47
Devices
int main() {
cout << 1; // write to terminal
<< 1; // write to string
<< 1; // write to file
}
14 / 47
Devices istream& operator>>(istream& is, T& data); int main() { int x; istringstream iss{"1"}; ifstream ofs{"my_file.txt"}; cin >> x; // read from terminal
}
15 / 47
Devices
16 / 47
Error handling int x; ifstream ifs{"file"}; while (ifs >> x) { // do stuff }
fail:
eof:
bad:
16 / 47
Error handling int x; ifstream ifs{"file"}; while (ifs >> x) { // do stuff }
fail:
eof:
bad:
16 / 47
Error handling int x; ifstream ifs{"file"}; while (ifs >> x) { // do stuff }
fail:
eof:
bad:
16 / 47
Error handling int x; ifstream ifs{"file"}; while (ifs >> x) { // do stuff }
fail:
eof:
bad:
16 / 47
Error handling int x; ifstream ifs{"file"}; while (ifs >> x) { // do stuff }
fail: unable to read as int eof:
bad:
16 / 47
Error handling int x; ifstream ifs{"file"}; while (ifs >> x) { // do stuff }
fail: unable to read as int eof: found end of file character bad:
16 / 47
Error handling int x; ifstream ifs{"file"}; while (ifs >> x) { // do stuff }
fail: unable to read as int eof: found end of file character bad: file is corrupt
17 / 47
Error handling int x; ifstream ifs{"file"}; ifs >> x; if (ifs.fail()) // unable to read as int // ... else if (ifs.eof()) // reached end of file // ... else if (ifs.bad()) // device is corrupt // ...
18 / 47
Error flags istream& operator>>(istream& is, T& t) { // try to read from is if (/* unable to read as T */) { is.setstate(ios::failbit); } return is; }
19 / 47
Error flags ios::failbit
ios::eofbit
ios::badbit
ios::goodbit
20 / 47
Error flags
21 / 47
Converng from strings
int main(int argc, char* argv[]) { int x; istringstream iss{argv[1]}; if (!(iss >> x)) { // error // reset flags iss.clear(); } // continue } int main(int argc, char* argv[]) { int x; try { x = stoi(argv[1]); } catch (invalid_argument& e) { // error } // continue }
22 / 47
Converng from strings istringstream version
stoi version
23 / 47
What will be printed?
#include <sstream> #include <iostream> #include <string> using namespace std; int main() { stringstream ss{}; ss << "123a bc hello"; int n{}; char c{}; string str{}; if (ss >> n >> n >> c) cout << n << " "; ss.clear(); if (ss >> c >> c) cout << c << " "; ss.clear(); if (ss >> str) cout << str << " "; }
25 / 47
Containers
26 / 47
Important concepts
26 / 47
Important concepts
26 / 47
Important concepts
26 / 47
Important concepts
26 / 47
Important concepts
26 / 47
Important concepts
27 / 47
What is a sequenal container?
28 / 47
Which sequenal containers are there?
29 / 47
std::array
data std::array<int, 4>
std::array<int, 4> array{};
29 / 47
std::array
data std::array<int, 4>
array[0] = 1;
29 / 47
std::array
data std::array<int, 4>
array[0] = 1;
29 / 47
std::array
data std::array<int, 4>
array[1] = 2;
29 / 47
std::array
data std::array<int, 4>
array[1] = 2;
29 / 47
std::array
data std::array<int, 4>
array[2] = 3;
29 / 47
std::array
data std::array<int, 4>
array[2] = 3;
29 / 47
std::array
data std::array<int, 4>
array[3] = 4;
29 / 47
std::array
data std::array<int, 4>
array[3] = 4;
30 / 47
std::array
31 / 47
std::array
32 / 47
Example
#include <array> // ... int main() { std::array<int, 5> data{}; for (unsigned i{}; i < data.size(); ++i) { cin >> data.at(i); } for (auto&& i : data) { cout << i << endl; } }
33 / 47
std::vector
data size capacity
4
std::vector<T>
std::vector<int> vector{};
33 / 47
std::vector
data size capacity
4
std::vector<T>
vector.push_back(1);
33 / 47
std::vector
data size
1
capacity
4
std::vector<T>
vector.push_back(1);
33 / 47
std::vector
data size
1
capacity
4
std::vector<T>
vector.push_back(2);
33 / 47
std::vector
data size
2
capacity
4
std::vector<T>
vector.push_back(2);
33 / 47
std::vector
data size
2
capacity
4
std::vector<T>
vector.push_back(3);
33 / 47
std::vector
data size
3
capacity
4
std::vector<T>
vector.push_back(3);
33 / 47
std::vector
data size
3
capacity
4
std::vector<T>
vector.push_back(4);
33 / 47
std::vector
data size
4
capacity
4
std::vector<T>
vector.push_back(4);
33 / 47
std::vector
data size
4
capacity
4
std::vector<T>
vector.push_back(5);
33 / 47
std::vector
data size
5
capacity
8
std::vector<T>
vector.push_back(5);
33 / 47
std::vector
data size
5
capacity
8
std::vector<T>
vector.push_back(5);
33 / 47
std::vector
data size
5
capacity
8
std::vector<T>
vector.erase(vector.begin() + 2);
33 / 47
std::vector
data size
4
capacity
8
std::vector<T>
vector.erase(vector.begin() + 2);
33 / 47
std::vector
data size
4
capacity
8
std::vector<T>
vector.erase(vector.begin() + 2);
33 / 47
std::vector
data size
4
capacity
8
std::vector<T>
vector.erase(vector.begin() + 2);
33 / 47
std::vector
data size
4
capacity
8
std::vector<T>
vector.erase(vector.begin() + 2);
33 / 47
std::vector
data size
4
capacity
8
std::vector<T>
vector.erase(vector.begin() + 2);
34 / 47
std::vector
35 / 47
std::vector
36 / 47
Example
#include <vector> // ... int main() { std::vector<int> data{}; int x{}; while (cin >> x) { data.push_back(x); } for (auto&& i : data) cout << i << endl; }
37 / 47
std::list
first last size std::list<T>
std::list<int> list{};
37 / 47
std::list
first last size std::list<T>
list.push_back(1);
37 / 47
std::list
first last size
1
std::list<T> 1
list.push_back(1);
37 / 47
std::list
first last size
1
std::list<T> 1
list.push_back(2);
37 / 47
std::list
first last size
2
std::list<T> 1 2
list.push_back(2);
37 / 47
std::list
first last size
2
std::list<T> 1 2
list.push_back(3);
37 / 47
std::list
first last size
3
std::list<T> 1 2 3
list.push_back(3);
37 / 47
std::list
first last size
3
std::list<T> 1 2 3
list.push_back(4);
37 / 47
std::list
first last size
4
std::list<T> 1 2 3 4
list.push_back(4);
38 / 47
std::list
39 / 47
std::list
39 / 47
std::list
40 / 47
Example
#include <list> #include <vector> // ... int main() { std::list<int> data{}; std::vector<int*> order{}; int x; while (cin >> x) { data.push_back(x);
} data.sort(); int i{0}; for (auto&& val : data) { cout << val << ", " << *order[i++] << endl; } }
41 / 47
std::forward_list
first size std::forward_list<T>
std::forward_list<int> list{};
41 / 47
std::forward_list
first size std::forward_list<T>
list.push_front(1);
41 / 47
std::forward_list
first size
1
std::forward_list<T> 1
list.push_front(1);
41 / 47
std::forward_list
first size
1
std::forward_list<T> 1
list.push_front(2);
41 / 47
std::forward_list
first size
2
std::forward_list<T> 2 1
list.push_front(2);
41 / 47
std::forward_list
first size
2
std::forward_list<T> 2 1
list.push_front(3);
41 / 47
std::forward_list
first size
3
std::forward_list<T> 3 2 1
list.push_front(3);
41 / 47
std::forward_list
first size
3
std::forward_list<T> 3 2 1
list.push_front(4);
41 / 47
std::forward_list
first size
4
std::forward_list<T> 4 3 2 1
list.push_front(4);
42 / 47
std::forward_list
43 / 47
std::forward_list
44 / 47
std::deque
begin data size chunks std::deque<T>
std::deque<int> deque{};
44 / 47
std::deque
begin data size chunks std::deque<T>
deque.push_back(1);
44 / 47
std::deque
begin data size chunks
1
std::deque<T>
deque.push_back(1);
44 / 47
std::deque
begin data size
1
chunks
1
std::deque<T>
deque.push_back(1);
44 / 47
std::deque
begin data size
1
chunks
1
std::deque<T>
deque.push_back(2);
44 / 47
std::deque
begin data size
2
chunks
1
std::deque<T>
deque.push_back(2);
44 / 47
std::deque
begin data size
2
chunks
1
std::deque<T>
deque.push_back(3);
44 / 47
std::deque
begin data size
3
chunks
1
std::deque<T>
deque.push_back(3);
44 / 47
std::deque
begin data size
3
chunks
1
std::deque<T>
deque.push_back(4);
44 / 47
std::deque
begin data size
4
chunks
1
std::deque<T>
deque.push_back(4);
44 / 47
std::deque
begin data size
4
chunks
1
std::deque<T>
deque.push_back(5);
44 / 47
std::deque
begin data size
4
chunks
2
std::deque<T>
deque.push_back(5);
44 / 47
std::deque
begin data size
5
chunks
2
std::deque<T>
deque.push_back(5);
44 / 47
std::deque
begin data size
5
chunks
2
std::deque<T>
deque.pop_front();
44 / 47
std::deque
begin data size
4
chunks
2
std::deque<T>
deque.pop_front();
44 / 47
std::deque
begin data size
4
chunks
2
std::deque<T>
deque.erase(deque.begin() + 2);
44 / 47
std::deque
begin data size
3
chunks
2
std::deque<T>
deque.erase(deque.begin() + 2);
44 / 47
std::deque
begin data size
3
chunks
2
std::deque<T>
deque.erase(deque.begin() + 2);
44 / 47
std::deque
begin data size
3
chunks
2
std::deque<T>
deque.erase(deque.begin() + 2);
44 / 47
std::deque
begin data size
3
chunks
1
std::deque<T>
deque.erase(deque.begin() + 2);
45 / 47
std::deque
46 / 47
std::deque
47 / 47
Uses