๐Ÿ“’ CS/๐Ÿ“ Data Structure

[Data Structure] ๊ทธ๋ž˜ํ”„ - ์ธ์ ‘ํ–‰๋ ฌ๊ณผ ์ธ์ ‘๋ฆฌ์ŠคํŠธ

dana4056 2023. 8. 19. 00:47
320x100

๊ทธ๋ž˜ํ”„ (Graph)

๊ทธ๋ž˜ํ”„๋Š” ์ •์ ๊ณผ ๊ฐ„์„ ์œผ๋กœ ์ด๋ฃจ์–ด์ง„ ๋น„์„ ํ˜• ์ž๋ฃŒ ๊ตฌ์กฐ๋ฅผ ๋งํ•œ๋‹ค.

 

๐Ÿ”น์ •์ (V) (vertex) - ๊ทธ๋ž˜ํ”„ ๋‚ด์˜ ํ•˜๋‚˜์˜ ๊ฐœ๋ณ„์  ์š”์†Œ
๐Ÿ”น๊ฐ„์„ (E) (edge) - ์ •์ ๊ณผ ์ •์  ์‚ฌ์ด๋ฅผ ์—ฐ๊ฒฐํ•˜๋Š” ์„  (ํ๋ฆ„, ๊ด€๊ณ„ ํ‘œํ˜„)
๐Ÿ”น๊ฐ€์ค‘์น˜(W) (weight) - ๊ฐ„์„ ๊ณผ ์ •์  ์‚ฌ์ด์— ๋“œ๋Š” ๋น„์šฉ
๐Ÿ”น์ฐจ์ˆ˜ (degree) - ์ • ์ •์ ์— ์—ฐ๊ฒฐ๋œ ๊ฐ„์„ ์˜ ์ˆ˜
        โ—ฝout-degree: ๋‹ค๋ฅธ ์ •์ ์œผ๋กœ ๋‚˜๊ฐ€๋Š” ๊ฐ„์„  (์ˆ˜)
        โ—ฝin-degree: ํŠน์ • ์ •์ ์œผ๋กœ ๋“ค์–ด์˜ค๋Š” ๊ฐ„์„  (์ˆ˜)
        โ—ฝ๋ฌด๋ฐฉํ–ฅ ๊ทธ๋ž˜ํ”„์—์„  ํ•˜๋‚˜์˜ ๊ฐ„์„ ์ด ๋‘ ์ •์ ์— ์ธ์ ‘ํ•˜๋ฏ€๋กœ ๊ฐ„์„  ์ˆ˜์˜ ๋‘ ๋ฐฐ

๐Ÿ’ก ๋น„์„ ํ˜• ์ž๋ฃŒ ๊ตฌ์กฐ
๋น„์„ ํ˜• ์ž๋ฃŒ ๊ตฌ์กฐ๋ž€ ์ผ๋ ฌ๋กœ ๋‚˜์—ดํ•˜์ง€ ์•Š๊ณ  ์ž๋ฃŒ ์ˆœ์„œ๋‚˜ ๊ด€๊ณ„๊ฐ€ ๋ณต์žกํ•œ ๊ตฌ์กฐ๋ฅผ ๋งํ•œ๋‹ค.
์ผ๋ฐ˜์ ์œผ๋กœ ํŠธ๋ฆฌ๋‚˜ ๊ทธ๋ž˜ํ”„๋ฅผ ๋งํ•œ๋‹ค.

 

๋ฐฉํ–ฅ ๊ทธ๋ž˜ํ”„(Diredted Graph)
๊ทธ๋ž˜ํ”„์˜ ๊ฐ„์„ ์ด ํ•œ ์ •์ ์—์„œ ๋‹ค๋ฅธ ์ •์ ์œผ๋กœ์˜ ๋ฐฉํ–ฅ์„ ๊ฐ€์ง

 

๋ฌด๋ฐฉํ–ฅ ๊ทธ๋ž˜ํ”„(Undirected Graph)
๊ทธ๋ž˜ํ”„์˜ ๊ฐ„์„ ์— ๋ฐฉํ–ฅ์„ฑ์ด ์—†๋Š” ๊ทธ๋ž˜ํ”„

 

๊ฐ€์ค‘์น˜ ๊ทธ๋ž˜ํ”„(Weighted Graph)
๊ฐ„์„ ์— ๋น„์šฉ์ด๋‚˜ ๊ฐ€์ค‘์น˜๊ฐ€ ํ• ๋‹น๋œ ๊ทธ๋ž˜ํ”„

 

 

๊ทธ๋ž˜ํ”„ ๊ตฌํ˜„

