C++实现四叉树
什么是四叉树?
四叉树可以有效解决这个问题。
四叉树每一层都把地图划分四块,根据地图尺寸来决定树的层数,层数越大划分越细。
但需要对某一范围的单位筛选时,只需要定位到与范围相交的树区域,再对其区域内的对象筛选即可。
四叉树的实现
#pragma once
#include "base.h"
#include "math.h"
template <class Value>
class Tree4 {
private:
struct Pointer {
Tree4 *LT, *RT, *LB, *RB;
Pointer() :LT(nullptr), RT(nullptr), LB(nullptr), RB(nullptr)
{ }
~Pointer()
{
SAFE_DELETE(LT);
SAFE_DELETE(RT);
SAFE_DELETE(LB);
SAFE_DELETE(RB);
}
};
public:
Tree4(): _rect(rect)
{
STD queue<Tree4 *> queue;
queue.push(this);
; n != ; --n, c *= )
{
; i != c; ++i)
{
auto tree = queue.front();
tree->Root();
queue.pop();
queue.push(tree->_pointer.LT);
queue.push(tree->_pointer.RT);
queue.push(tree->_pointer.LB);
queue.push(tree->_pointer.RB);
}
}
}
template <class Range>
bool Insert(const Value * value, const Range & range)
{
auto tree = Contain(range);
auto ret = nullptr != tree;
if (ret) { tree->_values.emplace_back(value); }
return ret;
}
template <class Range>
bool Remove(const Value * value, const Range & range)
{
auto tree = Contain(range);
auto ret = nullptr != tree;
if (ret) { ret = tree->Remove(value); }
return ret;
}
template <class Range>
bool Match(const Range & range, const STD function<bool(Value *)> & func)
{
if (!MATH intersect(_rect, range))
{
return true;
}
for (auto & value : _values)
{
if (!func(const_cast<Value *>(value)))
{
return false;
}
}
auto ret = true;
if (!IsLeaf())
{
if (ret) ret = _pointer.LT->Match(range, func);
if (ret) ret = _pointer.RT->Match(range, func);
if (ret) ret = _pointer.LB->Match(range, func);
if (ret) ret = _pointer.RB->Match(range, func);
}
return ret;
}
template <class Range>
Tree4 * Contain(const Range & range)
{
Tree4<Value> * ret = nullptr;
if (MATH contain(STD cref(_rect), range))
{
if (!IsLeaf())
{
if (nullptr == ret) ret = _pointer.LT->Contain(range);
if (nullptr == ret) ret = _pointer.RT->Contain(range);
if (nullptr == ret) ret = _pointer.LB->Contain(range);
if (nullptr == ret) ret = _pointer.RB->Contain(range);
}
if (nullptr == ret)
ret = this;
}
return ret;
}
private:
void Root()
{
_pointer.LT = new Tree4(MATH Rect(_rect.x, _rect.y, _rect.w * 0.5f, _rect.h * 0.5f));
_pointer.LB = new Tree4(MATH Rect(_rect.x, _rect.y + _rect.h * 0.5f, _rect.w * 0.5f, _rect.h * 0.5f));
_pointer.RT = new Tree4(MATH Rect(_rect.x + _rect.w * 0.5f, _rect.y, _rect.w * 0.5f, _rect.h * 0.5f));
_pointer.RB = new Tree4(MATH Rect(_rect.x + _rect.w * 0.5f, _rect.y + _rect.h * 0.5f, _rect.w * 0.5f, _rect.h * 0.5f));
}
bool Remove(const Value * value)
{
auto iter = STD find(_values.begin(), _values.end(), value);
auto ret = _values.end() != iter;
if (ret) { _values.erase(iter); }
return ret;
}
bool IsLeaf()
{
return nullptr == _pointer.LT
|| nullptr == _pointer.RT
|| nullptr == _pointer.LB
|| nullptr == _pointer.RB;
}
Tree4(const Tree4 &) = delete;
Tree4(Tree4 &&) = delete;
Tree4 &operator=(const Tree4 &) = delete;
Tree4 &operator=(Tree4 &&) = delete;
private:
MATH Rect _rect;
Pointer _pointer;
STD list<const Value *> _values;
};
代码简洁,通俗易懂,承让。
效果图

