Download as pptx, pdf, or txt
Download as pptx, pdf, or txt
You are on page 1of 74

SVNServetica

Medium
#9Slide03 Bebas Neue
Regular

#9Slide03 Maven Pro


SET PPT
I/. Sử dụng Set trong C+
+
II/. Multiset và
Unordered_set:
I/. Sử dụng Set trong
C++
I/. Sử dụng Set trong C++
1. Khái niệm kiểu dữ
liệu set:
-Trong C++, set là một associative
container của thư viện Template chuẩn C+
+ (STL) Hay nói cách khác, set là một
dạng cấu trúc dữ liệu dùng để lưu trữ các
phần tử có cùng kiểu dữ liệu, tuy nhiên các
phần tử đó không được lặp lại.
-Độ phức tạp: O(nlog(n))
I/. Sử dụng Set trong C++

2. Tính chất:
-Set là một container mà mỗi phần tử trong đó là duy nhất, tức là
sẽ không có hai phần tử có giá trị giống nhau tồn tại trong set.
-Các phần tử trong set-được gọi là khóa-có giá trị tăng dần về giá
trị số và tăng dần về thứ tự từ điển nếu là xâu kí tự. Mặc định
trong set là tăng dần và chúng ta có thể viết lại hàm so sánh theo
mục đích của chúng ta.]
I/. Sử dụng Set trong C++
3. Khai báo:
Để khai báo một set, ta sử dụng những cú pháp sau:
I/. Sử dụng Set trong C++

Ví dụ:
I/. Sử dụng Set trong C++
Mặc dù chúng ta có thể dùng bất cứ kiểu dữ liệu nào có
*Lưu ý: trong C++ để khai báo type, tuy nhiên do trong set các phần
tử cần phải được sắp xếp, nên kiểu của chúng cũng phải là
kiểu dữ liệu có thể được so sánh.
I/. Sử dụng Set trong C++
4. Các thao tác với set:
a) Duyệt set:
- Duyệt bằng iterator theo cú pháp:
I/. Sử dụng Set trong C++
Ví dụ: Với set integers={1,2,3,4,5}; đoạn chương trình
trên sẽ có kết quả là:
I/. Sử dụng Set trong C++
b) Truy cập các phần tử trong set:

-Truy cập tuần tự vào các phần tử của set, thông qua
vòng lặp hoặc là trình lặp
I/. Sử dụng Set trong C++

Ví dụ:

Truy cập vào phần tử


của set 1 chiều thông
qua vòng lặp dựa trên
phạm vi như sau:
I/. Sử dụng Set trong C++
I/. Sử dụng Set trong C++
I/. Sử dụng Set trong C++
I/. Sử dụng Set trong C++
I/. Sử dụng Set trong C++

5. Một số hàm trong set:

a) Insert():
-Hàm insert là một hàm thành viên trong class std:list, có tác dụng chèn
một hoặc nhiều phần tử vào set cũng như tăng độ dài tương ứng của nó và
tự động sắp xếp lại.
-Độ phức tạp: O(log(n))
I/. Sử dụng Set trong C++

- Chèn 1 phần tử:


+ Cú pháp: st.insert(value);
+ Cặp kết quả pair<iterator, bool> với iterator và bool, dưới dạng 0 hoặc
1.
+ Các phần tử trong một set là duy nhất.
+ Trong trường hợp tất cả các phần tử chèn vào vốn đã tồn tại từ trước
trong set, bản thân set ban đầu sẽ được trả về.
+ Phần tử trong set được sắp xếp theo thứ tự cụ thể trước khi được lưu.
I/. Sử dụng Set trong C++
I/. Sử dụng Set trong C++
I/. Sử dụng Set trong C++
MAP
I/. Map
II/. Multimap trong C++:
III/. Unorderd_map:
IV/. So sánh:
V/. BÀI TẬP
I/. Map
I/. Map
1. Khái niệm:

Map trong C++ là một tập hợp các phần tử được sắp xếp theo thứ tự cụ thể, mà
mỗi phần tử trong đó được hình thành bởi sự kết hợp của một cặp khóa và giá trị
(key & value), với mỗi khóa là duy nhất trong map. Các giá trị trong map thì có thể
trùng lặp, chúng có thể thay đổi giá trị, cũng như là được chèn hoặc xóa khỏi map.
Các cấu trúc dữ liệu như mảng hay xâu kí tự, khi truy xuất dữ liệu bạn sẽ sử dụng
một tham số gọi là chỉ số, ví dụ như arr[1], str[2], ... Đối với cấu trúc dữ liệu map,
để truy xuất dữ liệu bạn sẽ sử dụng một tham số gọi là key.
1. Khái niệm:

C++:
I/. Map
Cấu trúc dữ liệu Map trong C++:
- Cấu trúc dữ liệu map trong C++ thuộc dạng
Red–black tree (cây đỏ đen).
•Trong các Node sẽ lưu giữ cặp khóa, giá trị
(key & value) cũng như con trỏ của các Node
con ( bên trái, phải) của nó.
•Các giá trị trong Node thỏa mãn điều kiện giá
trị của Node con bên trái < Giá trị Node cha <
Giá trị của Node con bên phải.
•Độ sâu của các Node bằng nhau và cây Node
thì cân bằng.
2. Cấu trúc dữ liệu Map trong C++:

* Một số tính chất quan trọng:


- Các key trong map là riêng biệt, không có 2 key trùng nhau.
- Map duy trì thứ tự các phần tử theo giá trị key tăng dần.
- Map tìm kiếm giá trị key với độ phức tạp O(logN).
- Map không hỗ trợ truy cập thông qua chỉ số như mảng hay vector,
string.
- Mỗi phần tử trong map chính là 1 pair, với first lưu key và second
lưu value.
2. Cấu trúc dữ liệu Map trong C++:

Pair là gì?
- Pair nằm trong thư viện "utility" được sử dụng để kết hợp 2 kiểu dữ liệu
với nhau, nó cung cấp cách lưu trữ 2 giá trị đi kèm nhau nhưng chỉ sử dụng 1
biến.
- Phần tử thứ nhất của pair được gọi là first, phần tử thứ 2 của pair được gọi
là second.
- Cú pháp khai báo: pair<valueType1, valueType2> variableName;
2. Cấu trúc dữ liệu Map trong C++:

Ví dụ:
pair<string, string> dictionary;

Kết quả:
I/. Map

3. Std::map trong C++:


- std::map trong C++ là một thư viện
chuẩn được sử dụng để xử lý map
trong C++.
- std::map được cài sẵn trong header
file map và để sử dụng được chức
năng này, chúng ta cần thêm dòng
#include <map> vào đầu chương trình.
I/. Map

4. Khai báo map trong


C++:
- Để khai báo map trong C++, chúng ta viết dòng std::map, sau đó
viết kiểu dữ liệu của key và value cách nhau bởi dấu phẩy ở giữa
cặp dấu <>, và cuối cùng là tên biến map như sau:
std::map <k_type, v_type> mp;
- Trong đó mp là tên biến map và k_type, v_type lần lượt là kiểu dữ
liệu của key và value.
4. Khai báo map trong
C++:
- Trong trường hợp đã khai báo
namespace std vào đầu chương trình,
chúng ta cũng có thể lược bỏ dòng std:: Vd:
và dùng cú pháp khai báo map như sau:
std::map<std::string, int> mp;
map <k_type, v_type> mp;
mp["Mot"] = 1; // {"Mot", 1}
Sau khi đã khai báo map, chúng ta
mp["Hai"] = 2; // {"Hai", 2}
có thể gán giá trị các phần tử vào nó
bằng cách sử dụng toán tử [] với cú mp["Ba"] = 3; // {"Ba", 3}
pháp sau đây:
mp[key] = value;
4. Khai báo map trong
C++:
Chúng ta khởi tạo map trong C++ cách sử dụng cặp dấu ngoặc {} với cú pháp
sau đây:
std::map<k_type, v_type> mp = { {k1, v1}, {k2, v2}, {k3, v3}, ...};

* Lưu ý:
- Do mỗi khóa trong map là duy nhất, nên nếu chúng ta chỉ định các phần tử có
cùng khóa thì dù giá trị của chúng có giống hay khác nhau thì chỉ có duy nhất
phần tử viết đầu tiên sẽ được lưu vào trong map.
4. Khai báo map trong
C++:

Ví dụ:

Kết quả:
I/. Map

5. Truy cập phần tử trong


map C++:
a. Truy cập phần tử bằng toán tử []:
- Để truy cập phần tử trong map C++, chúng ta viết key của phần tử cần
truy cập vào giữa cặp toán tử [] với cú pháp sau đây:
mp[key]
- Nếu như key tồn tại trong map, giá trị tương ứng của key sẽ được trả
về. Tuy nhiên nếu không tồn tại, giá trị 0 sẽ được trả về.
5. Truy cập phần tử trong
map C++:
b. Truy cập phần tử bằng hàm at():
- Hàm at() trong C++ là một hàm thành viên trong class std:map, có
tác dụng truy cập vào phần tử trong map thông qua key của nó.
- Nếu như key tồn tại trong map, giá trị tương ứng của key sẽ được trả
về. Tuy nhiên nếu không tồn tại, hàm at() sẽ trả về lỗi out_of_range.
- Cú pháp truy cập phần tử trong map C++ bằng hàm at() trong C++
như sau:
mp.at(key);
5. Truy cập phần tử trong
map C++:
/*Khai báo và gán giá trị*/
Vd: std::map<std::string, int> mp;
mp["A"] = 1;
/*Truy cập vào phần tử vừa gán bằng key*/
cout << mp.at("A"); //kết quả: 1
/*Truy cập vào phần tử không tồn tại trong map*/
cout << mp.at("B"); // throwing an instance of
'std::out_of_range

-> Có thể thấy rõ sự khác biệt giữa cách truy cập phần tử trong map
bằng hàm at() và toán tử [] chính là ở kết quả khi chỉ định một key
không tồn tại trong map.
I/. Map
6. Duyệt map trong C++:
a. Duyệt map bằng iterator:
#include <iostream>
#include <algorithm>
#include <map>
using namespace std;
int main(){
map<int, int> mp;
mp={{1,2},{2,4},{3,5}};
map<int,int>::iterator it;
for(it = mp.begin(); it != mp.end(); it++){
cout << "key = " << (*it).first << ", value = " <<(*it).second << endl;
}}
6. Duyệt map trong C++:

key = 1, value = 2
key = 2, value = 4
Kết quả: key = 3, value = 5

Nếu bạn muốn truy cập vào phần tử đầu tiên trong map thì thông qua
iterator begin(), còn nếu muốn truy cập vào phần tử cuối cùng trong
map thì thông qua iterator rbegin().
6. Duyệt map trong C++:
b. Duyệt map bằng for each:
#include <iostream>
#include <algorithm>
#include <map>
using namespace std;
int main(){
map<int, int> mp;
mp={{1,2},{2,4},{3,5}};
for(pair<int, int> it : mp){ // Hoặc: for( auto it: mp )
cout << "key = " << it.first << ", value = " << it.second << endl;
}
}
6. Duyệt map trong C++:

map:
- auto là kiểu suy luận giúp tự xác định kiểu dữ liệu của giá trị lấy
từ map.
- it là tên một biến dùng để gán từng phần tử được lấy từ map.

key = 1, value = 2
Output : key = 2, value = 4
key = 3, value = 5
I/. Map
7. Một số hàm cơ bản của map:

a. Hàm insert:
- Đùng để thêm một phần tử vào trong map.
- Cú pháp: map[key]= value nếu key chưa tồn tại trong map
hoặc sẽ thay đổi value nếu key đã tồn tại.
7. Một số hàm cơ bản của map:
#include <bits/stdc++.h>
#include <map>
using namespace std;
int main() {
map<int, int> mp;
mp.insert({1,2}); // Thêm cặp (1,2)
mp.insert({2,4}); // Thêm cặp (2,4)
mp[3]=10;// Thêm cặp (3,10)
Ví dụ: mp[2]=5; // Thay đổi cặp (2,4) thành cặp
(2,5)
cout << "mp={\n";
for (auto it: mp) {
cout <<
"{"<<it.first<<","<<it.second<< '\n';
} cout<<"}"<<endl;
return 0;
}
7. Một số hàm cơ bản của map:

mp={
{1,2}
Kết quả: {2,5}
{3,10}
}
7. Một số hàm cơ bản của map:

b. Hàm size:
- Trả về số lượng phần tử trong map.
- Cú pháp: mp.size()

Lưu ý: số phần tử hay kích thước của


map ở đây được tính sau khi các phần tử
được kiểm tra key có trùng lặp và sắp xếp
trong map, chứ không phải là số phần tử
mà chúng ta đã dùng khi khai báo map.
7. Một số hàm cơ bản của map:

c. Hàm empty, clear:


- Hàm empty: kiểm tra map rỗng, nếu rỗng trả
về true, ngược lại trả về false.
- Hàm clear: xóa mọi phần tử trong map. Khác
với vector thì hàm map clear ngoài việc làm
trống map chỉ ddinhj thì còn giải phóng bộ nhớ
sử dụng cho việc lưu trữ dữ liệu đã dùng.
Cú pháp của 2 hàm này tương tự như hàm
size.
7. Một số hàm cơ bản của map:

d. Hàm find:
- Tìm kiếm sự xuất hiện của một key nào đó
trong map. Độ phức tạp là O(logN).
- Cú pháp: mp.find(key);
- Hàm này trả về iterator tới cặp phần tử nếu
nó tìm thấy, ngược lại nó trả về iterator end()
của map khi giá trị key tìm kiếm không tồn tại
trong map.
7. Một số hàm cơ bản của map:

e. Hàm count:
- Hàm này dùng để đếm số lần
xuất hiện của một key nào đó
trong map. Đối với map hàm
cout trả về 0 hoặc 1, có thể sử
dụng hàm này để thay cho hàm
find. Độ phức tạp là O(log N).
- Cú pháp: mp.cout(key);
7. Một số hàm cơ bản của map:

f. Hàm erase: Xóa thông qua giá trị của key:


- Hàm erase() có chức năng xóa 1 cặp phần Cú pháp: mp. erase(key);
tử trong map thông qua key với độ phức tạp
là O(log N), có 2 cách cơ bản sử dụng hàm
này là xóa thông qua giá trị hoặc xóa thông
qua iterator.
- Lưu ý: Trước khi sử dụng hàm erase hãy
đảm bảo phần tử bạn cần xóa có tồn tại
trong map, nếu không sẽ xảy ra lỗi runtime
error.
7. Một số hàm cơ bản của map:

rong C++:
- Xóa thông qua iterator:
Cú pháp: mp.erase(itr);

Trong đó, itr là trình lặp hoặc


là khóa của phần tử cần xóa.
Hàm sẽ xóa đi phần tử tại vị
trí mà trình lặp được xác định
bởi itr trỏ đến.
I/. Map
8. Ý nghĩa của map trong C++:
- Lưu trữ và truy xuất dữ liệu.
- Tối ưu hóa thời gian truy cập.
- Kiểm soát trùng lặp.
- Sắp xếp dữ liệu.
-…
I/. Map

9. Ứng dụng:

- Ta thường sử dụng Map ở các trường hợp sau:


+ Các bài toán liên quan tới tần suất của các phần tử.
+ Các bài toán cần tìm kiếm, thêm, xóa một cách nhanh chóng.
+ Dùng map thay cho các bài toán sử dụng mảng đánh dấu khi dữ liệu
không đẹp.
9. Ứng dụng:

Vd:
Cho một danh sách các số điện thoại kèm theo tên của chủ thuê bao đó.
Yêu cầu đầu vào là một số điện thoại (key), hãy đưa ra tên của chủ thuê
bao (value)
Cho danh sách thể hiện lịch sử đi muộn của các nhân viên một công ty
nào đó. Hãy tìm xem nhân viên (key) nào có số lần đi muộn (value)
nhiều nhất?
9. Ứng dụng:

for (int i=0; i<keysArray.size(); i++)


if (keysArray[i] == key) return valuesArray[i];
return "notFound";

Với đoạn mã như trên, độ phức tạp thuật toán sẽ là O(N).

