【计算几何7】帝国边界划分问题【Voronoi图的原理】

2023-05-16

目录

一、说明

二、帝国边界划分问题

三、voronoi的正规定义

3.1 最简单的voronoi情况

3.2 在距离空间的数学描述

3.3 不同距离空间所得 Voronoi 单元不同

四、代码和库

4.1 算法库

4.2 参数说明 

4.3 调用方法 

五、后记


一、说明

        Voronoi 单元也称为泰森多边形。 Voronoi 图在许多领域都有实际和理论应用,主要是在科学和技术领域,但也在视觉艺术领域使用。Voronoi 图以数学家 Georgy Voronoy 的名字命名,也称为 Voronoi 镶嵌、Voronoi 分解、Voronoi 分区或 Dirichlet 镶嵌(以 Peter Gustav Lejeune Dirichlet 命名)。

        在数学中,Voronoi 图是将对平面(集合)划分为多个区域的算法。在最简单的情况下,这些对象只是平面上的有限多个点(称为种子、站点或生成器)。对于每个种子,都有一个对应的优先划分区域。这种区域称为 Voronoi 单元,由平面上离该种子比其他任何点更近的所有点组成。一组点的 Voronoi 图与该组的 Delaunay 三角剖分是对偶的。

        注意:点、区域、边界线成为这个算法的关键要素。

二、帝国边界划分问题

        我们用一个童话故事构成思想实验。

        话说,哈里发国王年事已高,厌倦朝政,因而计划将他的王国分为四份,分别由四个王子管理。于是召来宰相易普拉辛,说到:“我亲爱的宰相,我打算将王国分成四个部落,分别交给王子们统辖,如今有四个城池,分别是查兰,是哥,达玛,宿吐作为它们的都城,可是如何划分疆土我毫无主张,是真主启发我召你商议此事。”宰相思索片刻,说到:“赞美安拉,我倒是有一个谋划,请借地图叙述”,国王当即请出地图如下:

         且看宰相如何划分国土。首先,确定查兰的边疆,如下:

        1)从查兰引出两个线段,分别连接(是哥,达玛)因为宿土与查兰不接壤,所以不必引进宿土。

        2)分别作出两条线段的垂直中分线。

         做出两条中分线L1,L2。中分线上的特征是:L1线上点到查兰的距离一定等于该点到是哥距离,L2上的任意点到查兰距离,一定等于它到达玛的距离。因此,站在平分线上看两国首都,谁也没“侵犯”谁。故绿线和红线都是“公平线”,就此,查兰的土地被公平线L1和L2包络,已经画出。

         3)接着划分达玛:从达玛引出线段,连接宿土和是哥,作公平线S1,和S2,这样达玛土地在公平线L2,S1,S1包围下也能画出,如图粉色区域。    

        显然,图中新增出粉色区域中,任意一点到达玛距离比到其它三城距离更近,保证达玛没有“侵犯”其它邻国。至此,达玛的边界因L2,S1,S2包络而确定。    

        注意: 虽然有公平线L1横穿达玛,但此线是【查兰,是哥】的公平线,与达玛无关。       

        4)最后,从宿土到是哥引出线段,并做出中分线T ,如图:

         至此,宿土的边疆也因T-S2-L1包络出是哥的领土,至此国土划分完成。       

         哈里发看了宰相的划分,依然不悦,对宰相说到:“依照爱卿的划分,国土面积不等,如何说服四位王子服从分配?”宰相说到:“安啦是唯一的主,不妨把命运交给安拉,让他们抓阄分配”,国王听后,大喜曰:“然”。

        提示:有个三线交于一点的问题,如L1-L2-S2三线交于一点,T-S1-S2三线相交。这需要证明。

        三条线共交于一点的说明:在相邻三城边界划分中,每三个中分线是共点的,如下证明:

        先假定篮圈内三线不相交,从角的垂线定律说明,红蓝角+红黑角+黑绿角=180度,因此三线必然共点。

        或者说,三个点组成三角形,其外接圆圆心引出三条到边的垂线,这三条垂线正好等分三边。

三、voronoi的正规定义