๊ทธ๋ž˜ํ”„๋ฅผ ๊ตฌํ˜„ํ•˜๋Š” ๋ฐฉ์‹์œผ๋กœ๋Š” ํฌ๊ฒŒ ์ธ์ ‘ ๋ฆฌ์ŠคํŠธ์™€ ์ธ์ ‘ ํ–‰๋ ฌ์„ ์‚ฌ์šฉํ•˜๋Š” ๋ฐฉ์‹์œผ๋กœ ๋‚˜๋‰œ๋‹ค.

 

1๏ธโƒฃ์ธ์ ‘ ํ–‰๋ ฌ(Adjacency Matrix)

์ •๋ฐฉ ํ–‰๋ ฌ์„ ์‚ฌ์šฉํ•˜์—ฌ ๊ทธ๋ž˜ํ”„์˜ ์ •์  ๊ฐ„ ์—ฐ๊ฒฐ ๊ด€๊ณ„๋ฅผ ํ‘œํ˜„ํ•˜๋Š” ๋ฐฉ์‹์ด๋‹ค. ํ–‰๋ ฌ์˜ ๊ฐ ์›์†Œ(i,j)๋Š” ์ •์  i์™€ ์ •์  j ์‚ฌ์ด์˜ ๊ฐ„์„  ์—ฌ๋ถ€๋ฅผ ๋‚˜ํƒ€๋‚ธ๋‹ค. ๋ณดํ†ต 1์ธ ๊ฒฝ์šฐ๋Š” ๊ฐ„์„ ์ด ์กด์žฌํ•œ๋‹ค๋Š” ์˜๋ฏธ์ด๊ณ , 0์ธ ๊ฒฝ์šฐ๋Š” ๊ฐ„์„ ์ด ์—†์–ด ์—ฐ๊ฒฐ๋˜์–ด ์žˆ์ง€ ์•Š๋‹ค๋Š” ๊ฒƒ์„ ์˜๋ฏธํ•œ๋‹ค. ๊ฐ„์„ ์˜ ์ˆ˜๊ฐ€ ์ •์ ์˜ ์ˆ˜์— ๋น„ํ•ด ๋งŽ์€ ๊ทธ๋ž˜ํ”„์— ํšจ๊ณผ์ ์ด๋‹ค. (๊ฐ„์„ ์˜ ์ˆ˜๊ฐ€ ์ ์€ ๊ทธ๋ž˜ํ”„๋ฅผ ํ‘œํ˜„ํ•  ๋•Œ์—๋Š” ๋‚ญ๋น„๋˜๋Š” ํ–‰๋ ฌ์˜ ๊ณต๊ฐ„์ด ๋งŽ์•„์ ธ ๋น„ํšจ์œจ์ ์ด๋‹ค.)

 

๐Ÿ”น์ •์  ์ˆ˜ ๊ฐ€ n์ผ ๋•Œ, n*nํฌ๊ธฐ์˜ ํ–‰๋ ฌ ํ•„์š”
๐Ÿ”น๊ฐ ํ–‰๊ณผ ์—ด์€ ์ •์ ์„ ์˜๋ฏธ, ๊ฐ ์›์†Œ ๊ฐ’๋“ค์€ ๊ฐ„์„ ์„ ์˜๋ฏธ
๐Ÿ”น๋ฌด๋ฐฉํ–ฅ ๊ทธ๋ž˜ํ”„๋Š” ๋Œ€์นญ ๊ตฌ์กฐ
๐Ÿ”น๊ฐ€์ค‘์น˜ ๊ทธ๋ž˜ํ”„๋Š” ๋ณดํ†ต ๊ฐ€์ค‘์น˜ ๊ฐ’ ์ €์žฅ

๐Ÿ‘‰ ์žฅ๋‹จ์ 
๋‘ ์ •์ ์˜ ๊ฐ„์„  ์กฐํšŒ ์‹œ  O(1) ์˜ ์‹œ๊ฐ„ ์†Œ์š”
ํŠน์ • ์ •์  i์˜ ์ฐจ์ˆ˜๋ฅผ ๊ตฌํ•  ๋•Œ  O(n)  ์˜ ์‹œ๊ฐ„ ์†Œ์š” (i๋ฒˆ์งธ ํ–‰์˜ ๊ฐ’์„ ๋ชจ๋‘ ๋”ํ•˜์—ฌ ๊ตฌํ•  ์ˆ˜ ์žˆ์Œ)
๊ฐ„์„  ์ˆ˜์— ์ƒ๊ด€์—†์ด ๋ฌด์กฐ๊ฑด  n*n  ํฌ๊ธฐ์˜ ๋ฐฐ์—ด ํ•„์š”ํ•˜๋ฏ€๋กœ ๋ฉ”๋ชจ๋ฆฌ ๊ณต๊ฐ„ ๋‚ญ๋น„ํ•  ๊ฐ€๋Šฅ์„ฑ ๋†’์Œ
๊ทธ๋ž˜ํ”„์˜ ๋ชจ๋“  ๊ฐ„์„ ์˜ ์ˆ˜ ์•Œ์•„๋‚ผ ๋•Œ  O(n^2) ์†Œ์š”

 

