最小有向包围盒——2D平面

目录

介绍

主要步骤

代码

__init__.py

min_bounding_rect.py

min_rect.py

qhull_2d.py

结果


介绍

最小有向包围盒算法广泛应用于多个领域,包括:

  • 计算几何:用于分析点集的边界特征。
  • 图形学:用于碰撞检测和物体包围。
  • 数据科学:在聚类分析、异常值检测等场景中用于计算数据的紧致边界。

本文提出了一种基于凸包和最小矩形算法的二维最小有向包围盒计算方法,并展示了如何通过代码实现这一算法。

主要步骤

  1. 凸包计算:使用 qhull2D 方法计算输入点集的凸包。这一步可以确保我们找到点集的外部边界,以此作为最小矩形的候选边界。
  2. 最小矩形计算:利用 minBoundingRect 算法计算最小有向包围盒。算法返回矩形的宽度、高度、角点坐标和面积。

程序结构如下:

调用入口:

输入为numpy格式的n*2数组。

代码

__init__.py

from .min_rect import *
from .qhull_2d import *
from .min_bounding_rect import *

min_bounding_rect.py

import numpy as np
import sysdef minBoundingRect(hull_points_2d):# Compute edges (x2-x1, y2-y1)edges = np.zeros((len(hull_points_2d)-1, 2))  # empty 2 column arrayfor i in range(len(edges)):edge_x = hull_points_2d[i+1, 0] - hull_points_2d[i, 0]edge_y = hull_points_2d[i+1, 1] - hull_points_2d[i, 1]edges[i] = [edge_x, edge_y]# Calculate edge angles   atan2(y/x)edge_angles = np.zeros(len(edges))  # empty 1 column arrayfor i in range(len(edge_angles)):edge_angles[i] = np.arctan2(edges[i, 1], edges[i, 0])# Check for angles in 1st quadrantedge_angles = np.abs(edge_angles % (np.pi/2))  # want strictly positive answers# Remove duplicate anglesedge_angles = np.unique(edge_angles)# Test each angle to find bounding box with smallest areamin_bbox = (0, sys.maxsize, 0, 0, 0, 0, 0, 0)  # rot_angle, area, width, height, min_x, max_x, min_y, max_y# print("Testing", len(edge_angles), "possible rotations for bounding box... \n")for i in range(len(edge_angles)):# Create rotation matrix to shift points to baselineR = np.array([[np.cos(edge_angles[i]), np.cos(edge_angles[i]-(np.pi/2))],[np.cos(edge_angles[i]+(np.pi/2)), np.cos(edge_angles[i])]])# Apply this rotation to convex hull pointsrot_points = np.dot(R, np.transpose(hull_points_2d))  # 2x2 * 2xn# Find min/max x,y pointsmin_x = np.nanmin(rot_points[0], axis=0)max_x = np.nanmax(rot_points[0], axis=0)min_y = np.nanmin(rot_points[1], axis=0)max_y = np.nanmax(rot_points[1], axis=0)# Calculate height/width/area of this bounding rectanglewidth = max_x - min_xheight = max_y - min_yarea = width * height# Store the smallest rect found firstif area < min_bbox[1]:min_bbox = (edge_angles[i], area, width, height, min_x, max_x, min_y, max_y)# Re-create rotation matrix for smallest rectangle = min_bbox[0]R = np.array([[np.cos(angle), np.cos(angle-(np.pi/2))],[np.cos(angle+(np.pi/2)), np.cos(angle)]])# Project convex hull points onto rotated frameproj_points = np.dot(R, np.transpose(hull_points_2d))  # 2x2 * 2xn# min/max x,y points are against baselinemin_x = min_bbox[4]max_x = min_bbox[5]min_y = min_bbox[6]max_y = min_bbox[7]# Calculate center point and project onto rotated frame# center_x = (min_x + max_x) / 2# center_y = (min_y + max_y) / 2# center_point = np.dot([center_x, center_y], R)# Calculate corner points and project onto rotated framecorner_points = np.zeros((4, 2))  # empty 2 column arraycorner_points[0] = np.dot([max_x, min_y], R)corner_points[1] = np.dot([min_x, min_y], R)corner_points[2] = np.dot([min_x, max_y], R)corner_points[3] = np.dot([max_x, max_y], R)return  min_bbox[2], min_bbox[3], corner_points,area

min_rect.py