左侧全图遍历,右侧四叉树遍历,通过左上角的开销时间,差异很明显。
C++实现四叉树的更多相关文章
- 地图四叉树一般用在GIS中,在游戏寻路中2D游戏中一般用2维数组就够了
地图四叉树一般用在GIS中,在游戏寻路中2D游戏中一般用2维数组就够了 四叉树对于区域查询,效率比较高. 原理图
- HTML5实现3D和2D可视化QuadTree四叉树碰撞检测
QuadTree四叉树顾名思义就是树状的数据结构,其每个节点有四个孩子节点,可将二维平面递归分割子区域.QuadTree常用于空间数据库索引,3D的椎体可见区域裁剪,甚至图片分析处理,我们今天介绍的是 ...
- HT for Web可视化QuadTree四叉树碰撞检测
QuadTree四叉树顾名思义就是树状的数据结构,其每个节点有四个孩子节点,可将二维平面递归分割子区域.QuadTree常用于空间数据库索引,3D的椎体可见区域裁剪,甚至图片分析处理,我们今天介绍的是 ...
- [转]一个四叉树Demo学习
程序代码: http://www.codeproject.com/Articles/30535/A-Simple-QuadTree-Implementation-in-C 四叉树: using Sys ...
- [转]基于四叉树(QuadTree)的LOD地形实现
实现基于四叉树的LOD地形时,我遇到的主要问题是如何修补地形裂缝. 本段我将描述使用LOD地形的优势,我实现LOD地形的思路,实现LOD地形核心模块的详细过程,以及修补地形裂缝的思路. 首先,LOD地 ...
- 线性四叉树十进制Morton码计算示例
线性四叉树十进制Morton码计算,具体算法描述龚健雅<地理信息系统基础>P108
- 一个四叉树Demo学习
程序代码: http://www.codeproject.com/Articles/30535/A-Simple-QuadTree-Implementation-in-C 四叉树: using Sys ...
- UVA 297 Quadtrees(四叉树建树、合并与遍历)
<span style="font-size: 18pt; font-family: Arial, Helvetica, sans-serif; background-color: r ...
- [LeetCode] Quad Tree Intersection 四叉树相交
A quadtree is a tree data in which each internal node has exactly four children: topLeft, topRight, ...
随机推荐
- Python系列之heapq内置模块
heapq 是 python 的内置模块,源码位于 Lib/heapq.py ,该模块提供了基于堆的优先排序算法. 堆的逻辑结构就是完全二叉树,并且二叉树中父节点的值小于等于该节点的所有子节点的值.这 ...
- Python学习--20 Web开发
HTTP格式 HTTP协议是基于TCP和IP协议的.HTTP协议是一种文本协议. 每个HTTP请求和响应都遵循相同的格式,一个HTTP包含Header和Body两部分,其中Body是可选的. HTTP ...
- java线程之多个生产者消费者
温故一下上一节所学习的生产者消费者代码: 两个线程时: 通过标志位flag的if判断和同步函数互斥较好解决两个线程,一个生产者.一个消费者交替执行的功能 类名:ProducterConsumerDem ...
- Python2和Python3中除法操作/的不同
X/Y 在3.0版本之前的Python中 >>>1/2 0 即一个整数(无小数部分的数)被另外一个整数除,计算结果的小数部分被截除了,只留下了整数部分 有时候,这个功能比较有用,譬如 ...
- 什么是Bootstrap?
简介 - 框架:库 lib library- jQuery作为一个框架来讲,提供一套比较便捷的操作DOM的方式- 把大家都需要的功能预先写好到一些文件 这就是一个框架- Bootstrap 让我们的 ...
- js获取浮动(float)元素的style.left值为空的解决办法
解决办法: 1.使用行内样式设置元素的top和left值; 2.or直接获取元素的offsetLeft得到相关数值,还不需要parseInt 问题原因: 如果父div的position定义为relat ...
- 在CentOS 7中安装Redis 3.2.8
文章环境: CentOS 7 biuld 1611最小化安装@VMware Redis 3.2.8 安装步骤: #安装gcc yum -y install gcc #下载redis curl -O h ...
- java学习之路
先来说一说我和it之间的不解之缘.准确来说,我接触it是从大二是我买的第一个手机开始的(国产的,展讯平台,能够运行mrp虚拟机),那时候还没有智能手机,或者说还不够普及,总之就是买不起.一次偶然的机会 ...
- Ansible 系列之 Ad-Hoc介绍及使用
Ad-Hoc 介绍 一.什么是ad-hoc 命令? ad-hoc 命令是一种可以快速输入的命令,而且不需要保存起来的命令.就相当于bash中的一句话shell.这也是一个好的地方,在学习ansible ...
- tcp粘包和拆包的处理方案
随着智能硬件越来越流行,很多后端开发人员都有可能接触到socket编程.而很多情况下,服务器与端上需要保证数据的有序,稳定到达,自然而然就会选择基于tcp/ip协议的socekt开发.开发过程中,经常 ...