Java数据结构之加权无向图的设计实现

yizhihongxing

Java数据结构之加权无向图的设计实现

前言

在计算机科学中,图(Graph)作为一种基本数据结构,被广泛应用于各种领域,如网络流、图像处理、计算机视觉等。本文将介绍加权无向图(Weighted Undirected Graph)的设计实现,涉及图的存储、添加边、获取特定节点的相邻节点、计算最短路径等。

设计实现

存储结构

加权无向图可以用一个邻接表数组存储,其中每个邻接表包含该节点相连的边和权值。每个节点的信息可以用一个 Map 存储,其中键为节点名称,值为相应节点的邻接表。

public class WeightedUndirectedGraph {
    private final Map<String, List<Edge>> graph = new HashMap<>();

    // add undirected edge to the graph
    public void addEdge(String node1, String node2, int weight) {
        addDirectedEdge(node1, node2, weight);
        addDirectedEdge(node2, node1, weight);
    }

    // add directed edge to the graph
    private void addDirectedEdge(String startNode, String endNode, int weight) {
        List<Edge> edges = graph.get(startNode);
        if (edges == null) {
            edges = new ArrayList<>();
            graph.put(startNode, edges);
        }
        edges.add(new Edge(startNode, endNode, weight));
    }
}

class Edge {
    String startNode;
    String endNode;
    int weight;

    Edge(String startNode, String endNode, int weight) {
        this.startNode = startNode;
        this.endNode = endNode;
        this.weight = weight;
    }
}

获取特定节点的相邻节点

通过节点名称从图中获取该节点的相邻节点,只需要在 Map 中查找相应的邻接表即可。

List<String> getNeighbors(String node) {
    List<Edge> edges = graph.get(node);
    if (edges == null) {
        return Collections.emptyList();
    }
    List<String> neighbors = new ArrayList<>();
    for (Edge edge : edges) {
        neighbors.add(edge.endNode);
    }
    return Collections.unmodifiableList(neighbors);
}

计算最短路径

实现最短路径算法,可以使用 Dijkstra 算法或 Bellman-Ford 算法。下面给出使用 Dijkstra 算法计算最短路径的代码示例。

Map<String, Integer> calculateShortestPath(String startNode) {
    Map<String, Integer> distances = new HashMap<>();
    for (String node : graph.keySet()) {
        distances.put(node, Integer.MAX_VALUE);
    }
    distances.put(startNode, 0);

    PriorityQueue<Node> queue = new PriorityQueue<>(Comparator.comparingInt(n -> n.distance));
    queue.offer(new Node(startNode, 0));

    Set<String> visited = new HashSet<>();

    while (!queue.isEmpty()) {
        Node node = queue.poll();
        if (visited.contains(node.name)) {
            continue;
        }
        visited.add(node.name);
        List<Edge> edges = graph.get(node.name);
        if (edges == null) {
            continue;
        }
        for (Edge edge : edges) {
            if (visited.contains(edge.endNode)) {
                continue;
            }
            int distance = distances.get(node.name) + edge.weight;
            if (distance < distances.get(edge.endNode)) {
                distances.put(edge.endNode, distance);
                queue.offer(new Node(edge.endNode, distance));
            }
        }
    }
    return Collections.unmodifiableMap(distances);
}

class Node {
    String name;
    int distance;

    Node(String name, int distance) {
        this.name = name;
        this.distance = distance;
    }
}

示例说明

添加边

使用 addEdge() 方法添加边,如下所示:

WeightedUndirectedGraph graph = new WeightedUndirectedGraph();
graph.addEdge("A", "B", 4);
graph.addEdge("A", "C", 2);
graph.addEdge("B", "C", 1);
graph.addEdge("B", "D", 5);
graph.addEdge("C", "D", 8);

计算最短路径

使用 calculateShortestPath() 方法计算两个节点之间的最短路径,例如从节点 "A" 到节点 "D" 的最短路径:

Map<String, Integer> shortestPath = graph.calculateShortestPath("A");
Integer distance = shortestPath.get("D"); // distance == 6

总结

本文介绍了加权无向图的设计实现,包括存储结构、获取相邻节点、计算最短路径等操作,并给出了相关代码实现。通过本文的学习,读者能够深入理解加权无向图的实现原理,为后续的算法实现奠定基础。

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:Java数据结构之加权无向图的设计实现 - Python技术站

(0)
上一篇 2023年5月17日
下一篇 2023年5月17日