3.1 最简单的voronoi情况

        在最简单的情况下,如第一张图片所示,我们在欧几里得平面中得到一组有限的点 {p1, ..., pn}。在这种情况下,每个站点 pk 只是一个点,其对应的 Voronoi 单元 Rk 由欧几里得平面中的每个点组成,这些点到 pk 的距离小于或等于它到任何其他 pk 的距离。每个这样的单元都是从半空间的交集获得的,因此它是一个(凸)多面体。 [6] Voronoi 图的线段是平面上与最近的两个站点等距的所有点。 Voronoi 顶点(节点)是与三个(或更多)站点等距的点。 

3.2 在距离空间的数学描述

        下文中:生成点==站点

        设X是一个距离函数的度量空间,K是一组索引,{\textstyle (P_{k})_{k\in K}} 是空间中非空子集(站点)的元组(索引集合){\textstyle X}。 Voronoi 单元或 Voronoi 区域,{\textstyle R_{k}},与网站相关{\textstyle P_{k}} 是所有点的集合{\textstyle X}距离{\textstyle P_{k}} 不大于它们到其他站点的距离{\textstyle P_{j}},其中{\textstyle j} 是任何不同于{\textstyle k}。换句话说,如果{\textstyle d(x,\,A)=\inf\{d(x,\,a)\mid a\in A\}}, 表示点与集合之间的距离({\textstyle x} 和子集{\textstyle A}),然后有:

        Voronoi 图只是单元格的元组{\textstyle (R_{k})_{k\in K}}。原则上,一些站点可以相交甚至重合(下面描述了代表商店的站点的应用程序),但通常假定它们是不相交的。此外,定义中允许有无限多个站点(此设置在数字几何和晶体学中有应用),但同样,在许多情况下,只考虑有限多个站点。

        在空间是有限维欧几里德空间的特殊情况下,每个站点都是一个点,有有限多个点并且所有点都不同,那么 Voronoi 单元是凸多边形,它们可以用组合方式表示它们的顶点、边、二维面等。有时,导出的组合结构被称为 Voronoi 图。然而,一般而言,Voronoi 单元可能不是凸的,甚至可能不是连接的。在通常的欧几里德空间中,我们可以用通常的术语重写形式定义。每个 Voronoi 多边形{\textstyle R_{k}} 与生成点相关联{\textstyle P_{k}}。假定{\textstyle X} 是欧氏空间中所有点的集合。且{\textstyle P_{1}} 是生成其 Voronoi 区域的{\textstyle R_{1}}的点,{\textstyle P_{2}} 生成2个{\textstyle R_{2}}, 和3个{\textstyle P_{3}} 生成3个{\textstyle R_{3}}等等。然后,Voronoi 多边形中的所有位置都比欧几里得平面中的 Voronoi 图中的任何其他生成点更接近该多边形的生成点”。

3.3 不同距离空间所得 Voronoi 单元不同

        如图,下面是基于欧氏空间和曼哈顿空间的划分:

       

        以上就是欧氏空间和曼哈顿空间的划分细节。

四、代码和库

4.1 算法库

以下给出算法库Voronoi,是通过python写的代码

from PIL import Image, ImageColor, ImageDraw
from random import randint, choice, random, seed as randomseed
from typing import *
from math import hypot, sqrt
from queue import Queue
from dataclasses import dataclass
from enum import Enum

import os
import sys


class ColorAlgorithm(Enum):
    random           = 1
    no_adjacent_same = 2
    least_possible   = 3


class RegionAlgorithm:
    def randomized(width: int, height: int, regions: int, mask_function) -> List[Tuple[int, int]]:
        """Return regions that are entirely random."""
        points = []
        while len(points) != regions:
            p = (randint(0, width - 1), randint(0, height - 1))

            if p in points:
                continue

            if not mask_function(p):
                continue

            points.append(p)

        return points

    def uniform(width: int, height: int, regions: int, mask_function) -> List[Tuple[int, int]]:
        """Return regions that attempt to be somewhat uniform."""
        k = 10
        points = []
        while len(points) != regions:
            best_p = None
            d_max = 0

            i = 0
            while i < k * len(points) + 1:
                p = (randint(0, width - 1), randint(0, height - 1))

                if p in points:
                    continue

                if not mask_function(p):
                    continue

                if len(points) == 0:
                    best_p = p
                    break

                d_min = float('inf')
                for x, y in points:
                    d = hypot(p[0]-x, p[1]-y)

                    if d < d_min:
                        d_min = d

                if d_min > d_max:
                    d_max = d_min
                    best_p = p

                i += 1

            points.append(best_p)

        return points


