[Algorithm][κ·Έλž˜ν”„] κΉŠμ΄μš°μ„ νƒμƒ‰(DFS, Depth First Search)

2025. 5. 5. 20:29Β·Computer Science/Algorithm

κΉŠμ΄μš°μ„ νƒμƒ‰(DFS)

이번 ν¬μŠ€νŠΈμ—μ„œλŠ” κ·Έλž˜ν”„ 탐색 μ•Œκ³ λ¦¬μ¦˜ 쀑 ν•˜λ‚˜μΈ κΉŠμ΄μš°μ„ νƒμƒ‰(DFS)에 λŒ€ν•΄μ„œ μ•Œμ•„λ³΄κ² μŠ΅λ‹ˆλ‹€.



κΉŠμ΄μš°μ„ νƒμƒ‰(DFS)μ΄λž€?

< κΉŠμ΄μš°μ„ νƒμƒ‰(DFS) κ³Όμ • >

  • κ·Έλž˜ν”„μ—μ„œ ν•œ λ°©ν–₯으둜 κ°€λŠ₯ν•œ κΉŠμ΄κΉŒμ§€ 계속 탐색 -> λ” 이상 갈 수 μ—†μœΌλ©΄ λ‹€μ‹œ λŒμ•„μ™€μ„œ λ‹€λ₯Έ λ°©ν–₯을 νƒμƒ‰ν•˜λŠ” λ°©μ‹μ˜ κ·Έλž˜ν”„ 순회 μ•Œκ³ λ¦¬μ¦˜μž…λ‹ˆλ‹€.
  • μŠ€νƒ(Stack) 자료ꡬ쑰의 λ™μž‘ 원리(LIFO)λ₯Ό λ”°λ¦…λ‹ˆλ‹€. -> μž¬κ·€ ν•¨μˆ˜ λ˜λŠ” λͺ…μ‹œμ  μŠ€νƒμœΌλ‘œλ„ κ΅¬ν˜„ κ°€λŠ₯
  • μˆ˜λ„ μ½”λ“œ(Pseudo Code)
u: ν˜„μž¬ 탐색 쀑인 정점
v: u의 μΈμ ‘ν•œ 정점
adj[u]: 정점 u에 μΈμ ‘ν•œ λͺ¨λ“  μ •μ λ“€μ˜ 리슀트
visited: 각 μ •μ μ˜ λ°©λ¬Έ μ—¬λΆ€λ₯Ό κΈ°λ‘ν•˜λŠ” λ°°μ—΄ λ˜λŠ” μ§‘ν•©

DFS(u):
    visited[u] ← true       // μ‹œμž‘ 정점 u λ°©λ¬Έ ν‘œμ‹œ
    u 처리                        // 정점 u 처리 (예: 좜λ ₯, κ²°κ³Ό μ €μž₯ λ“±)

    for each v in adj[u]:  // u의 λͺ¨λ“  인접 정점 v에 λŒ€ν•΄
        if not visited[v]:   // vλ₯Ό 아직 λ°©λ¬Έν•˜μ§€ μ•Šμ•˜λ‹€λ©΄
            DFS(v)              // v에 λŒ€ν•΄ DFS μž¬κ·€ 호좜



κΉŠμ΄μš°μ„ νƒμƒ‰ κ΅¬ν˜„ 방법

1. μž¬κ·€ν•¨μˆ˜ 호좜 μ „, λ°©λ¬Έμ—¬λΆ€ 확인

const int N = 4;
int visited[N];
vector<int> adj[N];

void dfs(int u) {
    visited[u] = true;

    for (int v: adj[u]) {
        if(visited[v]) continue; // 인접 정점 λ°©λ¬Έμ—¬λΆ€ 확인
        dfs(v);
    }
}

 

2. μž¬κ·€ν•¨μˆ˜ 호좜 ν›„, λ°©λ¬Έμ—¬λΆ€ 확인

const int N = 4;
int visited[N];
vector<int> adj[N];

void dfs(int u) {
    if (visited[u]) // μ‹œμž‘ 정점 λ°©λ¬Έμ—¬λΆ€ 확인
        return;

    visited[u] = true;
    for (int v: adj[u]) {
        dfs(v);
    }
}

 

λ¬Έμ œμ— 따라 각각의 κ΅¬ν˜„ 방법이 μœ μš©ν•  λ•Œκ°€ μžˆμœΌλ―€λ‘œ 2κ°€μ§€ μ½”λ“œ λͺ¨λ‘ μ΄ν•΄ν•˜κ³  κ΅¬ν˜„ν•˜λŠ” 것이 μ€‘μš”ν•©λ‹ˆλ‹€.



