λ³Έλ¬Έ λ°”λ‘œκ°€κΈ°
Problem Solving/C++ 정리

C++ 순차 μ»¨ν…Œμ΄λ„ˆ (vector, deque, list)

by 행뱁 2020. 5. 31.

vector<T>

νƒ€μž… Tλ₯Ό μ›μ†Œλ‘œ κ°–λŠ” 순차 μ»¨ν…Œμ΄λ„ˆλ‘œ ν˜„μž¬ ν• λ‹Ήλœ μš©λŸ‰(capacity)을 μ΄ˆκ³Όν•˜λŠ” μ¦‰μ‹œ 더 λ§Žμ€ μ›μ†Œλ₯Ό μ €μž₯ν•  수 μžˆλŠ” μΆ”κ°€ 곡간이 μžλ™μœΌλ‘œ ν• λ‹Ήλœλ‹€. μ»¨ν…Œμ΄λ„ˆμ˜ λμ—μ„œ μ›μ†Œλ₯Ό μΆ”κ°€ λ˜λŠ” μ‚­μ œν•  λ•Œλ§Œ νš¨μœ¨μ μ΄λ‹€.

- μš©λŸ‰/크기: capacity(), reserve(), size(), resize(), empty()

- μ›μ†Œ μ ‘κ·Ό: [], at(), front(), back()

- μ›μ†Œ μΆ”κ°€: push_back(), emplace_back(), emplace(), insert()

- μ›μ†Œ μ‚­μ œ: clear(), pop_back(), erase()

 

 

deque<T>

νƒ€μž… T의 μ›μ†Œλ“€μ„ deque(double-ended queue)둜 μ €μž₯ν•˜λŠ” μ»¨ν…Œμ΄λ„ˆμ΄λ‹€. μˆœμ°¨μ—΄μ˜ μ‹œμž‘μ΄λ‚˜ 끝에 객체듀을 효율적으둜 μΆ”κ°€ν•˜κ±°λ‚˜ μ‚­μ œν•  수 μžˆλ‹€. μ›μ†Œλ₯Ό μ €μž₯ν•˜λŠ” 방식 λ•Œλ¬Έμ— 크기(size)와 μš©λŸ‰μ΄(capacity) 항상 κ°™λ‹€.

- μš©λŸ‰/크기: capacity(), size(), resize(), empty()

- μ›μ†Œ μ ‘κ·Ό: [], at(), front(), back()

- μ›μ†Œ μΆ”κ°€: push_back(), push_front(), emplace_back(), emplace_front(), emplace(), insert()

- μ›μ†Œ μ‚­μ œ: clear(), pop_back(), pop_front(), erase()

 

 

list<T>

νƒ€μž… T 객체의 이쀑 μ—°κ²° 리슀트λ₯Ό κ΅¬ν˜„ν•œ μ»¨ν…Œμ΄λ„ˆμ΄λ‹€. vector, deque와 λΉ„κ΅ν•˜λ©΄ μˆœμ°¨μ—΄μ˜ μ–΄λŠ μœ„μΉ˜λΌλ„ μƒμˆ˜ μ‹œκ°„μ— μ›μ†Œλ₯Ό μ‚½μž… λ˜λŠ” μ‚­μ œν•  수 μžˆλ‹€λŠ” μž₯점이 μžˆλ‹€. ν•˜μ§€λ§Œ νŠΉμ • μœ„μΉ˜μ— μžˆλŠ” μ›μ†Œμ— λ°”λ‘œ μ ‘κ·Όν•  수 μ—†μ–΄ μ²˜μŒλΆ€ν„° λ§ˆμ§€λ§‰ μ›μ†ŒκΉŒμ§€ μˆœνšŒν•΄μ•Ό ν•œλ‹€λŠ” 단점이 μžˆλ‹€. 랜덀 μ—‘μ„ΈμŠ€ 반볡자λ₯Ό μ‚¬μš©ν•  수 μ—†κ³  μ–‘λ°©ν–₯ 반볡자λ₯Ό μ‚¬μš©ν•œλ‹€. μ–‘λ°©ν–₯ λ°˜λ³΅μžμ—λŠ” μ •μˆ˜λ₯Ό λ”ν•˜κ±°λ‚˜ λΊ„ 수 μ—†μœΌλ©° ++μ΄λ‚˜ --둜만 μˆ˜μ • κ°€λŠ₯ν•˜λ‹€. λ˜λŠ” iterator ν—€λ”μ˜ advance() ν•¨μˆ˜λ₯Ό μ΄μš©ν•  수 μžˆλ‹€. ( ex. advance(l.begin(), 10) )

- μš©λŸ‰/크기: capacity(), size(), resize(), empty()

- μ›μ†Œ μ ‘κ·Ό: [], at(), front(), back()

