物种分布的核密度估计

Machine LearningMachine LearningBeginner
立即练习

This tutorial is from open-source community. Access the source code

💡 本教程由 AI 辅助翻译自英文原版。如需查看原文,您可以 切换至英文原版

简介

本实验展示了一个基于邻居的地理空间数据查询示例(特别是核密度估计),使用基于哈弗辛距离度量构建的球树——即经纬度点之间的距离。数据集由菲利普斯等人(2006年)提供。该示例使用底图库绘制南美洲的海岸线和国家边界。

虚拟机使用提示

虚拟机启动完成后,点击左上角切换到“笔记本”标签,以访问Jupyter Notebook进行练习。

有时,你可能需要等待几秒钟让Jupyter Notebook完成加载。由于Jupyter Notebook的限制,操作验证无法自动化。

如果你在学习过程中遇到问题,随时向Labby提问。课程结束后提供反馈,我们将立即为你解决问题。


Skills Graph

%%%%{init: {'theme':'neutral'}}%%%% flowchart RL sklearn(("Sklearn")) -.-> sklearn/CoreModelsandAlgorithmsGroup(["Core Models and Algorithms"]) sklearn(("Sklearn")) -.-> sklearn/UtilitiesandDatasetsGroup(["Utilities and Datasets"]) ml(("Machine Learning")) -.-> ml/FrameworkandSoftwareGroup(["Framework and Software"]) sklearn/CoreModelsandAlgorithmsGroup -.-> sklearn/neighbors("Nearest Neighbors") sklearn/UtilitiesandDatasetsGroup -.-> sklearn/datasets("Datasets") ml/FrameworkandSoftwareGroup -.-> ml/sklearn("scikit-learn") subgraph Lab Skills sklearn/neighbors -.-> lab-49299{{"物种分布的核密度估计"}} sklearn/datasets -.-> lab-49299{{"物种分布的核密度估计"}} ml/sklearn -.-> lab-49299{{"物种分布的核密度估计"}} end

导入所需库

第一步是导入本实验所需的库。在本实验中,我们将使用numpy、matplotlib、fetch_species_distributions和KernelDensity库。

import numpy as np
import matplotlib.pyplot as plt
from sklearn.datasets import fetch_species_distributions
from sklearn.neighbors import KernelDensity

加载数据

下一步是加载菲利普斯等人(2006年)提供的数据。该数据集包含两个物种,我们将用它们来演示核密度估计。

data = fetch_species_distributions()
species_names = ["Bradypus Variegatus", "Microryzomys Minutus"]

准备数据

现在我们将为核密度估计准备数据。我们将从数据集中提取纬度和经度信息,并将它们转换为弧度。

Xtrain = np.vstack([data["train"]["dd lat"], data["train"]["dd long"]]).T
ytrain = np.array(
    [d.decode("ascii").startswith("micro") for d in data["train"]["species"]],
    dtype="int",
)
Xtrain *= np.pi / 180.0  ## Convert lat/long to radians

构建网格

现在我们将从批次对象构建地图网格。我们将使用construct_grids函数来实现这一点。

def construct_grids(batch):
    """从批次对象构建地图网格

    参数
    ----------
    batch : 批次对象
        :func:`fetch_species_distributions`返回的对象

    返回
    -------
    (xgrid, ygrid) : 一维数组
        与batch.coverages中的值对应的网格
    """
    ## 角单元格的x、y坐标
    xmin = batch.x_left_lower_corner + batch.grid_size
    xmax = xmin + (batch.Nx * batch.grid_size)
    ymin = batch.y_left_lower_corner + batch.grid_size
    ymax = ymin + (batch.Ny * batch.grid_size)

    ## 网格单元格的x坐标
    xgrid = np.arange(xmin, xmax, batch.grid_size)
    ## 网格单元格的y坐标
    ygrid = np.arange(ymin, ymax, batch.grid_size)

    return (xgrid, ygrid)

## 调用函数并将结果存储在xgrid和ygrid中
xgrid, ygrid = construct_grids(data)

准备数据网格

我们将为等高线图设置数据网格。我们将使用construct_grids函数来实现这一点。

X, Y = np.meshgrid(xgrid[::5], ygrid[::5][::-1])
land_reference = data.coverages[6][::5, ::5]
land_mask = (land_reference > -9999).ravel()

xy = np.vstack([Y.ravel(), X.ravel()]).T
xy = xy[land_mask]
xy *= np.pi / 180.0

绘制南美洲地图

现在我们将绘制南美洲地图,并标注出每个物种的分布情况。

fig = plt.figure()
fig.subplots_adjust(left=0.05, right=0.95, wspace=0.05)

for i in range(2):
    plt.subplot(1, 2, i + 1)

    print(" - 在球坐标中计算核密度估计")
    kde = KernelDensity(
        bandwidth=0.04, metric="haversine", kernel="gaussian", algorithm="ball_tree"
    )
    kde.fit(Xtrain[ytrain == i])

    Z = np.full(land_mask.shape[0], -9999, dtype="int")
    Z[land_mask] = np.exp(kde.score_samples(xy))
    Z = Z.reshape(X.shape)

    levels = np.linspace(0, Z.max(), 25)
    plt.contourf(X, Y, Z, levels=levels, cmap=plt.cm.Reds)

    if basemap:
        print(" - 使用Basemap绘制海岸线")
        m = Basemap(
            projection="cyl",
            llcrnrlat=Y.min(),
            urcrnrlat=Y.max(),
            llcrnrlon=X.min(),
            urcrnrlon=X.max(),
            resolution="c",
        )
        m.drawcoastlines()
        m.drawcountries()
    else:
        print(" - 根据覆盖范围绘制海岸线")
        plt.contour(
            X, Y, land_reference, levels=[-9998], colors="k", linestyles="solid"
        )
        plt.xticks([])
        plt.yticks([])

    plt.title(species_names[i])

plt.show()

总结

在本实验中,我们学习了如何对地理空间数据进行核密度估计。我们使用了菲利普斯等人(2006年)的数据集来演示这项技术。我们还学习了如何使用basemap库绘制南美洲地图以及每个物种的分布情况。