相关文章

  • C语言超详细讲解双向带头循环链表

    C语言双向带头循环链表 基本概念 带头双向循环链表是指在双向循环链表的基础上,在头节点前面添加一个头结点。这个头结点不存储任何数据,只是为了方便对链表进行操作。循环链表则是在单向或双向链表的基础上,使链表的头节点与尾节点相连,形成一个环。 综合这两种链表,就构成了“双向带头循环链表”这种数据结构。双向带头循环链表是一种灵活性较高的数据结构,支持前插、后插、前…

    数据结构 2023年5月17日
    00
  • C语言数据结构之栈和队列的实现及应用

    C语言数据结构之栈和队列的实现及应用 什么是栈和队列? 栈是一种具有后进先出(LIFO)特性的线性数据结构,可以理解为一个只能在一端进行插入和删除操作的数据结构。通常称插入元素的一端为栈顶,删除元素的一端为栈底。 队列是一种具有先进先出(FIFO)特性的线性数据结构,可以理解为一个只能在两端进行插入和删除操作的数据结构。一端进行插入操作,称之为队尾,一端进行…

    数据结构 2023年5月17日
    00
  • C++高级数据结构之优先队列

    C++高级数据结构之优先队列 什么是优先队列? 优先队列是一种特殊的队列,其中每个元素都有一个优先级。当加入一个元素时,它会被放置在队列中的适当位置,以确保优先级最高的元素位于队头。从队列中取出元素时,总是从队头删除元素。 优先队列的应用 优先队列的常见应用场景包括: 操作系统任务调度 网络传输协议TCP中的拥塞控制算法 各种图像算法如边缘检测等 C++中S…

    数据结构 2023年5月17日
    00
  • 题目 3158: 蓝桥杯2023年第十四届省赛真题-三国游戏(贪心)

    题目描述 小蓝正在玩一款游戏。游戏中魏蜀吴三个国家各自拥有一定数量的士兵X, Y, Z (一开始可以认为都为 0 )。游戏有 n 个可能会发生的事件,每个事件之间相互独立且最多只会发生一次,当第 i 个事件发生时会分别让 X, Y, Z 增加Ai , Bi ,Ci 。当游戏结束时 (所有事件的发生与否已经确定),如果 X, Y, Z 的其中一个大于另外两个之…

    算法与数据结构 2023年4月30日
    00
  • java数据结构实现顺序表示例

    如果想要实现一种数据结构,我们首先需要考虑它的存储结构。对于顺序存储结构,Java中的数组是一个很好的选择。下面就为大家分享关于Java数据结构实现顺序表示例的完整攻略,帮助读者更好地理解该数据结构的实现方式。 1. 定义一个顺序表数组 首先,我们需要定义一个数组类型的顺序表。这个顺序表可以使用泛型来表示各种类型的数据: public class MyArr…

    数据结构 2023年5月17日
    00
  • 【ACM算法竞赛日常训练】DAY5题解与分析【储物点的距离】【糖糖别胡说,我真的不是签到题目】| 前缀和 | 思维

    DAY5共2题: 储物点的距离(前缀和) 糖糖别胡说,我真的不是签到题目(multiset,思维) ? 作者:Eriktse? 简介:19岁,211计算机在读,现役ACM银牌选手?力争以通俗易懂的方式讲解算法!❤️欢迎关注我,一起交流C++/Python算法。(优质好文持续更新中……)?? 原文链接(阅读原文获得更好阅读体验):https://www.eri…

    算法与数据结构 2023年4月18日
    00
  • java数据结构排序算法之树形选择排序详解

    Java数据结构排序算法之树形选择排序详解 什么是树形选择排序 树形选择排序是对选择排序的一种改进和优化,它是通过利用完全二叉树的性质对选择排序进行了改进而得到的一种高效的排序算法。 树形选择排序通过将待排序的元素构建成一颗完全二叉树,然后从叶子节点向上比较,选择出最小的元素,并交换位置。这样子,每次选择最小元素的时候,减少了元素之间的比较次数,从而提高了排…

    数据结构 2023年5月17日
    00
  • C语言线性表之双链表详解

    C语言线性表之双链表详解 前言 本教程将详细介绍C语言中双链表的实现方法以及相关操作,适合有一定C语言基础的读者。 双链表定义 双链表是一种常见的数据结构,与单链表不同,双链表中每个节点不仅有指向后续节点的指针,还有指向前续节点的指针,即“双向链表”。 双链表的节点结构体可以定义如下: typedef struct double_node{ int data…

    数据结构 2023年5月17日
    00
合作推广
合作推广
分享本页
返回顶部