- μ›μ†Œ μΆ”κ°€: push_back(), push_front(), emplace_back(), emplace_front(), emplace(), insert()

- μ›μ†Œ μ‚­μ œ: clear(), pop_back(), pop_front(), erase(), remove()

 


 

μ΄ˆκΈ°ν™”: vector, deque, list λͺ¨λ‘ μ•„λž˜ λ°©λ²•μœΌλ‘œ μ΄ˆκΈ°ν™” κ°€λŠ₯

vector<int> v (n);                      // n개의 μ›μ†Œλ₯Ό κΈ°λ³Έκ°’μœΌλ‘œ μ΄ˆκΈ°ν™”
vector<int> v (n, x);                   // n개의 μ›μ†Œλ₯Ό xκ°’μœΌλ‘œ μ΄ˆκΈ°ν™”

vector<int> v {1, 2, 3, 4, 5};          // μ΄ˆκΈ°ν™” 리슀트둜 μ΄ˆκΈ°ν™”
vector<int> v {v2};                     // v2의 볡사본
vector<int> v {v2.begin(), v2.end()};   // 반볡자 λ²”μœ„λ₯Ό 지정해 μ΄ˆκΈ°ν™”

** uniform initialization (C++11~): https://modoocode.com/286

 

resize(): vector, deque, list λͺ¨λ‘ μ•„λž˜ λ°©λ²•μœΌλ‘œ resize κ°€λŠ₯

v.resize(n);        // sizeλ₯Ό n으둜 λ³€κ²½ν•˜λ˜, μΆ”κ°€λ˜λŠ” μ›μ†ŒλŠ” κΈ°λ³Έκ°’
v.resize(n, x);     // sizeλ₯Ό n으둜 λ³€κ²½ν•˜λ˜, μΆ”κ°€λ˜λŠ” μ›μ†ŒλŠ” xκ°’

vector<int> v {1, 2, 3};
v.resize(5);        // {1, 2, 3, 0, 0}
v.resize(7, 100);   // {1, 2, 3, 0, 0, 100, 100}
v.resize(6);        // {1, 2, 3, 0, 0, 100}

 

insert(): vector, deque, list λͺ¨λ‘ μ•„λž˜ λ°©λ²•μœΌλ‘œ insert κ°€λŠ₯

// 반볡자 pκ°€ κ°€λ¦¬ν‚€λŠ” μ›μ†Œ μ•žμ—
v.insert(p, x);                             // x μ‚½μž…
v.insert(p, n, x);                          // n개의 x μ‚½μž…
v.insert(p, b, e);                          // 반볡자 λ²”μœ„ [b, e)λ₯Ό μ‚½μž…

vector<int> v = {1, 2, 3};                  // {1, 2, 3}
v.insert(++v.begin(), 100);                 // {1, 100, 2, 3}
v.insert(++v.begin(), 2, 200);              // {1, 200, 200, 100, 2, 3}
v.insert(--v.end(), v2.begin(), v2.end());  // {1, 200, 200, 100, 2, ..., 3}

vectorλŠ” 끝이 μ•„λ‹Œ μœ„μΉ˜μ— μ‚½μž…ν•˜λ©΄ μ˜€λ²„ν—€λ“œκ°€ λ°œμƒν•œλ‹€. μ‚½μž… μœ„μΉ˜ 뒀에 μžˆλŠ” λͺ¨λ“  μ›μ†ŒλŠ” μƒˆ μ›μ†Œλ₯Ό μœ„ν•œ 곡간을 λ§Œλ“€κΈ° μœ„ν•΄ 이동해야 ν•œλ‹€. μ‚½μž… 이후에 μ›μ†Œμ˜ κ°œμˆ˜κ°€ ν• λ‹Ήλœ μš©λŸ‰(capacity)보닀 크닀면 λ©”λͺ¨λ¦¬λ„ 더 ν• λ‹Ήν•΄μ•Ό ν•œλ‹€. deque μ—­μ‹œ μ²˜μŒμ΄λ‚˜ 끝이 μ•„λ‹Œ μœ„μΉ˜μ— μ‚½μž…ν•˜λ©΄ μ˜€λ²„ν—€λ“œκ°€ λ°œμƒν•˜κ³  λͺ¨λ“  λ°˜λ³΅μžκ°€ λ¬΄νš¨ν™”λœλ‹€. κ·ΈλŸ¬λ‚˜ listλŠ” μ›μ†Œλ₯Ό μ‚½μž…ν•œλ‹€κ³  κΈ°μ‘΄ μ›μ†Œλ₯Ό 이동할 ν•„μš” 없이 ν¬μΈν„°λ§Œ λ°”κΏ”μ£Όλ©΄ λœλ‹€. μƒμˆ˜ μ‹œκ°„μ— μ²˜λ¦¬ν•  수 있으며 λ°˜λ³΅μžλ„ λ¬΄νš¨ν™”λ˜μ§€ μ•ŠλŠ”λ‹€. listμ—μ„œ λ°˜λ³΅μžκ°€ λ¬΄νš¨ν™”λ  λ•ŒλŠ” ν•΄λ‹Ή λ°˜λ³΅μžκ°€ κ°€λ¦¬ν‚€λŠ” μ›μ†Œκ°€ μ‚­μ œλ˜μ—ˆμ„ λ•Œ 뿐이닀.

 