class DistanceAlgorithm:
    def euclidean(x, y, xn, yn):
        """Calculate the image regions (up to a distance) using euclidean distance."""
        return hypot(xn-x, yn-y)

    def manhattan(x, y, xn, yn):
        """Calculate the image regions using manhattan distance."""
        return abs(xn-x) + abs(yn-y)

    def euclidean45degrees(x, y, xn, yn):
        """Calculate the image regions using euclidean, but allow only lines in 45 degree increments."""
        return sqrt(2 * min(abs(xn-x), abs(yn-y)) ** 2) + abs(abs(xn-x) - abs(yn-y))

    def chebyshev(x, y, xn, yn):
        """Calculate the image regions using chebyshev distance."""
        return min(abs(xn-x), abs(yn-y)) + abs(abs(xn-x) - abs(yn-y))

    def set_each_point(seed: int, width: int, height: int,
            region_centers: List[Tuple[int, int]], image: List[List[int]],
            d_limit: int, f: List[Callable[[int, int, int, int], float]], mask_function):
        """Calculate the image regions (up to a distance) using the provided metric."""
        randomseed(seed)

        region_distance_functions = [f if not isinstance(f, list) else choice(f) for _ in range(len(region_centers))]

        for x in range(width):
            for y in range(height):
                if not mask_function((x, y)):
                    continue

                d_min = float('inf')

                for i, region in enumerate(region_centers):
                    xn, yn = region
                    d = region_distance_functions[i](x, y, xn, yn)

                    if d < d_min:
                        d_min = d

                        if d <= d_limit:
                            image[x][y] = id(region)

class Utilities:
    def error(message, q=True):
        print(f"\u001b[38;5;1mERROR:\u001b[0m {message}", flush=True)

        if q:
            sys.exit(1)

    def warning(message):
        print(f"\u001b[38;5;208mWARNING:\u001b[0m {message}", flush=True)

    def info(message):
        print(f"\u001b[38;5;11mINFO:\u001b[0m {message}", flush=True)

    def success(message):
        print(f"\u001b[38;5;2mSUCCESS:\u001b[0m {message}", flush=True)

    def hex_to_tuple(color: str):
        color = color.strip("#")
        return (int(color[0:2], 16), int(color[2:4], 16), int(color[4:6], 16))

    def get_different_adjacent_colors(width, height, image, colors, color_algorithm):
        from pulp import LpProblem, LpVariable, LpMinimize, lpSum, PULP_CBC_CMD

        edges = set()

        mapping = {}
        n = 0

        for x in range(width):
            for y in range(height):
                for xd, yd in ((0, 1), (1, 0), (-1, 0), (0, -1)):
                    xn, yn = x + xd, y + yd

                    if not 0 <= xn < width or not 0 <= yn < height:
                        continue

                    i1, i2 = image[x][y], image[xn][yn]

                    if i1 is None or i2 is None:
                        continue

                    if i1 < i2:
                        if i1 not in mapping:
                            n += 1
                            mapping[n] = i1
                            mapping[i1] = n

                        if i2 not in mapping:
                            n += 1
                            mapping[n] = i2
                            mapping[i2] = n

                        edges.add((mapping[i1], mapping[i2]))

        edges = list(edges)
        model = LpProblem(sense=LpMinimize)

        chromatic_number = LpVariable(name="chromatic number", cat='Integer')
        variables = [[LpVariable(name=f"x_{i}_{j}", cat='Binary') \
                      for i in range(n)] for j in range(n)]

        for i in range(n):
            model += lpSum(variables[i]) == 1
        for u, v in edges:
            for color in range(n):
                model += variables[u - 1][color] + variables[v - 1][color] <= 1
        for i in range(n):
            for j in range(n):
                model += chromatic_number >= (j + 1) * variables[i][j]

        if color_algorithm == ColorAlgorithm.least_possible:
            model += chromatic_number
        else:
            model += chromatic_number == len(colors)

        status = model.solve(PULP_CBC_CMD(msg=False))

        if chromatic_number.value() > len(colors):
            Utilities.error("Not enough colors to color without adjacent areas having the same one!")

        return {mapping[variable + 1]: colors[color]
                for variable in range(n)
                for color in range(n)
                if variables[variable][color].value() == 1}

    def add_border(background, border_size, read_image, write_image, width, height, mask_function):
        r = border_size // 2

        for x in range(width):
            for y in range(height):
                if not mask_function((x, y)):
                    continue

                for dx, dy in ((0, 1), (1, 0)):
                    xn, yn = x + dx, y + dy

                    if not 0 <= xn < width or not 0 <= yn < height:
                        continue

                    if not mask_function((xn, yn)):
                        continue

                    if read_image[x][y] != read_image[xn][yn]:
                        draw = ImageDraw.Draw(write_image)
                        draw.ellipse((x-r, y-r, x+r, y+r), fill=(*background,0))