κΉŠμ΄μš°μ„ νƒμƒ‰μ˜ νŠΉμ§•

ν•­λͺ© μ„€λͺ…
μ‹œκ°„λ³΅μž‘λ„ \(O(V + E)\) (정점 + κ°„μ„  개수)
자료ꡬ쑰 μŠ€νƒ (λ˜λŠ” μž¬κ·€ 호좜 μŠ€νƒ)
μ‚¬μš© μ˜ˆμ‹œ 미둜 μ°ΎκΈ°, λ°±νŠΈλž˜ν‚Ή 문제, 사이클 κ²€μΆœ, μœ„μƒ μ •λ ¬ λ“±
κ΅¬ν˜„ 방식 μž¬κ·€ ν•¨μˆ˜ λ˜λŠ” λͺ…μ‹œμ  μŠ€νƒ μ‚¬μš©

 

⚠️ μ£Όμ˜ν•  점

  • λ¬΄ν•œ 루프 λ°©μ§€λ₯Ό μœ„ν•΄ visited μ²΄ν¬λŠ” κΌ­ ν•„μš”ν•©λ‹ˆλ‹€.
  • λ°©ν–₯ κ·Έλž˜ν”„μΌ 경우 λ°©ν–₯에 맞게만 탐색해야 ν•©λ‹ˆλ‹€.
  • μ—°κ²°λ˜μ§€ μ•Šμ€ κ·Έλž˜ν”„μ˜ λͺ¨λ“  정점을 νƒμƒ‰ν•˜λ €λ©΄ 반볡문으둜 λͺ¨λ“  정점 μ‹œμž‘ DFS μˆ˜ν–‰μ΄ ν•„μš”ν•©λ‹ˆλ‹€.



κΉŠμ΄μš°μ„ νƒμƒ‰ 예제

1. λ―Έλ‘œνƒˆμΆœ

  • μ„€λͺ…
    • N × M 크기의 λ―Έλ‘œμ—μ„œ μΆœλ°œμ μ—μ„œ λ„μ°©μ κΉŒμ§€ 갈 수 μžˆλŠ”μ§€ νŒλ³„ν•˜λŠ” 문제
    • 이동은 μƒν•˜μ’Œμš° μΈμ ‘ν•œ 칸으둜만 κ°€λŠ₯ν•˜λ©°, 이동할 수 μžˆλŠ” 칸은 1둜 ν‘œμ‹œλ˜μ–΄ μžˆμŠ΅λ‹ˆλ‹€. λ˜ν•œ, 벽은 0으둜 ν‘œμ‹œλ˜μ–΄ μžˆμŠ΅λ‹ˆλ‹€.
    • 좜발점(0, 0)μ—μ„œ 도착점(N-1, M-1)κΉŒμ§€ 도달 κ°€λŠ₯ν•˜λ©΄ '도착 κ°€λŠ₯', λΆˆκ°€λŠ₯ν•˜λ‹€λ©΄ '도착 λΆˆκ°€λŠ₯' 좜λ ₯
  • μž…λ ₯ μ˜ˆμ‹œ
5 6
1 0 1 0 1 0
1 1 1 1 1 0
0 0 0 0 1 0
1 1 1 0 1 0
0 0 1 1 1 1
  • 좜λ ₯ μ˜ˆμ‹œ
도착 κ°€λŠ₯
  • 아이디어
    • 1은 이동 κ°€λŠ₯ν•œ μΉΈ, 0은 λ²½
    • DFS둜 (0, 0)μ—μ„œ μ‹œμž‘ν•΄μ„œ (N-1, M-1)에 도달할 수 μžˆλŠ”μ§€ 확인
    • μƒν•˜μ’Œμš° λ°©ν–₯으둜 μ΄λ™ν•˜λ©° λ°©λ¬Έ 체크
  • μ •λ‹΅ μ½”λ“œ
#include <bits/stdc++.h>
using namespace std;

const int N = 5, M = 6;
int maze[N][M] = {
    {1, 0, 1, 0, 1, 0},
    {1, 1, 1, 1, 1, 0},
    {0, 0, 0, 0, 1, 0},
    {1, 1, 1, 0, 1, 0},
    {0, 0, 1, 1, 1, 1}
};
bool visited[N][M];

int dx[] = {-1, 1, 0, 0}; // μƒν•˜μ’Œμš°
int dy[] = {0, 0, -1, 1};

bool dfs(int x, int y) {
    if (x < 0 || y < 0 || x >= N || y >= M) return false;
    if (maze[x][y] == 0 || visited[x][y]) return false;

    visited[x][y] = true;
    if (x == N - 1 && y == M - 1) return true;

    for (int i = 0; i < 4; i++) {
        int nx = x + dx[i];
        int ny = y + dy[i];
        if (dfs(nx, ny)) return true;
    }

    return false;
}