erase(): vector, deque, list λͺ¨λ‘ μ•„λž˜ λ°©λ²•μœΌλ‘œ erase κ°€λŠ₯

v.erase(p);     // 반볡자 pκ°€ κ°€λ¦¬ν‚€λŠ” μ›μ†Œλ₯Ό μ‚­μ œν•˜κ³  κ·Έ λ‹€μŒ μ›μ†Œλ₯Ό λ°˜ν™˜
v.erase(b, e);  // 반볡자 λ²”μœ„ [b, e)의 μ›μ†Œλ₯Ό μ‚­μ œν•˜κ³  κ·Έ λ‹€μŒ μ›μ†Œλ₯Ό λ°˜ν™˜

vector<int> v {1, 2, 3, 4, 5};      // {1, 2, 3, 4, 5}
v.erase(++v.begin());               // {1, 3, 4, 5}
v.erase(++v.begin(), --v.end())	    // {1, 5}

vectorλŠ” erase둜 크기(size)κ°€ λ³€κ²½λ˜μ–΄λ„ μš©λŸ‰(capacity)λŠ” λ³€κ²½λ˜μ§€ μ•ŠλŠ”λ‹€. listλŠ” μ—­μ‹œ μƒμˆ˜ μ‹œκ°„μ— μ›μ†Œλ₯Ό μ‚­μ œν•  수 μžˆλ‹€.

 


algorithm ν—€λ”μ˜ μœ μš©ν•œ ν•¨μˆ˜

swap(), find(), copy(), sort(), reverse()

swap(Tx, Ty);       // 객체 Tx와 객체 Tyλ₯Ό swap
find(b, e, x);      // 반볡자 ꡬ간 [b, e)μ—μ„œ xλ₯Ό μ°Ύμ•„ κ°€λ¦¬ν‚€λŠ” 반볡자λ₯Ό λ°˜ν™˜
copy(sb, se, db);   // src의 반볡자 ꡬ간 [sb, se)λ₯Ό dst의 반볡자 dbκ°€ κ°€λ¦¬ν‚€λŠ” κ³³λΆ€ν„° 볡사
sort(b, e);         // 반볡자 ꡬ간 [b, e)λ₯Ό κΈ°λ³Έ μ˜€λ¦„μ°¨μˆœμœΌλ‘œ μ •λ ¬
sort(b, e, comp);   // 반볡자 ꡬ간 [b, e)λ₯Ό comp에 따라 μ •λ ¬ (compκ°€ greater<>()일 경우 λ‚΄λ¦Όμ°¨μˆœ μ •λ ¬)
reverse(b, e);      // 반볡자 ꡬ간 [b, e)의 μˆœμ„œλ₯Ό λ’€λ°”κΏˆ

** remove μΆ”κ°€: http://egloos.zum.com/h2ostudio/v/4343561

removeλŠ” μ–΄λ–€ 값을 κ°€μ§€λŠ” μ›μ†Œλ₯Ό μ‚­μ œν•΄μ£Όμ§€λ§Œ, μ§„μ§œλ‘œ μ‚­μ œν•˜μ§„ μ•ŠλŠ”λ‹€.

 

list의 sort()

sort()λŠ” 랜덀 μ—‘μ„ΈμŠ€ λ°˜λ³΅μžκ°€ ν•„μš”ν•˜λ―€λ‘œ listμ—λŠ” μ‚¬μš©ν•  수 μ—†λ‹€. λŒ€μ‹  list ν…œν”Œλ¦Ώμ— sort() ν•¨μˆ˜κ°€ λ³„λ„λ‘œ μ •μ˜λ˜μ–΄ μžˆλ‹€. 두 버전이 μžˆλŠ”λ° μΈμˆ˜κ°€ μ—†λŠ” 버전은 μ›μ†Œλ₯Ό μ˜€λ¦„μ°¨μˆœμœΌλ‘œ μ •λ ¬ν•˜λ©°, μΈμˆ˜κ°€ μžˆλŠ” 버전은 비ꡐλ₯Ό μœ„ν•œ λžŒλ‹€ ν‘œν˜„μ‹μ΄λ‚˜ ν•¨μˆ˜ 객체λ₯Ό 인수둜 λ°›λŠ”λ‹€.

l.sort()
l.sort(greater<>());

 

 


Reference: C++14 STL μ² μ € μž…λ¬Έ

λŒ“κΈ€