โ˜• in java

package dataStructure;

public class ๊ทธ๋ž˜ํ”„_์ธ์ ‘ํ–‰๋ ฌ {
    public static void main(String[] args) {

        GraphAdjacencyMatrix graph = new GraphAdjacencyMatrix(4);

        // ๋ฌด๋ฐฉํ–ฅ ๊ทธ๋ž˜ํ”„(์–‘๋ฐฉํ–ฅ ๊ทธ๋ž˜ํ”„) ๊ฐ„์„  ์ถ”๊ฐ€
        graph.addEdge(1, 2, true);
        graph.addEdge(2, 3, true);
        graph.addEdge(2, 4, true);
        graph.addEdge(3, 4, true);

        // ๊ฐ„์„  ์กฐํšŒ
        System.out.println("Graph has edge between 1 and 2: " + graph.hasEdge(1, 2));
        System.out.println("Graph has edge between 1 and 4: " + graph.hasEdge(1, 4));
        graph.printGraph();
    }


    static class GraphAdjacencyMatrix {
        private int[][] graph;
        private int size;

        public GraphAdjacencyMatrix(int size) {
            // ํŽธ์˜์ƒ +1 ํฌ๊ธฐ ๋ฐฐ์—ด ์ƒ์„ฑ
            this.size = size;
            this.graph = new int[size+1][size+1];
        }

        // ๊ฐ„์„  ์ถ”๊ฐ€
        public void addEdge(int from, int to, boolean undirected) {
            graph[from][to] = 1;

            // ์–‘๋ฐฉํ–ฅ ๊ฐ„์„  ์ถ”๊ฐ€
            if (undirected) {
                graph[to][from] = 1;
            }
        }

        // ๊ฐ„์„  ํ™•์ธ
        public boolean hasEdge(int from, int to) {
            return graph[from][to] == 1;
        }

        // ๊ทธ๋ž˜ํ”„ ์ถœ๋ ฅ
        public void printGraph() {
            for(int i = 1; i <= size; i++) {
                for(int j = 1; j <= size; j++) {
                    System.out.print(" " + graph[i][j]);
                }
                System.out.println();
            }
        }
    }
}
Graph has edge between 1 and 2: true
Graph has edge between 1 and 4: false
 0 1 0 0
 1 0 1 1
 0 1 0 1
 0 1 1 0

 

2๏ธโƒฃ์ธ์ ‘ ๋ฆฌ์ŠคํŠธ(Adjacency List)

๊ทธ๋ž˜ํ”„์˜ ๊ฐ ์ •์ ๋งˆ๋‹ค ๊ทธ ์ •์ ๊ณผ ์—ฐ๊ฒฐ๋œ ๋‹ค๋ฅธ ์ •์ ๋“ค์˜ ๋ชฉ๋ก์„ ์ €์žฅํ•˜๋Š” ๋ฐฉ์‹์ด๋‹ค. ๊ฐ ์ •์ ๋งˆ๋‹ค ์—ฐ๊ฒฐ๋œ ์ •์ ๋“ค์„ ๋ฆฌ์ŠคํŠธ๋‚˜ ๋ฐฐ์—ด๋กœ ํ‘œํ˜„ํ•˜์—ฌ ๊ทธ๋ž˜ํ”„์˜ ๊ตฌ์กฐ๋ฅผ ํšจ์œจ์ ์œผ๋กœ ๋‚˜ํƒ€๋‚ผ ์ˆ˜ ์žˆ๋‹ค. ํŠนํžˆ, ์ •์  ์ˆ˜์— ๋น„ํ•ด ๊ฐ„์„  ์ˆ˜๊ฐ€ ์ ์€ ๊ทธ๋ž˜ํ”„์— ํšจ๊ณผ์ ์ด๋‹ค.

 

๐Ÿ”น์ •์  ๊ฐœ์ˆ˜๋งŒํผ ๋ฆฌ์ŠคํŠธ ํ•„์š”
๐Ÿ”น๊ฐ ๋ฆฌ์ŠคํŠธ์—” ์ธ์ ‘ํ•œ ์ •์ ์˜ ์ •๋ณด ์ €์žฅ
๐Ÿ”น๋ฌด๋ฐฉํ–ฅ ๊ทธ๋ž˜ํ”„์˜ ๊ฒฝ์šฐ ๊ฐ„์„  ์ถ”๊ฐ€ ์‹œ ๊ฐ ์ •์ ์˜ ๋ฐ˜๋Œ€ ์ •์  ๋ฆฌ์ŠคํŠธ์—๋„ ๋…ธ๋“œ ์ถ”๊ฐ€

 