def generate(
        path: str,
        regions: int,
        colors: List[Union[Tuple[int], str]],
        width: int = 1920,
        height: int = 1080,
        region_algorithm = RegionAlgorithm.uniform,
        distance_algorithm = DistanceAlgorithm.euclidean,
        color_algorithm = ColorAlgorithm.random,
        seed: Optional[int] = None,
        border_size: int = 0,
        mask: Optional[str] = None,
        mask_color = "#000000",
        animate = False,
        background = "#FFFFFF",
):
    # possibly seed the random algorithm
    if seed is None:
        seed = random()

    # possibly convert string colors to tuples
    i = 0
    while i < len(colors):
        if type(colors[i]) == str:
            colors[i] = Utilities.hex_to_tuple(colors[i])

        i += 1

    if type(mask_color) == str:
        mask_color = Utilities.hex_to_tuple(mask_color)
    elif type(mask_color) == list:
        mask_color = tuple(mask_color)

    if type(background) == str:
        background = Utilities.hex_to_tuple(background)
    elif type(background) == list:
        background = tuple(background)

    randomseed(seed)

    mask_function = lambda p: True

    if mask is not None:
        try:
            mask_img = Image.open(mask)
            Utilities.info("Mask provided.")

            w, h = mask_img.size

            mask_function = lambda p: mask_img.getpixel(p) == mask_color

            if w != width:
                Utilities.warning("Specified width doesn't match mask width, using mask width.")
                width = w

            if h != height:
                Utilities.warning("Specified height doesn't match mask height, using mask width.")
                height = h


        except Exception as e:
            Utilities.error(f"Error loading mask from '{mask}'.")

    if type(regions) == list:
        Utilities.info("Region centers provided, skipping generation.")

        # flip vertically!
        region_centers = [(int(center[0] * width), int(height - center[1] * height)) for center in regions]
    else:
        Utilities.info("Calculating region centers.")
        region_centers = region_algorithm(width, height, regions, mask_function)

    image = [[None] * height for _ in range(width)]
    Utilities.info("Calculating region areas.")
    DistanceAlgorithm.set_each_point(seed, width, height, region_centers, image, float("inf"), distance_algorithm, mask_function)

    # either assign colors randomly, or calculate the chromatic number and assign them then
    if color_algorithm == ColorAlgorithm.random:
        Utilities.info("Assigning region colors.")
        region_colors = {id(region): choice(colors) for region in region_centers}
    else:
        Utilities.info("Assigning region colors such that no two adjacent regions have the same color.")
        region_colors = Utilities.get_different_adjacent_colors(width, height, image, colors, color_algorithm)

    # if we're masking, some regions won't be assigned
    region_colors[None] = background

    # the original, full image (without borders)
    pil_image = Image.new("RGB", (width, height))
    for x in range(width):
        for y in range(height):
            pil_image.putpixel((x, y), region_colors[image[x][y]])

    if border_size != 0:
        Utilities.add_border(background, border_size, image, pil_image, width, height, mask_function)

    if animate:
        if not os.path.exists(path):
            os.makedirs(path)

        d = 1

        while True:
            animation_image = [[None] * height for _ in range(width)]
            DistanceAlgorithm.set_each_point(seed, width, height, region_centers, animation_image, d, distance_algorithm, mask_function)

            animation_pil_image = Image.new("RGB", (width, height))

            for x in range(width):
                for y in range(height):
                    animation_pil_image.putpixel((x, y), background if animation_image[x][y] is None else region_colors[image[x][y]])

            if border_size != 0:
                Utilities.add_border(background, border_size, animation_image, animation_pil_image, width, height)

            animation_path = os.path.join(path, f"{d}.png")

            animation_pil_image.save(animation_path, "PNG")
            Utilities.success(f"Animation image saved to {animation_path}")

            d += 1

            if image == animation_image:
                Utilities.success(f"Done!")
                break

    else:
        pil_image.save(path, resolution=300)
        Utilities.success(f"Image saved to {path}!")