int main() {
    if (dfs(0, 0)) cout << "도착 κ°€λŠ₯" << "\n";
    else cout << "도착 λΆˆκ°€λŠ₯" << "\n";
    return 0;
}

 

2. μ—°κ²° μš”μ†Œμ˜ 개수 κ΅¬ν•˜κΈ°

  • μ„€λͺ…
    • 무방ν–₯ κ·Έλž˜ν”„κ°€ μ£Όμ–΄μ‘Œμ„ λ•Œ, κ·Έλž˜ν”„μ˜ μ—°κ²° μš”μ†Œκ°€ λͺ‡ κ°œμΈμ§€ 좜λ ₯ν•˜λŠ” 문제
  • μž…λ ₯ μ˜ˆμ‹œ
    • 첫 μ€„μ—λŠ” μ •μ μ˜ 개수(N)와 κ°„μ„ μ˜ 개수(M)이 μ£Όμ–΄μ§‘λ‹ˆλ‹€.
    • λ‘λ²ˆμ§Έ 쀄뢀터 두 개의 μ—°κ²°λœ 정점이 각각 μ£Όμ–΄μ§‘λ‹ˆλ‹€.
6 5
1 2  
2 5  
5 1  
3 4  
4 6
  • 좜λ ₯ μ˜ˆμ‹œ
2
  • 아이디어
    • DFS둜 λ°©λ¬Έ κ°€λŠ₯ν•œ λͺ¨λ“  λ…Έλ“œλ₯Ό 순회
    • λ°©λ¬Έν•˜μ§€ μ•Šμ€ λ…Έλ“œμ—μ„œ DFSλ₯Ό μƒˆλ‘œ μ‹œμž‘ν•˜λ©΄ μ—°κ²° μš”μ†Œ +1
  • μ •λ‹΅ μ½”λ“œ
#include <bits/stdc++.h>
using namespace std;

const int MAX = 1001;
vector<int> adj[MAX];
bool visited[MAX];
int N = 6, M = 5;

void dfs(int u) {
    visited[u] = true;
    for (int v : adj[u]) {
        if (!visited[v])
            dfs(v);
    }
}

int main() {
    vector<pair<int, int>> edges = {
        {1, 2}, {2, 5}, {5, 1}, {3, 4}, {4, 6}
    };

    for (auto [u, v] : edges) {
        adj[u].push_back(v);
        adj[v].push_back(u); // 무방ν–₯ κ·Έλž˜ν”„
    }

    int components = 0;
    for (int i = 1; i <= N; i++) {
        if (!visited[i]) {
            dfs(i);
            components++;
        }
    }

    cout << "μ—°κ²° μš”μ†Œ 개수: " << components << "\n";
    return 0;
}



λ§ˆλ¬΄λ¦¬ν•˜λ©°

  • μ§€κΈˆκΉŒμ§€ DFS κ°œλ…μ— λŒ€ν•΄ μ•Œμ•„λ³΄λ©° DFSλŠ” ν•œ μ •μ μ—μ„œ μ‹œμž‘ν•΄ κ°€λŠ₯ν•œ ν•œ 깊이 λ“€μ–΄κ°”λ‹€κ°€ 더 이상 갈 곳이 μ—†μœΌλ©΄ λ˜λŒμ•„μ˜€λŠ” λ°©μ‹μœΌλ‘œ λ™μž‘ν•œλ‹€λŠ” 점을 μ΄ν•΄ν–ˆμŠ΅λ‹ˆλ‹€.
  • μž¬κ·€ 호좜 λ˜λŠ” μŠ€νƒμ„ μ΄μš©ν•΄ κ΅¬ν˜„ν•  수 있으며 이λ₯Ό 톡해 κ·Έλž˜ν”„ λ‚΄μ˜ μ—°κ²°μ„± 확인, 경둜 탐색, 사이클 μ—¬λΆ€ νŒλ‹¨ λ“± λ‹€μ–‘ν•œ 문제λ₯Ό ν•΄κ²°ν•  수 μžˆμŠ΅λ‹ˆλ‹€.
  • DFSλ₯Ό ν™•μ‹€νžˆ μ΄ν•΄ν•˜λ©΄ 이후 배우게 될 BFS(λ„ˆλΉ„ μš°μ„  탐색), μœ„μƒ μ •λ ¬, 트리 탐색, κ°•ν•œ μ—°κ²° μš”μ†Œ λ“±μ˜ κ°œλ…λ„ μ‰½κ²Œ 이해할 수 μžˆμŠ΅λ‹ˆλ‹€.
  • λ‹€μŒ κΈ€μ—μ„œλŠ” DFS와 μŒμ„ μ΄λ£¨λŠ” BFS(λ„ˆλΉ„ μš°μ„  탐색)에 λŒ€ν•΄ 닀뀄볼 μ˜ˆμ •μž…λ‹ˆλ‹€.

