
나는 이 포스트를 다시 봐야할 때에,
밑의 DFS 예제를 재귀함수 / 스택으로 구현해봐야하고,
BFS 예제를 큐로 구현해봐야하고,
음료수 얼려먹기 / 미로 찾기 문제를 풀어야한다.
1번 노드와 연결되어 있는 것 [2, 3, 8]
2번 노드와 연결되어 있는 것[1, 7]
이런 식이다.
그리고, 방문 여부를 표현하는 1차원 리스트를 정해준다.
1번 노드로 시작한다 (방문 1)
1번 노드와 인접한 노드들 중 방문하지 않은 노드[2, 3, 8]로 굴린다.
2부터 시작한다.
2는 방문하지 않았으므로, 재귀한다
2번 노드로 시작한다 (방문 1, 2)
1은 방문 했으므로 7로 재귀한다.
7번 노드로 시작한다 (방문 1, 2, 7)
2는 방문 했으므로, 6으로 재귀한다.
6번 노드로 시작한다 (방문 1,2,7,6)
7은 이미 방문했다. 6에 대한 재귀는 종료한다.
7번으로 돌아왔지만, 2와 6을 모두 방문했으므로 8로 재귀한다.
8번 노드로 시작한다. (방문 1,2,7,6,8)
1과 7은 모두 방문했으므로, 7번으로 돌아간다.
7번에서, 2와 6과 8은 모두 방문했으므로,
2번으로 돌아간다.
2번에서, 1과 7을 모두 방문했으므로,
1번으로 돌아간다.
1번에서, 2와 8을 모두 방문했으므로,
3번으로 재귀한다.
3번 노드로 시작한다. (방문 1,2,7,6,8,3)
3번에서, 1번은 방문했으므로 4번으로 재귀한다.
4번 노드로 시작한다. (방문 1,2,7,6,8,3,4)
3과 5는 방문했으므로, 3번으로 돌아간다.
3번에서, 1과 4는 방문했으므로,
5번으로 재귀한다.
5번 노드로 시작한다. (방문 1,2,7,6,8,3,5)
3과 4를 모두 방문했으므로, 3번으로 돌아간다.
3번에서, 인접한 노드를 모두 방문했으므로,
1번으로 돌아간다.
1번에서, 인접한 노드를 모두 방문했으므로,
함수가 종료된다.
방문순서 (1, 2, 7, 6, 8, 3, 5)
스택을 이용한 DFS는 어떻게 구현할까?
스택이 비어질 때 까지, (1로 돌아와서 1이 없어질 때 까지)
스택에 첫 노드를 넣고,
그 노드를 방문처리 해준다음,
그 노드와 인접한 노드들을 stack에 차례대로 넣는다.
오름차순으로 들어가기 때문에, pop을 이용해서 반복하게되면
인접한 노드들 중 가장 큰 값들을 기준으로 DFS를 하게 된다.
딕셔너리로도 그래프를 표현하기도 하는구나.
1을 큐에 넣고 방문처리한다.
queue에 든 게 없을 때 까지 반복문을 실행한다(마지막 1로 돌아오고 끝남)
큐의 맨 왼쪽 값을 v로 pop한다. (1 기준 [2,3,8]중 2부터 시작)
v의 인접 노드들 중에서, 방문하지 않은 노드가 있다면 큐에 넣고, 방문처리 한다.
1로 시작한다. (방문 1 / 큐 1)
v = 1로 팝한다.
1의 인접노드 [2,3,8] 중
2를 큐에 넣고, 방문처리한다 (방문 1, 2 / 큐 2)
3을 큐에 넣고, 방문처리한다. (방문 1,2,3 / 큐 2, 3)
8을 큐에 넣고, 방문처리한다. (방문 1,2,3,8 / 큐 2, 3, 8)
v = 2로 팝한다.(방문 1,2,3,8 / 큐 3, 8)
2의 인접노드 [1, 7]중 (1은 이미 방문)
7을 큐에 넣고, 방문처리한다.(방문 1,2,3,8,7 / 큐 3, 8, 7)
v = 3으로 팝한다. (방문 1,2,3,8,7 / 큐 8, 7)
3의 인접 노드 [1,4,5]중 (1은 이미 방문)
4를 큐에 넣고 방문 처리한다. (1,2,3,8,7,4 / 8,7,4)
5를 큐에 넣고 방문처리한다. (1,2,3,8,7,4,5 / 8,7,4,5)
v = 8로 팝한다. (1,2,3,8,7,4,5 / 7,4,5)
8의 인접노드 [1,7] 중
방문하지 않은 노드는 없으므로 넘어간다.
v = 7로 팝한다. (1,2,3,8,7,4,5 / 4,5)
7의 인접노드 [2,6,8] 중
6을 큐에 넣고, 방문처리한다. (1,2,3,8,7,4, 5, 6 / 4,5,6)
모든 노드를 방문했으므로 큐에 남아있는 4,5,6이 돌때까지 아무런 일도 일어나지 않는다.
popleft()가 반복되어서 큐에 아무것도 남지 않고 함수 실행이 끝난다.
어... 문제를 어떻게 풀어야 할지 감이 안 온다..
문제를 이해하고 노드가 어떻게 이어져 있는지에 대해서 떠올릴 수 있어야할 것 같다.
상하좌우 개념이 쓰인다 -> 2차원 배열을 떠올린다.
1. 그래프를 2차원 배열로 바꿀 수 있는가?
[[~~~~~~~~~~],
[~~~~~~~~~~],
[~~~~~~~~~~]]
와 같은 꼴에서 [x][y]로 그 지점을 빼낼 수 있다는 점.
2. 예외처리를 잘 했는가?
이게 중요한 것 같다. x나 y는 얼음틀(m*n) 안에 있어야하고, 0과 1의 값만을 가져야하니까.
3.재귀를 떠올릴 수 있는가?
한 지점으로부터 시작해서 재귀를 이용해서
그 주변 지점을 전부 바꾸는, 즉 음료수를 부어서 틀마다 넘치도록 채우게끔 하는 것이다.
4. 함수를 만들 때 어떤 값을 return할 지 떠올릴 수 있는가?
일단 나였으면 어떻게 저 칸을 센다는거지? 하는 생각이 있었는데,
칸막이를 기준으로 다 채워버리고, True를 리턴해서 그 수를 센다는 점이 신기하다.
1. 그래프를 2차원 배열로 바꿀 수 있는가?
2. 어떻게 풀지 생각했는가?
한 칸씩 가는데, 0으로는 가지 않고 1로만 가는 식으로 진행하면 되지 않을까?
최단 경로를 어떻게 식별하지..?
일단 상하좌우를 구현해야겠지?
.....
계속 머리 뜯으면서 생각해봤는데 어떻게 해야할지를 모르겠다..
해설을 보고 학습하고 유사한 문제로 복습해야지..
일단 답을 도출하기 위해서 어떤 식으로 변화가 일어날 지에 대한 그림조차 그리지 못했다.
음료수 얼려 먹기도 그렇고 미로 찾기도 그렇고,
또, 그 방법이나 그림을 알았다고 하더라도
구현을 하는 데에 있어서 아직 너무 부족하다.
특히, 어떤 변수를 설정해서 어떻게 쓸 지,
2차원 배열을 어떻게 노드로 생각해서 DFS나 BFS를 쓸 지, - 큐를쓰냐 스택을 쓰냐 느낌이긴 하다.
어떻게 제한 조건을 설정할지.. 등
비록 지금은 만져보지도 못하고 끝났지만,
해설이 최고의 풀이법이라고, 유사한 문제를 보게 된다면 어떻게든 풀어봐야지..
나의 미약함을 다시금 깨달았다..
어떤 놈인지는 알았다.. ㅠ
'CS > 자료구조-알고리즘' 카테고리의 다른 글
(파이썬)이분 탐색 - 숫자 카드 2 (3) | 2022.08.05 |
---|---|
구현 - 좌표이동 / 조건부 시각 세기 / 왕실의 나이트 (0) | 2022.06.22 |
그리디 알고리즘 (0) | 2022.06.21 |
(파이썬) 후위 표기식(postfix) 계산기 - 스택 (0) | 2022.06.21 |
(자료구조)순차적 자료구조/스택과 큐 - postfix 계산기와 첫 증발 (0) | 2022.06.20 |