4.2 参数说明 

generate function arguments

  • path: the path (including an extension) to save the resulting file to
  • regions: the number of distinct regions in the diagram
  • colors: a list of tuples denoting the RGB of the color, or strings denoting the color in hex
  • width: the width of the image; defaults to 1920
  • height: the height of the image; defaults to 1080
  • region_algorithm: the algorithm that determines the centers of the regions:
    • RegionAlgorithm.uniform attempts to make the centers equidistant to one another; default
    • RegionAlgorithm.randomized makes the center positions entirely random
  • distance_algorithm: the algorithm that determines the way the distance is measured; if a list of the algorithms is provided, a random one is picked for each point
    • DistanceAlgorithm.euclidean: standard euclidean distance (hypotenuse); default
    • DistanceAlgorithm.manhattan: Manhattan (taxicab) distance (4 directions)
    • DistanceAlgorithm.chebyshev: Chebyshev distance (8 directions)
    • DistanceAlgorithm.euclidean45degrees: euclidean distance, but lines can only point in 45 degree increments
  • color_algorithm: the algorithm that determines the colors of the regions
    • DistanceAlgorithm.random: pick the colors randomly
    • DistanceAlgorithm.no_adjacent_same: pick the colors such that no two adjacent regions have the same color
    • DistanceAlgorithm.least_possible: same as no_adjacent_same, but attempt to do so in the least number of colors
  • seed: the seed for the random number generator; no seed by default
  • border_size: the thickness of the border (in pixels); defaults to 0 (no border)
  • mask: a path to an image mask so only specific areas are used
  • mask_color: the color of the mask to fill, ignoring everything else; defaults to #000000
  • animate: creates images in the folder path of the regions filling in; defaults to False
  • background: background of the animation/masking/borders; defaults to #FFFFFF

4.3 调用方法 

from voronoi import *

generate(
    path = "1.png",
    width = 3840,
    height = 2160,
    regions = 70,
    colors = [(0, 0, 0), (15, 15, 15), (23, 23, 23), (30, 30, 30)],
    color_algorithm = ColorAlgorithm.no_adjacent_same,
)

结果图: 

五、后记

        值得注意的是,本文专注于说明Voronoi图是个啥,有两个问题需要进一步阐述:1)特殊情况分析。2)算法和原理没有说明。鉴于时间和精力有限,本文先就此告一段落,后续文章我们继续讨论更多的相关内容。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