'Computer Science > Algorithm' μΉ΄ν…Œκ³ λ¦¬μ˜ λ‹€λ₯Έ κΈ€

[Algorithm][κ·Έλž˜ν”„] 트리 순회(Tree Traversal)  (0) 2025.05.06
[Algorithm][κ·Έλž˜ν”„] λ„ˆλΉ„μš°μ„ νƒμƒ‰(BFS, Breadth First Search)  (0) 2025.05.05
[Algorithm][κ·Έλž˜ν”„] 이둠 기초(κ·Έλž˜ν”„, 이진 트리, 인접행렬, μΈμ ‘λ¦¬μŠ€νŠΈ)  (1) 2025.05.05
[Algorithm][μ„±λŠ₯뢄석] κ³΅κ°„λ³΅μž‘λ„(Space Complexity)  (0) 2025.04.29
[Algorithm][μ„±λŠ₯뢄석] μ‹œκ°„λ³΅μž‘λ„(Time Complexity)  (0) 2025.04.27
'Computer Science/Algorithm' μΉ΄ν…Œκ³ λ¦¬μ˜ λ‹€λ₯Έ κΈ€
  • [Algorithm][κ·Έλž˜ν”„] 트리 순회(Tree Traversal)
  • [Algorithm][κ·Έλž˜ν”„] λ„ˆλΉ„μš°μ„ νƒμƒ‰(BFS, Breadth First Search)
  • [Algorithm][κ·Έλž˜ν”„] 이둠 기초(κ·Έλž˜ν”„, 이진 트리, 인접행렬, μΈμ ‘λ¦¬μŠ€νŠΈ)
  • [Algorithm][μ„±λŠ₯뢄석] κ³΅κ°„λ³΅μž‘λ„(Space Complexity)
_λŒ€λ‹ˆ_
_λŒ€λ‹ˆ_
  • _λŒ€λ‹ˆ_
    λŒ€λ‹ˆμ˜ Devlog πŸ‘¨‍πŸ’»
    _λŒ€λ‹ˆ_
  • 전체
    였늘
    μ–΄μ œ
    • λΆ„λ₯˜ 전체보기 (18)
      • Computer Science (17)
        • Algorithm (17)
      • Language (0)
        • Java (0)
      • Cloud (1)
        • Azure (Microsoft) (1)
        • NCP (Naver) (0)
        • GCP (Google) (0)
        • AWS (Amazon) (0)
  • λΈ”λ‘œκ·Έ 메뉴

    • ν™ˆ
    • νƒœκ·Έ
    • λ°©λͺ…둝
  • 링크

  • 곡지사항

  • 인기 κΈ€

  • νƒœκ·Έ

    μ•Œκ³ λ¦¬μ¦˜κΈ°μ΄ˆ
    ν”Œλ‘œμ΄λ“œμ›Œμ…œλΉ„κ΅
    κ·Έλž˜ν”„νƒμƒ‰
    μ΅œλ‹¨κ²½λ‘œ
    κ·Έλž˜ν”„
    bigo
    μ•Œκ³ λ¦¬μ¦˜
    o(logn)
    BFS
    μž¬κ·€ν•¨μˆ˜
    λΉ…μ˜€ν‘œκΈ°λ²•
    μˆœμ—΄μ‘°ν•©
    완전탐색
    μ½”λ”©ν…ŒμŠ€νŠΈ
    경우의수
    κ·Έλž˜ν”„μ•Œκ³ λ¦¬μ¦˜
    λ°±νŠΈλž˜ν‚Ή
    μ΅œμ ν™”
    μ΄μ§„νŠΈλ¦¬
    λ‹€μ΅μŠ€νŠΈλΌλΉ„κ΅
  • 졜근 λŒ“κΈ€

  • 졜근 κΈ€

  • hELLOΒ· Designed Byμ •μƒμš°.v4.10.3
_λŒ€λ‹ˆ_
[Algorithm][κ·Έλž˜ν”„] κΉŠμ΄μš°μ„ νƒμƒ‰(DFS, Depth First Search)
μƒλ‹¨μœΌλ‘œ

ν‹°μŠ€ν† λ¦¬νˆ΄λ°”