STL 기초, 객체지향 설계, 알고리즘 2문제
map<int, string> myMap = { {1, "Apple"}, {2, "Banana"}, {3, "Cherry"} } myMap[1] = "Alice" mymap.insert(make_pair(1, "Alice")); mymap.insert{(1, "Alice")}
이렇게 많이 값을 할당 할 수 있는데 어떤 차이 이고, 왜 이렇게 쓸까?
map<int, string> myMap = { {1, "Apple"}, {2, "Banana"}, {3, "Cherry"} }
myMap[1] = "Alice"
그냥 대입 방식인 이 두 방법은 기존 값이 있어도 덮어쓴다.
mymap.insert(make_pair(1, "Alice"));
mymap.insert{(1, "Alice")}
insert는 만약 값이 존재한다면 삽입하지 않음.
insert는 기존에 들어있는 데이터를 '원본'으로 간주하고 보호해야 할 때 사용.cout << it->first << "\n";
보면서 it은 뭔데 포인터의 전유물인 ->을 쓰는거지? 라는 의문점을 갖게 됨.
결론부터 말하면 진짜 메모리 주소(raw pointer)는 아니다. 하지만 C++ 개발자들은
"컨테이너의 요소를 가리키는 건 포인터와 사용법이 같아야 한다"
그래서 iterator(반복자)는 원본 데이터를 직접 들고 있는 게 아니라 원본을 가리키고 있다.
평소에 정의해둔 범위를 넘어가는 배열을 사용하면 오류가 나던게 왜 .end()도 배열의 범위를 넘어간 것인데 오류가 나지 않을까 궁금해졌다
end()를 쓸때는 end()의 값을 보는게 아니라 "여기는 끝입니다 !" 라는 end()라는 표지판을 보는 거기 때문
Q. end()는 왜 마지막 원소 다음을 가리키도록 설계 됐을까?
- find를 한다고 하면 실패한 상황을 잘 표현하기 위해 마지막 원소 값이 아닌 end를 반환.
reverse iterator 를 사용할 때 base() 가 필요한 이유reverse_iterator(역방향 반복자)의 .base()는 "현재 내가 가리키는 위치(현재위치 다음)를 담고 있는 진짜 순방향 화살표(iterator)를 그대로 반환하는 함수"
역방향으로 가고 있을때 distance를 구하려면 begin과 it은 방향이 달라 비교를 하지 못한다. 그래서 it.base()로 순방향 계산으로 바꾸는 것.
근데 왜 distance(.begin(), it.base() - 1)에서 -1을 할까? 그건 바로 it의 순방향 +1을 가리키고 있기 때문이다
distance를 구하려면 it.base() - 1 꼭 하셈 모르면 외워auto it = vec.begin(); 에서 auto는vector<int>::const_iterator를 변환해 준 것
= 가리키는 대상인 vector 내부의 값을 수정할 수 없는 '읽기 전용 iterator(반복자)
객체지향적 설계 SOLID원칙을 확인하며 지키는게 도움이 된다
* vector.pop_back() = 맨 끝 부터 지우는 STL 컨테이너
* vector.erase() = 특정 배열 지울 수 있는 STL 컨테이너
* map<const KEY, Value> = key와 값으로 매칭시키는 STL 컨테이너
- map<int, string> studentMap = { {101, "Alice"}, {2, "Appel"} }`
- studentMap[101] = "Alice";
- mymap.instert(make_pair(1, "Alice"));
- mymap.instert{(1, "Alice")};
* myMap.find(Key) = map에 존재하는지 확인 가능한 STL 컨테이너
* myMap.clear = 모든 원소를 삭제하는 STL 컨테이너
* sort(Betgin, End) = Begin 부터 End까지 오름차순으로 정렬
- sort(Begin, End, compare) = 여기서 bool compare(int a, int b) { return a > b;}이면 내림차순 정렬
* `Iterator` = 반복자
- begin() = 시작원소, end() = 끝 다음 원소
- rbegin() = 오른쪽 끝 원소, rend() = end()의 반대, 맨 처음 앞 원소
- it.base() = 현재 내가 가리키는 위치(현재위치 다음)를 담고 있는 순방향 화살표(iterator)를 그대로 반환하는 함수
* distance(begin(), end()); = 컨테이너 길이
* SOLID 원칙
- 단일 책임 원칙(SRP) = 각 클래스는 하나의 책임을 가져야 한다는 원칙
- 개방 폐쇄 원칙(OCP) = 확장에는 열려 있어야 하고, 수정에는 닫혀있어야 함
- 리스 코프 치환 원칙(LSP) = 자식 클래스는 부모 클래스에서 기대되는 행동을 보장해야 함
- 인터페이스 분리 원칙(ISP) = 클라이언트는 자신이 사용하지 않는 메서드에 의존하지 않아야함
- 의존 역전 원칙(DIP) = 고 수준 모듈은 저수준 모듈에 의존하지 않고 둘다 추상화에 의존해야 한다