import numpy as np
import matplotlib.pyplot as plt
from .qhull_2d import qhull2D
from .min_bounding_rect import minBoundingRectdef min_area_rect(xy_points):# Find convex hullhull_points = qhull2D(xy_points)# Reverse order of points, to match output from other qhull implementationshull_points = hull_points[::-1]# print('Convex hull points: \n', hull_points, "\n")# Find minimum area bounding rectanglewidth, height, corner_points,area = minBoundingRect(hull_points)# # Visualizationplt.figure()plt.plot(xy_points[:, 0], xy_points[:, 1], 'o', label='Points')plt.plot(hull_points[:, 0], hull_points[:, 1], 'r--', lw=2, label='Convex Hull')# Plot the bounding boxbox = np.vstack([corner_points, corner_points[0]])  # Close the box by repeating the first pointplt.plot(box[:, 0], box[:, 1], 'g-', lw=2, label='Min Bounding Box')plt.legend()plt.xlabel('X')plt.ylabel('Y')plt.title('Convex Hull and Minimum Area Bounding Box')plt.grid(True)plt.axis('equal')plt.show()return  width, height,corner_points,area

qhull_2d.py

from __future__ import division
from numpy import *def link(a, b):return concatenate((a, b[1:]))def edge(a, b):return concatenate(([a], [b]))def qhull2D(sample):def dome(sample, base, depth=0, max_depth=1000):h, t = basedists = dot(sample - h, dot(((0, -1), (1, 0)), (t - h)))if len(dists) == 0:return base# Handle cases where all distances are very smallif all(abs(dists) < 1e-10):return baseouter = sample[dists > 0]# print("dists:",dists,"outer:",outer)# Handle empty outer caseif len(outer) == 0:return basepivot_index = argmax(dists)pivot = sample[pivot_index]# Ensure depth does not exceed maximum allowedif depth > max_depth:return base# Recursive caseleft_dome = dome(outer, edge(h, pivot), depth + 1, max_depth)right_dome = dome(outer, edge(pivot, t), depth + 1, max_depth)return link(left_dome, right_dome)if len(sample) > 2:axis = sample[:, 0]base = take(sample, [argmin(axis), argmax(axis)], axis=0)left_dome = dome(sample, base)right_dome = dome(sample, base[::-1])return link(left_dome, right_dome)else:return sample

结果

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/481483.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

windows平台使用C#创建系统服务

使用 C# 在 Windows 平台创建和管理系统服务 在 Windows 平台上&#xff0c;系统服务&#xff08;Windows Service&#xff09;是一种运行在后台、无需用户交互的应用程序。系统服务广泛应用于长期任务处理、网络监听、后台调度等场景。本文将详细介绍如何使用 C# 创建一个 Win…

【C++笔记】位图和布隆过滤器

【C笔记】位图和布隆过滤器 &#x1f525;个人主页&#xff1a;大白的编程日记 &#x1f525;专栏&#xff1a;C笔记 文章目录 【C笔记】位图和布隆过滤器前言一. 位图1.1 位图相关面试题1.2 C库中的位图1.3位图优缺点1.4位图相关考察题目 二.布隆过滤器2.1 什么是布隆过滤器…

小迪安全第四十二天笔记 简单的mysql注入 mysql的基础知识 用户管理数据库模式 mysql 写入与读取 跨库查询

前言 之前的安全开发我们学习了 php联动数据库的模式 &#xff0c;这个模式是现在常用的模式 这一节来学习 如何 进行数据库的注入和数据库相关知识 1、了解数据库的结构 我们使用 navicate连接数据库之后看一下 一共四层结构 库 》表》字段》数据 这个层级关系…

如何估算自然对流传热系数

介绍 一般来说&#xff0c;对流可以定义为通过加热流体&#xff08;例如空气或水&#xff09;的运动来传递热量的过程。 自然对流&#xff08;对流的一种特定类型&#xff09;可以定义为流体在重力作用下由于较热因此密度较小的物质上升&#xff0c;而较冷且密度较大的物质下…

阿里云服务器(centos7.6)部署前后端分离项目(MAC环境)

Jdk17安装部署 下载地址&#xff1a;https://www.oracle.com/java/technologies/downloads/ 选择自己需要的jdk版本进行下载。 通过mac终端scp命令上传下载好的jdk17到服务器的/usr/local目录下 scp -r Downloads/jdk-17.0.13_linux-x64_bin.tar.gz 用户名服务器ip地址:/us…

ipad项目 蓝湖宽度

ipad项目 横屏状态时 蓝湖宽度设置930px media screen and (orientation: portrait) {/* 竖屏时的样式 */ } media screen and (orientation: landscape) {/* 默认是 横屏时的样式 */ }

【Linux——实现一个简易shell】

黑暗中的我们都没有说话&#xff0c;你只想回家&#xff0c;不想你回家............................................................... 文章目录 前言 一、【shell工作过程】 二、【命令行参数】 2.1、【获取命令行参数】 1、【输出命令行提示符】 2、【输入命令行参数】 2…

理解Linux的select、poll 和 epoll:从原理到应用场景