【计算几何7】帝国边界划分问题【Voronoi图的原理】 的相关文章

  • Nvidia Jetson TX2+Intel Realsense D435i跑ORB_SLAM3

    前言 xff1a 网上的教程实在是太多 xff0c 从诸多教程中找到一个适合自己的实属不易 将此记录下来 xff0c 希望能够帮助到有需要的人 因为时间紧迫 xff0c 没时间写特别详细的内容 xff0c 只能引用一些他人的步骤 请见谅 x
  • catkin_make

    普通情况下编译文件都是使用cmake make工具 xff0c 与此有关的内容可以参考 xff1a cmake CMakeLists txt make makefile的关系 但ROS中还有catkin make xff0c 不清楚他们之间
  • Airsim仿真

    Airsim设计的目的 xff1a 1 现实世界开发测试自动驾驶车辆算法费时费力 2 迎合AI的发展 xff0c 需要在各种条件下和环境下收集大量带注释训练数据 模块化设计 xff0c 强调可扩展性 提供很多API xff0c 核心组件包括
  • 0404---通过SSH连接远程服务器运行图形界面程序问题

    远程运行 linux 服务器图形界面程序问题 通常部署在数据中心机房中的服务器是没有图形桌面的 xff0c 对服务器的日常运维也往往通过远程客户端命令窗口来进行 xff0c 但有时候往往需要在服务器上远程安装或运行图形窗口类软件 xff0c
  • Jetson NX emmc版本系统转移到SSD

    因emmc版本的NX自带内存不够大 xff0c 只有16GB xff08 手上的是这个型号 xff09 xff0c 安装系统大概需要除去4G多内存 xff0c 再安装CUDA cuDNN TensorRT等内存直接爆满 无法继续使用 所以需
  • ssh远程登录报错:kex_exchange_identification: Connection closed by remote host

    基本信息 系统 xff1a MacOS Catalina 10 15 7 报错信息 xff1a 终端登录远程 服务器 时报错 xff1a kex exchange identification Connection closed by re
  • 如何在Windows的cmd下让程序在后台执行

    如何在Windows的cmd下让程序在后台执行 xff1f Hu Dennis 2008 12 24 在windows下启动JBoss服务器 xff0c 需要在命令行中输入run bat 但是运行后如果你想停止服务器 xff0c 可能的做法
  • 嵌入式LINUX识别U盘的问题

    我试过mount U盘 当开机后mount 第一个U盘时 xff0c 一般设备名为sda xff0c 然后umount xff0c 并重插另外一个U盘 xff0c 再mount xff0c 发现设备名变为sdb了 此试验进行了几次 xff0
  • yolov4+deepsort(yolo目标检测+自适应卡尔曼滤波追踪+毕业设计代码)

    项目介绍 该项目一个基于深度学习和目标跟踪算法的项目 xff0c 主要用于实现视频中的目标检测和跟踪 该项目使用了 YOLOv4 目标检测算法和 DeepSORT 目标跟踪算法 xff0c 以及一些辅助工具和库 xff0c 可以帮助用户快速
  • 集成学习(含常用案列)

    集成学习原理 xff1a 工作原理是生成多个分类器 模型 xff0c 各自独立地学习和作出预测 这些预测最后结合成组合预测 xff0c 因此优于任何一个单分类的做出预测 集成学习算法分类 xff1a 集成学习算法一般分为 xff1a bag
  • 字节序与比特序详解

    字节序的定义 几种类型的字节序 cpu字节序外部bus字节序设备字节序网络协议字节序 Ethernet协议字节序IP协议字节序 编译字节序 比特序的定义字节序与bit序的转换结构体的位域 字节序的定义 字节序就是说一个对象的多个字节在内存中
  • 【动态规划】01背包问题

    问题描述 有n个物品 xff0c 它们有各自的体积和价值 xff0c 现有给定容量的背包 xff0c 如何让背包里装入的物品具有最大的价值总和 xff1f 为方便讲解和理解 xff0c 下面讲述的例子均先用具体的数字代入 xff0c 即 x
  • 献给初学labview数据采集的初学者

    前言 xff1a 参考来源 xff1a http bbs elecfans com jishu 209658 1 5 html xff0c 感谢原作者 zhihuizhou 这里的内容只针对NI的数据采集卡 xff0c 不保证适用于其它公司
  • 如何从科学论文中实现一个算法

    原文 xff1a http codecapsule com 2012 01 18 how to implement a paper 作者 xff1a Emmanuel Goossaert 本文是从科学论文中实现算法的简短指南 我从书籍和科学
  • 国内C/C++刷题网站汇总

    作者 xff1a Luau Lawrence 链接 xff1a https www zhihu com question 25574458 answer 31175374 来源 xff1a 知乎 Welcome To PKU JudgeOn
  • 华为16道经典面试题

    面试过程中 xff0c 面试官会向应聘者发问 xff0c 而应聘者的 回答将成为面试官考虑是否接受他的重要依据 对应聘者而言 xff0c 了解这些问题背后的 猫腻 至关重要 本文对面试中经常出现的一些典型问题进行了整理 xff0c 并给出相
  • 语音信号的预加重和加窗处理

    原文转载于 xff1a http blog csdn net ziyuzhao123 article details 12004603 非常感谢 一 语音信号的预加重 语音信号的预加重 xff0c 目的是为了对语音的高频部分进行加重 xff
  • 单独编译和使用webrtc音频增益模块(AGC)

    原文转载于 xff1a http www cnblogs com mod109 p 5767867 html top 非常感谢 webrtc的音频处理模块分为降噪ns xff08 nsx xff09 xff0c 回音消除aec xff08
  • 功率谱和频谱的区别

    生活中很多东西之间都依靠信号的传播 xff0c 信号的传播都是看不见的 xff0c 但是它以波的形式存在着 xff0c 这类信号会产生功率 xff0c 单位频带的信号功率就被称之为功率谱 它可以显示在一定的区域中信号功率随着频率变化的分布情
  • 如何解决在rviz中,路径规划导航时,点击2D Pose estimate后机器人位置没有改变,终端也没有反应的问题

    在rviz中 xff0c 点击2D Pose estimate后机器人位置没有改变 xff0c 终端也没有反应 xff0c 通常这种情况就是由于客户端和服务端IP地址不一致导致的 xff0c IP地址有时候系统会自动变更 xff0c 这里我

