杰瑞科技汇

Python中如何计算多边形面积?

Of course! Calculating the area of a polygon is a classic problem in computational geometry. The most common and robust method is the Shoelace Formula (also known as Gauss's area formula).

Python中如何计算多边形面积?-图1
(图片来源网络,侵删)

I'll show you how to implement this in Python, starting with a simple version and then building up to a more robust, reusable function.

The Shoelace Formula (The Concept)

Imagine you list the vertices of your polygon in order (either clockwise or counter-clockwise). The Shoelace formula gets its name from the way you multiply the x-coordinate of each vertex by the y-coordinate of the next one, and vice-versa.

The formula is: Area = 1/2 * |sum(x_i * y_{i+1} - x_{i+1} * y_i)|

Where:

Python中如何计算多边形面积?-图2
(图片来源网络,侵删)
  • x_i, y_i are the coordinates of vertex i.
  • The sum is taken over all vertices.
  • The last vertex connects back to the first vertex (this is the "loop").
  • means you take the absolute value.
  • The final result is divided by 2.

Simple Python Implementation

Here is a basic function that takes a list of (x, y) tuples and returns the area.

def polygon_area(vertices):
    """
    Calculates the area of a polygon using the Shoelace formula.
    Args:
        vertices: A list of (x, y) tuples representing the vertices of the polygon.
                  The vertices must be ordered (clockwise or counter-clockwise)
                  and the first and last vertices should not be the same.
    Returns:
        The area of the polygon as a float.
    """
    n = len(vertices)
    area = 0.0
    for i in range(n):
        # Get the current vertex and the next vertex (wrapping around to the first)
        x_i, y_i = vertices[i]
        x_j, y_j = vertices[(i + 1) % n]
        # Apply the shoelace formula part
        area += (x_i * y_j) - (x_j * y_i)
    # The final area is half the absolute value of the sum
    area = abs(area) / 2.0
    return area
# --- Example Usage ---
# A simple square with vertices (0,0), (0,1), (1,1), (1,0)
square_vertices = [(0, 0), (0, 1), (1, 1), (1, 0)]
area_of_square = polygon_area(square_vertices)
print(f"Area of the square: {area_of_square}")  # Expected: 1.0
# A triangle with vertices (0,0), (2,0), (0,2)
triangle_vertices = [(0, 0), (2, 0), (0, 2)]
area_of_triangle = polygon_area(triangle_vertices)
print(f"Area of the triangle: {area_of_triangle}") # Expected: 2.0
# A more complex polygon
complex_vertices = [(0, 0), (2, 0), (3, 2), (1, 3), (-1, 1)]
area_of_complex = polygon_area(complex_vertices)
print(f"Area of the complex polygon: {area_of_complex}") # Expected: 6.0

A More Robust and Reusable Function

The simple version works, but it can be improved. A good function should:

  1. Handle edge cases (like an empty list or a polygon with less than 3 vertices).
  2. Automatically close the polygon if the first and last points are different (a common user input format).
  3. Be well-documented.

Here is a more robust version.

def calculate_polygon_area(vertices):
    """
    Calculates the area of a polygon using the Shoelace formula.
    This function is robust and handles common cases:
    - Automatically closes the polygon if the first and last vertices differ.
    - Returns 0.0 for invalid polygons (less than 3 vertices).
    Args:
        vertices: A list of (x, y) tuples representing the vertices of the polygon.
                  The vertices must be ordered (clockwise or counter-clockwise).
    Returns:
        The area of the polygon as a float. Returns 0.0 for invalid input.
    """
    # A polygon must have at least 3 vertices
    if len(vertices) < 3:
        return 0.0
    # Work with a mutable copy of the vertices list
    v = list(vertices)
    # Automatically close the polygon if it's not already closed
    if v[0] != v[-1]:
        v.append(v[0])
    n = len(v)
    area = 0.0
    for i in range(n - 1):  # Loop until the second-to-last point
        x_i, y_i = v[i]
        x_j, y_j = v[i + 1]
        area += (x_i * y_j) - (x_j * y_i)
    area = abs(area) / 2.0
    return area
# --- Example Usage with the robust function ---
# Same square, but now with an unclosed list
unclosed_square = [(0, 0), (0, 1), (1, 1), (1, 0)]
area_unclosed = calculate_polygon_area(unclosed_square)
print(f"Area of unclosed square: {area_unclosed}") # Expected: 1.0
# A polygon with a hole (this simple function cannot handle holes)
# For complex polygons with holes, you'd need a library like Shapely.
# This will just calculate the area of the outer boundary.
polygon_with_hole_boundary = [(0, 0), (10, 0), (10, 10), (0, 10), (0, 0), (2, 2), (2, 8), (8, 8), (8, 2), (2, 2)]
area_with_hole = calculate_polygon_area(polygon_with_hole_boundary)
print(f"Area of polygon with hole boundary: {area_with_hole}") # Incorrect result, but shows the function's limitation
# Invalid polygon (a line)
invalid_polygon = [(0, 0), (1, 0), (2, 0)]
area_invalid = calculate_polygon_area(invalid_polygon)
print(f"Area of invalid polygon: {area_invalid}") # Expected: 0.0

Using a Specialized Library (Shapely)

For any serious geospatial or geometric work, it's highly recommended to use a dedicated library like Shapely. It's fast, robust, and can handle much more complex cases (holes, different coordinate systems, etc.).

Python中如何计算多边形面积?-图3
(图片来源网络,侵删)

First, you need to install it:

pip install shapely

Here's how you would calculate the area using Shapely. The shapely.geometry.Polygon class is perfect for this.

from shapely.geometry import Polygon
# --- Example Usage with Shapely ---
# Define the polygon using the same list of vertices
square_vertices = [(0, 0), (0, 1), (1, 1), (1, 0)]
# Create a Polygon object
# Shapely automatically handles closing the polygon
p = Polygon(square_vertices)
# The area is a simple attribute of the object
area = p.area
print(f"Area of square using Shapely: {area}") # Expected: 1.0
# Example with a hole
# Holes are defined as a list of lists of coordinates
outer_ring = [(0, 0), (10, 0), (10, 10), (0, 10)]
inner_ring = [(2, 2), (2, 8), (8, 8), (8, 2)] # The hole
# The polygon constructor takes the outer ring and a list of inner rings
polygon_with_hole = Polygon(outer_ring, [inner_ring])
area_with_hole = polygon_with_hole.area
print(f"Area of polygon with hole using Shapely: {area_with_hole}") # Expected: 96.0 (100 - 4)

Summary: Which Method to Use?

Method Pros Cons Best For
Shoelace Formula (DIY) - No external dependencies.
- Good for learning the algorithm.
- Fast for simple cases.
- Not robust (handles no edge cases).
- Cannot handle polygons with holes.
- Prone to user error (e.g., wrong vertex order).
Quick scripts, coding interviews, or situations where you cannot install libraries.
Robust Shoelace Function - Handles common errors.
- No dependencies.
- More reliable than the simple version.
- Still cannot handle holes or complex geometry. General-purpose scripts where you need reliability but can't use external libraries.
Shapely Library - Extremely robust and well-tested.
- Handles holes, validity, and complex operations.
- Industry standard for geometry in Python.
- Requires an external installation (pip install shapely).
- Slight overhead for very simple polygons.
Almost all real-world applications, including GIS, data analysis, and any complex geometric task.
分享:
扫描分享到社交APP
上一篇
下一篇