I/O 多路复用并不是什么新东西&#xff0c;select 早在 1983 年就出现了&#xff0c;poll 在 1997 年&#xff0c;epoll 是 2002 年的产物。面试题总爱问“多路复用多厉害&#xff1f;”其实它就是把轮询的锅甩给了操作系统&#xff0c;而操作系统不过是用 CPU 指令帮你完成事件…

阅读方法论

选择固有缺陷,选项是对比出来的

关于函数式接口和编程的解析和案例实战

文章目录 匿名内部类“匿名”在哪里 函数式编程lambda表达式的条件Supplier使用示例 ConsumeracceptandThen使用场景 FunctionalBiFunctionalTriFunctional 匿名内部类 匿名内部类的学习和使用是实现lambda表达式和函数式编程的基础。是想一下&#xff0c;我们在使用接口中的方…

ChatGPT 网络安全秘籍(二)

第三章&#xff1a;代码分析和安全开发 这一章深入探讨软件开发的复杂过程&#xff0c;关注当今数字世界中的一个关键问题&#xff1a;确保软件系统的安全。随着技术的不断复杂和威胁的不断演变&#xff0c;采用融合了安全考虑的安全软件开发生命周期&#xff08;SSDLC&#x…

学习笔记044——HashMap源码学习2

文章目录 1、HasMap 底层实现2、HashMap 加载顺序 1、HasMap 底层实现 JDK 1.8 HashMap 底层设计涉及到三种不同的数据结构&#xff0c;分别是数组、链表、红黑树。 1、基本的存储是数组&#xff0c;根据 key 值求出一个数组下标&#xff0c;将元素&#xff08;key-value&am…

计算机网络常见面试题总结(上)

计算机网络基础 网络分层模型 OSI 七层模型是什么&#xff1f;每一层的作用是什么&#xff1f; OSI 七层模型 是国际标准化组织提出的一个网络分层模型&#xff0c;其大体结构以及每一层提供的功能如下图所示&#xff1a; 每一层都专注做一件事情&#xff0c;并且每一层都需…

用micropython 操作stm32f4单片机的定时器实现蜂鸣器驱动

import pyb import time # 初始化引脚和定时器通道作为PWM输出 # 注意&#xff1a;这里我们假设您使用的是支持PWM的引脚和定时器 # 在不同的MicroPython板上&#xff0c;支持的引脚和定时器可能不同 # 请查阅您的板的文档以确认正确的引脚和定时器 buzzer_pin pyb.Pin(PD15,…

前端框架Vue3项目实战(基于Vue3实现一个小相册)

下面是是对Vue3操作的一个项目实战 下面代码是html的基本骨架&#xff08;没有任何的功能&#xff09;&#xff1a; <!DOCTYPE html> <html lang"en"> <head> <meta charset"UTF-8"> <title>相册</title> <style&…

【英特尔IA-32架构软件开发者开发手册第3卷:系统编程指南】2001年版翻译,2-39

文件下载与邀请翻译者 学习英特尔开发手册&#xff0c;最好手里这个手册文件。原版是PDF文件。点击下方链接了解下载方法。 讲解下载英特尔开发手册的文章 翻译英特尔开发手册&#xff0c;会是一件耗时费力的工作。如果有愿意和我一起来做这件事的&#xff0c;那么&#xff…

群控系统服务端开发模式-应用开发-前端短信配置开发

一、添加视图 在根目录下src文件夹下views文件夹下param文件夹下sms文件夹下&#xff0c;新建index.vue&#xff0c;代码如下 <template><div class"app-container"><div class"filter-container" style"float:left;"><el…

极致性能:19个Vue 项目的优化手段

前言 在前端开发领域&#xff0c;Vue.js 广泛应用于各种类型的项目中。然而&#xff0c;随着项目规模的扩大和用户需求的增加&#xff0c;性能优化的重要性愈发凸显。优化不仅可以提升用户体验&#xff0c;还能显著减少资源消耗&#xff0c;提高应用的响应速度和稳定性。 本文…

基于Java Springboot个人记账之财来财往微信小程序

一、作品包含 源码数据库设计文档万字PPT全套环境和工具资源部署教程 二、项目技术 前端技术&#xff1a;Html、Css、Js、Vue、Element-ui 数据库&#xff1a;MySQL 后端技术&#xff1a;Java、Spring Boot、MyBatis 三、运行环境 开发工具&#xff1a;IDEA/eclipse 微信…

【maven-5】Maven 项目构建的生命周期:深入理解与应用

1. 生命周期是什么 ​在Maven出现之前&#xff0c;项目构建的生命周期就已经存在&#xff0c;软件开发人员每天都在对项目进行清理&#xff0c;编译&#xff0c;测试及部署。虽然大家都在不停地做构建工作&#xff0c;但公司和公司间&#xff0c;项目和项目间&#xff0c;往往…