随机推荐

  • 五款免费开源的语音识别工具

    按 xff1a 本文原作者 Cindi Thompson xff0c 美国德克萨斯大学奥斯汀分校 xff08 University of Texas at Austin xff09 计算机科学博士 xff0c 数据科学咨询公司硅谷数据科学
  • 动态内存分配

    动态内存分配 常见的内存分配的错误 先上一个内存分配的思维导图 便于联想想象 xff0c 理解 xff1a 首先我们介绍一下内存分配的方式 xff1a 1 在静态存储区域中进行分配 内存在程序编译的时候就已经分配好 xff0c 这块内存在程
  • UEFI架构

    UEFI架构 UEFI提供系统化的标准方法 xff0c 加载驱动并管理他们之间的交互 前言 xff1a 感谢uefi blog UEFI 提供了一个标准接口 xff0c 以便在硬件发生变更时固件能提供足够信息而保证操作系统不受影响 它包含有
  • C++调试工具(未完)

    C 43 43 调试相关命令 ld so conf https blog csdn net Bruce 0712 article details 78816790相关的命令 ar nm 目标格式文件分析 xff0c 所以也可以分析 a文件
  • 11_UART串口

    11 UART 文章目录 11 UART1 串口连接芯片图2 串口传输一个字节的过程3 发送接收过程4 编写UART函数4 1 初始化函数uart0 init 4 1 1 设置引脚用于串口4 1 2 使能上拉4 1 3 设置波特率4 1 4
  • 汇编指令:LDMIA、LDMIB、LDMDB、LDMDA、STMIA、LDMFD、LDMFA、LDMED、LDMEA

    ARM指令中多数据传输共有两种 xff1a LDM load much xff1a 多数据加载 将地址上的值加载到寄存器上 STM store much xff1a 多数据存储 将寄存器的值存到地址上 主要用途 xff1a 现场保护 数据复
  • C++ 实现 发送HTTP Get/Post请求

    1 简述 最近简单看了一下关于HTTP请求方面的知识 xff0c 之前一直用Qt来实现 xff0c 有专门HTTP请求的QNetworkAccessManager类来处理 xff0c 实现也比较简单 xff0c 这里主要讲解一下用C 43
  • [Simple] 洗牌算法

    题目要求 xff1a 平时洗牌是两打牌 xff0c 交叉洗在一起 也就是开始 1 2 3 4 5 6 7 8 第一次 1 5 2 6 3 7 4 8 第二次 1 3 5 7 2 4 6 8 第k次 给你一个数组a 2N xff0c 要求在O
  • 【PID控制原理及其算法】

    前言 本文以自己的学习过程总结而来 xff0c 将自己的经验写出来以供大家一起学习 xff0c 如有错误请多指教 一 PID是什么 xff1f PID就是比例 积分 微分 xff0c PID算法可以说是在自动控制原理中比较经典的一套算法 x
  • printf重定向的相关总结

    简介 实现printf重定向有多种方式 xff0c 下面一一介绍 linux环境下 虽然linux系统的默认标准输出设备是显示器 xff0c 但是我们可以把printf打印输出的内容重定向到其他设备或文件 方法如下 xff1a 方法1 xf
  • 开发者七问七答:什么是产品化?

    简介 xff1a 之前参加了企业智能部门如何做产品化的讨论 xff0c 大家对产品化的定义和过程都有各自不同的见解 我觉得这个话题其实可以扩展下 xff0c 想站在一个开发人员的视角尝试探讨一下产品化 下面以自问自答的方式来展开 1 当我们
  • 系统调用和库函数及API的区别

    在写程序的过程中 xff0c 像MFC xff0c VC 43 43 这些编程 xff0c 都会涉及到函数的调用 xff0c 有库函数也有系统函数 xff0c 下面看一看它们的区别 xff01 xff01 系统调用 xff08 system
  • 应用服务器与zk之间的连接超时

    关于connectString服务器地址配置 格式 192 168 1 1 2181 192 168 1 2 2181 192 168 1 3 2181 这个地址配置有多个ip port之间逗号分隔 底层操作 span class hljs
  • 日本小学生走向APP开发私塾 智能手机迫切改变IT教育——日本经济新闻报道

    如要在日本接受专门的信息技术教育 xff08 IT xff09 xff0c 只有结束义务教育课程才能接受 如今 xff0c 打破这些障碍的趋势逐渐浓厚 因为从小就接触到各种数字机器和互联网而长大的 数字土著 xff08 digital na
  • 步进电机和伺服电机的区别

    步进电机作为一种开环控制的系统 xff0c 和现代数字控制技术有着本质的联系 在目前国内的数字控制系统中 xff0c 步进电机的应用十分广泛 随着全数字式交流伺服系统的出现 xff0c 交流伺服电机也越来越多地应用于数字控制系统中 为了适应
  • 【图像处理】墨西哥小波和带通滤波

    一 说明 在连续小波的家族当中 xff0c 埃尔米特小波是个非常特别的存在 xff08 应用在连续小波转换称作埃尔米特转换 xff09 Ricker子波计算电动力学的广谱源项 它通常只在美国才会被称作墨西哥帽小波 xff0c 因为在作为核函
  • 【halcon知识】应用仿射变换

    一 说明 无论什么样的变换 xff0c 都离不开齐次变换矩阵 一般地 xff0c 先准备一个空的齐次变换矩阵 xff0c 这个矩阵随便填写 xff1a 1 xff09 填入旋转类参数就是旋转矩阵 xff0c 2 填入仿射参数就可进行仿射变换
  • 【ROS2知识】SQLite数据库

    目录 一 说明 二 介绍SQLite 三 安装 3 1 简单测试 生成一个表 3 2 sqlite 共五种数据类型
  • open3D

    目录 一 说明 二 如何安装open3d xff1f 三 显示点云数据 3 1 显示点云场景数据 3 2 体素下采样 3 3 顶点法线估计 一 说明 对于点云 处理 xff0c 这里介绍哦pen3d xff0c 该软件和opencv同样是i
  • 【计算几何7】帝国边界划分问题【Voronoi图的原理】

    目录 一 说明 二 帝国边界划分问题 三 voronoi的正规定义 3 1 最简单的voronoi情况 3 2 在距离空间的数学描述 3 3 不同距离空间所得 Voronoi 单元不同 四 代码和库 4 1 算法库 4 2 参数说明 4 3