if (mymap.find(key) != mymap.end()) return mymap[key];


else return "notFound";
II/. Multimap trong
C++
II/. Multimap trong C++
Multimap tương tự như map có điều khác biệt là trong multimap có
thể tồn tại nhiều key có cùng giá trị. Các tính chất như key được sắp
xếp tăng dần hay độ phức tạp, cách sử dụng hàm thì tương tự như
map.
Chú ý: Trong multimap bạn không thể truy cập value thông qua
key, hoặc gán theo cú pháp map[key] = value, vì các key có thể trùng
nhau.
Có 3 hàm có sự khác biệt so với map là: find, count, erase:
II/. Multimap trong C++
Hàm find:

- Vì trong multimap có nhiều key


có cùng giá trị nên nếu ta tìm
kiếm giá trị của 1 key nào đó, nó
sẽ trả về vị trí xuất hiện đầu tiên
của key đó trong multimap.
II/. Multimap trong C++

Hàm cout:
- Hàm count() trong multimap
khi bạn sử dụng để đếm số lần
xuất hiện của key, trả về giá trị
tương ứng với số cặp phần tử
có key tương ứng. Nếu key bạn
đếm không xuất hiện thì hàm
này trả về 0.
II/. Multimap trong C++

Hàm eraser:

- Nếu bạn xóa thông qua giá trị


của key, nó sẽ xóa toàn bộ cặp
phần tử có key tương ứng trong
multimap.
II/. Multimap trong C++

- Để xóa đi 1 cặp phần tử


duy nhất thì bạn nên xóa
thông qua iterator. Nó sẽ
xóa phần tử mà iterator đó
chỉ vào.
III/. Unorderd_map
III/. Unorderd_map

- Unordered_map
cũng tương tự như
map nhưng các key
trong unorderd_map
không có thứ tự như Vd:
map và multimap.
III/. Unorderd_map

- Cấu trúc dữ liệu của unordered_map trong c++ dựa


vào hash table- một bảng hash chứa các giá trị đã được
hash để so sánh các key của phần tử, và quyết định thứ
tự lưu giữ các phần tử này bên trong nó
- Cách sử dụng các hàm phổ biến như cout, find,…
trong Unordered_map không có gì khác biệt so với
map.
IV/. So sánh
IV/. So sánh

- Map, multimap và unordered_map cho phép bạn lưu trữ cặp khóa-giá
trị, trong khi set chỉ lưu trữ các giá trị.
- Map, multimap đảm bảo thứ tự của các phần tử dựa trên khóa, trong
khi Set được sắp xếp dựa trên giá trị của chúng và unordered_map thì
theo thứ tự giá trị hash của khóa.
- Set và unordered_map được sử dụng khi bạn quan tâm đến tính duy
nhất của các key, trong khi map được sử dụng khi bạn cần ánh xạ từ khóa
đến giá trị và ở multimap thì key có thể trùng nhau.
IV/. So sánh

- Ở map và multimap, các hàm có độ phức tạp là O(log n). Trong


khi unordered_map có độ phức tạp truy xuất O(1) trong trường
hợp tốt nhất, còn tệ nhất có thể lên đến O(N).
- Cấu trúc dữ liệu của set, map và multimap đều thuộc dạng cây
nhị phân Red–black tree (cây đỏ đen) còn unordered_map thì
theo giá trị trong bảng hash.
V/. Bài tập
1. Dự đoán output của chương trình sau:
1 3
2 4
2. Bài toán đếm tần suất
của phần tử trong mảng 2

Đề bài : Cho mảng A[] gồm N


(1≤N≤106) các số nguyên 32 bit, hãy
đếm xem mỗi giá trị trong mảng xuất
hiện bao nhiêu lần và in ra theo thứ tự
xuất hiện trong mảng, mỗi giá trị chỉ
liệt kê 1 lần.
3. Bài toán tìm tập hợp của 2
mảng

Đề bài : Cho mảng A[] và B[] gồm N, M


(1≤N, M≤106) các số nguyên 32 bit, hãy
tìm những giá trị xuất hiện ít nhất ở 1
trong 2 mảng và liệt kê theo thứ tự tăng
dần.

You might also like