在计算机图形学、地理信息系统(GIS)、机器人路径规划等领域,凸包算法是一个非常基础且重要的概念。本文将带你从零开始,用Java语言实现经典的凸包算法——Andrew算法(也称为单调链算法),即使你是编程小白,也能轻松理解并上手!
想象你有一堆钉子钉在木板上,然后用一根橡皮筋把它们全部套住。当你松开手,橡皮筋会自然收缩,最终只包裹住最外层的那些钉子。这些被包裹的钉子所形成的多边形,就是这组点的凸包(Convex Hull)。

Andrew算法是Graham扫描法的一种变体,具有以下优点:
这也是我们在Java凸包算法教学中首选它的原因。
Andrew算法的核心思想是将点集按x坐标(x相同时按y)排序,然后分别构建凸包的上半部分和下半部分:
首先,我们需要定义一个表示二维点的类:
class Point { int x, y; Point(int x, int y) { this.x = x; this.y = y; } @Override public String toString() { return "(" + x + ", " + y + ")"; }}接下来是核心的凸包算法实现:
import java.util.*;public class ConvexHull { // 计算叉积:(B - A) × (C - A) // > 0 表示 C 在 AB 左侧(逆时针) // < 0 表示 C 在 AB 右侧(顺时针) // = 0 表示三点共线 private static long cross(Point A, Point B, Point C) { return (long)(B.x - A.x) * (C.y - A.y) - (long)(B.y - A.y) * (C.x - A.x); } public static List<Point> convexHull(List<Point> points) { if (points.size() <= 1) return points; // 按 x 升序,x 相同按 y 升序 Collections.sort(points, (a, b) -> { return a.x != b.x ? a.x - b.x : a.y - b.y; }); // 构建下凸壳 List<Point> lower = new ArrayList<>(); for (Point p : points) { while (lower.size() >= 2 && cross(lower.get(lower.size() - 2), lower.get(lower.size() - 1), p) <= 0) { lower.remove(lower.size() - 1); } lower.add(p); } // 构建上凸壳 List<Point> upper = new ArrayList<>(); for (int i = points.size() - 1; i >= 0; i--) { Point p = points.get(i); while (upper.size() >= 2 && cross(upper.get(upper.size() - 2), upper.get(upper.size() - 1), p) <= 0) { upper.remove(upper.size() - 1); } upper.add(p); } // 合并:去掉首尾重复点(因为起点和终点被重复添加) lower.remove(lower.size() - 1); upper.remove(upper.size() - 1); lower.addAll(upper); return lower; } // 测试示例 public static void main(String[] args) { List<Point> points = Arrays.asList( new Point(0, 0), new Point(1, 1), new Point(2, 2), new Point(0, 2), new Point(2, 0), new Point(1, 0) ); List<Point> hull = convexHull(points); System.out.println("凸包顶点:" + hull); }}这个实现能正确处理各种边界情况,包括所有点共线、点数小于3等。
掌握凸包算法教程后,你可以将其应用于:
进阶方向包括:动态凸包维护、三维凸包、快速近似凸包等。但无论多复杂,都离不开今天学习的这个基础版本。
本文详细讲解了如何用Java语言实现Andrew算法来求解凸包问题。通过清晰的步骤说明和完整的代码示例,即使是初学者也能理解并运行这段计算几何Java代码。希望这篇凸包算法教程能为你打开计算几何的大门!
动手试试吧!修改点集,观察凸包的变化,加深理解。
本文由主机测评网于2025-12-10发表在主机测评网_免费VPS_免费云服务器_免费独立服务器,如有疑问,请联系我们。
本文链接:https://vpshk.cn/2025125617.html