์•„๋ž˜ ๊ทธ๋ฆผ์„ ๋ณด๋ฉด ๊ฐ ์ •์ ๋งˆ๋‹ค ์—ฐ๊ฒฐ๋œ ๋‹ค๋ฅธ ์ •์ ๋“ค์˜ ์ •๋ณด๋ฅผ ๋ฆฌ์ŠคํŠธ ํ˜•ํƒœ๋กœ ์ €์žฅํ•˜๊ณ  ์žˆ๋Š”๋ฐ, ์—ฐ๊ฒฐ ๋ฆฌ์ŠคํŠธ๋‚˜ ์ผ๋ฐ˜ ๋ฆฌ์ŠคํŠธ๋ฅผ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋‹ค. ์—ฐ๊ฒฐ ๋ฆฌ์ŠคํŠธ์— ๋น„ํ•ด ์ผ๋ฐ˜ ๋ฆฌ์ŠคํŠธ๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์ด ๊ตฌํ˜„์ด ์šฉ์ดํ•˜๋‹ค.

๐Ÿ‘‰ ์žฅ๋‹จ์ 
์—ฐ๊ฒฐ๋˜์–ด ์žˆ๋Š” ์ •์ ๋“ค์˜ ์ •๋ณด(๊ฐ„์„ )๋งŒ ๊ด€๋ฆฌํ•˜๋ฏ€๋กœ ๋ฉ”๋ชจ๋ฆฌ ์‚ฌ์šฉ ์ธก๋ฉด์—์„œ ํšจ์œจ์ 
๋‘ ์ •์ ์„ ์—ฐ๊ฒฐํ•˜๋Š” ๊ฐ„์„ ์„ ์กฐํšŒํ•˜๊ฑฐ๋‚˜ ์ •์ ์˜ ์ฐจ์ˆ˜๋ฅผ ์•Œ๊ธฐ ์œ„ํ•ด์„  ์ธ์ ‘ ๋ฆฌ์ŠคํŠธ๋ฅผ ํƒ์ƒ‰
→ ์ •์ ์˜ ์ฐจ์ˆ˜๋งŒํผ์˜ ์‹œ๊ฐ„ ํ•„์š”  O(degree(v)) 

 

โ˜• in java

package dataStructure;
import java.util.ArrayList;

public class ๊ทธ๋ž˜ํ”„_์ธ์ ‘๋ฆฌ์ŠคํŠธ {
    public static void main(String[] args) {
        int numNodes = 4;
        GraphAdjacencyList graph = new GraphAdjacencyList(numNodes);

        graph.addEdge(2, 1, false);
        graph.addEdge(2, 4, false);
        graph.addEdge(3, 2, false);
        graph.addEdge(4, 3, false);

        // ์ •์ ๋งˆ๋‹ค ์—ฐ๊ฒฐ๋œ ์ •์ ๋“ค ํ™•์ธ
        for (int i = 1; i <= numNodes; i++) {
            ArrayList<Integer> neighbors = graph.getAdjacentNodes(i);
            System.out.println("Node " + i + " is adjacent to: " + neighbors);
        }
    }

    static public class GraphAdjacencyList {
        private int numNodes;
        private ArrayList<ArrayList<Integer>> adjList;

        // ์ƒ์„ฑ์ž
        public GraphAdjacencyList(int numNodes) {
            // ๊ทธ๋ž˜ํ”„ ์ •์  ์ˆ˜๋งŒํผ ๋ฆฌ์ŠคํŠธ ์ƒ์„ฑ
            // ๋…ธ๋“œ ๋ฒˆํ˜ธ 1๋ถ€ํ„ฐ ์‹œ์ž‘ํ•˜๊ธฐ ์œ„ํ•ด ํŽธ์˜์ƒ + 1
            this.numNodes = numNodes + 1;
            adjList = new ArrayList<>(this.numNodes);

            // ๊ฐ ๋…ธ๋“œ๋งˆ๋‹ค ์—ฐ๊ฒฐ ์ •๋ณด ์ €์žฅํ•  ๋ฆฌ์ŠคํŠธ ์ƒ์„ฑ
            for (int i = 0; i <= numNodes; i++) {
                adjList.add(new ArrayList<>());
            }
        }

        // ๊ฐ„์„  ์ถ”๊ฐ€
        public void addEdge(int u, int v, boolean undirected) {
            adjList.get(u).add(v);

            // ๋ฌด๋ฐฉํ–ฅ ๊ทธ๋ž˜ํ”„์ผ ๋•Œ
            if(undirected){
                adjList.get(v).add(u);
            }
        }

        public ArrayList<Integer> getAdjacentNodes(int node) {
            return adjList.get(node);
        }
    }
}
Node 1 is adjacent to: []
Node 2 is adjacent to: [1, 4]
Node 3 is adjacent to: [2]
Node 4 is adjacent to: [3]
๋ฐ˜์‘ํ˜•