遥感图像地物覆盖分类,数据集制作-分类模型对比-分类保姆级教程

在遥感影像上人工制作分类数据集

1.新建shp文件
地理坐标系保持和影像一致,面类型
在这里插入图片描述
2.打开属性表
在这里插入图片描述
3.添加字段
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
这里分类6类,点击添加值添加
在这里插入图片描述
添加完毕
在这里插入图片描述
开始人工选地物类型,制作数据集
在这里插入图片描述

在这里插入图片描述

开始标注,标注的时候可以借助谷歌地图来看
在这里插入图片描述
标记足够多的样本
在这里插入图片描述
打开面转栅格工具
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
设置nodata值为15

采用python+gdal库制作数据集



import csv
import numpy as np
import rasterio
import pandas as pd


def readTif(fileName):
    try:
        dataset = rasterio.open(fileName)
        return dataset
    except rasterio.errors.RasterioIOError:
        print(f"文件 {fileName} 无法打开")
        return None


num_bands = 8
csv_head_name = [f'Band{i}' for i in range(1, num_bands + 1)] + ['Label', 'LabelName']
labels_name = {0: "水体", 1: "植被",2: "建筑",3: "裸地",4: "农田",5: "道路"}

ori_dataset = readTif(orgin_path)
label_dataset = readTif(sample_path)

if ori_dataset is not None and label_dataset is not None:
    label_matri = label_dataset.read(1)
    data_matri = ori_dataset.read()
    nodata_indices = np.where(label_matri != 15)  # 获取所有非 nodata 的索引


    # 准备数据
    data = []
    for i in range(nodata_indices[0].size):
        row, col = nodata_indices[0][i], nodata_indices[1][i]
        label = label_matri[row, col]
        band_values = data_matri[:, row, col].tolist()
        label_name = labels_name.get(label, 'Unknown')
        band_values.extend([label, label_name])
        data.append(band_values)

    df = pd.DataFrame(data, columns=csv_head_name)

    # 下采样多数类
    g = df.groupby('LabelName')
    df = g.apply(lambda x: x.sample(g.size().min())).reset_index(drop=True)
    #首先将所有数据读取到一个Pandas DataFrame中。然后,使用DataFrame的groupby方法按标签进行分组,并应用sample函数对每个类别进行随机抽样,抽样数等于所有类别中样本最少的那个。这样做可以确保每个类别在最终数据集中有相同数量的样本,从而达到类别平衡。首先将所有数据读取到一个Pandas DataFrame中。
    # 然后,使用DataFrame的groupby方法按标签进行分组,并应用sample函数对每个类别进行随机抽样,抽样数等于所有类别中样本最少的那个。这样做可以确保每个类别在最终数据集中有相同数量的样本,从而达到类别平衡。
    # 写入 CSV
    df.to_csv(csv_filename, index=False, encoding='utf_8_sig')
    print(f"已将数据写入 CSV 文件: {csv_filename}")

得到的表格如下
在这里插入图片描述

挑选分类模型



import pandas as pd
from sklearn.ensemble import RandomForestClassifier
from sklearn.svm import SVC
from sklearn.linear_model import LogisticRegression
from sklearn.neighbors import KNeighborsClassifier
from sklearn.model_selection import train_test_split, cross_val_score
from sklearn.metrics import confusion_matrix, accuracy_score
import numpy as np

# 读取CSV文件的路径
path = r"F:\datasets\ZY1E\不透水面提取\地物覆盖分类\labels.csv"

# 读取数据集
data = pd.read_csv(path)

# 划分数据与标签
x = data.iloc[:, 0:8]  # 假设前8列是数据
y = data['Label']  # 标签在'Label'列

# 划分训练集和测试集
train_data, test_data, train_label, test_label = train_test_split(x, y, random_state=1, train_size=0.7, test_size=0.3)

# 创建各种模型
models = {
    'Random Forest': RandomForestClassifier(n_estimators=100, bootstrap=True, max_features='sqrt'),
    'SVM': SVC(kernel='linear', C=1, decision_function_shape='ovr'),
    'Logistic Regression': LogisticRegression(max_iter=1000),
    'KNN': KNeighborsClassifier(n_neighbors=5)
}

# 训练并评估模型
for name, model in models.items():
    try:
        model.fit(train_data, train_label.ravel())  # 训练模型
        train_pred = model.predict(train_data)
        test_pred = model.predict(test_data)
    except Exception as e:
        print(f"在模型 {name} 中发生错误: {str(e)}")
        continue

    print(f"\n{name}:")
    print("  训练集准确率:", accuracy_score(train_label, train_pred))
    print("  测试集准确率:", accuracy_score(test_label, test_pred))
    print("  交叉验证准确率:", np.mean(cross_val_score(model, x, y, cv=5)))
    print("  训练集混淆矩阵:\n", confusion_matrix(train_label, train_pred))
    print("  测试集混淆矩阵:\n", confusion_matrix(test_label, test_pred))

得到输出结果

Random Forest:
训练集准确率: 1.0
测试集准确率: 0.9258809234507898
交叉验证准确率: 0.9128402004972545
训练集混淆矩阵:
[[319 0 0 0 0 0]
[ 0 314 0 0 0 0]
[ 0 0 304 0 0 0]
[ 0 0 0 332 0 0]
[ 0 0 0 0 334 0]
[ 0 0 0 0 0 316]]
测试集混淆矩阵:
[[138 0 0 0 0 0]
[ 0 139 1 0 3 0]
[ 0 0 138 1 1 13]
[ 0 0 1 123 0 1]
[ 0 17 0 2 104 0]
[ 0 0 18 3 0 120]]

SVM:
训练集准确率: 0.7634184471078687
测试集准确率: 0.7800729040097205
交叉验证准确率: 0.7629439059737013
训练集混淆矩阵:
[[317 0 0 0 0 2]
[ 0 233 0 1 78 2]
[ 0 1 186 55 1 61]
[ 0 3 18 241 19 51]
[ 0 81 0 15 223 15]
[ 4 0 41 6 0 265]]
测试集混淆矩阵:
[[138 0 0 0 0 0]
[ 0 108 0 1 34 0]
[ 0 1 98 30 0 24]
[ 0 2 2 102 8 11]
[ 0 34 0 6 78 5]
[ 1 0 20 2 0 118]]

Logistic Regression:
训练集准确率: 0.7535174570088587
测试集准确率: 0.7533414337788579
交叉验证准确率: 0.7654939970483826
训练集混淆矩阵:
[[319 0 0 0 0 0]
[ 1 192 0 1 118 2]
[ 0 1 180 58 1 64]
[ 0 0 20 243 18 51]
[ 0 59 0 15 247 13]
[ 12 0 32 7 0 265]]
测试集混淆矩阵:
[[138 0 0 0 0 0]
[ 0 82 0 1 60 0]
[ 0 1 98 29 0 25]
[ 0 0 5 100 9 11]
[ 0 26 0 6 86 5]
[ 4 0 20 1 0 116]]

KNN:
训练集准确率: 0.9322563835330901
测试集准确率: 0.9015795868772782
交叉验证准确率: 0.90445468203635
训练集混淆矩阵:
[[318 0 0 0 0 1]
[ 0 292 1 0 21 0]
[ 0 0 255 20 1 28]
[ 0 0 0 326 0 6]
[ 0 25 0 1 308 0]
[ 0 0 20 6 0 290]]
测试集混淆矩阵:
[[137 0 0 0 0 1]
[ 0 128 1 3 11 0]
[ 0 0 127 5 1 20]
[ 0 0 0 123 0 2]
[ 0 19 0 1 103 0]
[ 0 0 13 3 1 124]]

Process finished with exit code 0

选择随机森林模型建模分类




import pandas as pd
from sklearn.ensemble import RandomForestClassifier
from sklearn.model_selection import train_test_split, cross_val_score
import pickle
from sklearn.metrics import confusion_matrix
import numpy as np

# 读取CSV文件的路径


# 1.读取数据集
data = pd.read_csv(path)

# 2.划分数据与标签
x = data.iloc[:, 0:8]  # 假设前8列是数据
y = data['Label']  # 假设标签在'Label'列

# 3.划分训练集和测试集
train_data, test_data, train_label, test_label = train_test_split(x, y, random_state=1, train_size=0.7, test_size=0.3)

# 4.创建随机森林模型并训练
classifier = RandomForestClassifier(n_estimators=100, bootstrap=True, max_features='sqrt')
classifier.fit(train_data, train_label.ravel())  # ravel函数拉伸到一维

# 5.计算准确率
print("训练集准确率:", classifier.score(train_data, train_label))
print("测试集准确率:", classifier.score(test_data, test_label))

# 6.交叉验证
scores = cross_val_score(classifier, x, y, cv=5)  # 5折交叉验证
print("平均交叉验证准确率:", np.mean(scores))

# 7.特征重要性
feature_importances = pd.Series(classifier.feature_importances_, index=x.columns)
print("特征重要性:\n", feature_importances.sort_values(ascending=False))

# 8.混淆矩阵
train_pred = classifier.predict(train_data)
test_pred = classifier.predict(test_data)
print("训练集混淆矩阵:\n", confusion_matrix(train_label, train_pred))
print("测试集混淆矩阵:\n", confusion_matrix(test_label, test_pred))

# 9.保存模型
with open(SavePath, "wb") as file:
    pickle.dump(classifier, file)

训练集准确率: 1.0
测试集准确率: 0.9149453219927096
平均交叉验证准确率: 0.9146590350072461
特征重要性:
Band8 0.177021
Band4 0.145268
Band5 0.139987
Band1 0.132925
Band7 0.125840
Band3 0.103912
Band2 0.093239
Band6 0.081808
dtype: float64
训练集混淆矩阵:
[[319 0 0 0 0 0]
[ 0 314 0 0 0 0]
[ 0 0 304 0 0 0]
[ 0 0 0 332 0 0]
[ 0 0 0 0 334 0]
[ 0 0 0 0 0 316]]
测试集混淆矩阵:
[[138 0 0 0 0 0]
[ 0 140 1 0 2 0]
[ 0 0 134 1 1 17]
[ 0 0 0 123 0 2]
[ 0 16 0 2 105 0]
[ 0 0 21 7 0 113]]

遥感图像预测


import numpy as np
import gdal
import pickle
#读取tif数据集
def readTif(fileName):
    dataset = gdal.Open(fileName)
    if dataset == None:
        print(fileName+"文件无法打开")
    return dataset
#保存tif文件函数
def writeTiff(im_data,im_geotrans,im_proj,path):
    if 'int8' in im_data.dtype.name:
        datatype = gdal.GDT_Byte
    elif 'int16' in im_data.dtype.name:
        datatype = gdal.GDT_UInt16
    else:
        datatype = gdal.GDT_Float32
    if len(im_data.shape) == 3:
        im_bands, im_height, im_width = im_data.shape
    elif len(im_data.shape) == 2:
        im_data = np.array([im_data])
        im_bands, im_height, im_width = im_data.shape
    #创建文件
    driver = gdal.GetDriverByName("GTiff")
    dataset = driver.Create(path, int(im_width), int(im_height), int(im_bands), datatype)
    if(dataset!= None):
        dataset.SetGeoTransform(im_geotrans) #写入仿射变换参数
        dataset.SetProjection(im_proj) #写入投影
    for i in range(im_bands):
        dataset.GetRasterBand(i+1).WriteArray(im_data[i])
    del dataset



dataset = readTif(Landset_Path)
Tif_width = dataset.RasterXSize #栅格矩阵的列数
Tif_height = dataset.RasterYSize #栅格矩阵的行数
Tif_geotrans = dataset.GetGeoTransform()#获取仿射矩阵信息
Tif_proj = dataset.GetProjection()#获取投影信息
Landset_data = dataset.ReadAsArray(0,0,Tif_width,Tif_height)
#调用保存好的模型
#以读二进制的方式打开文件
file = open(RFpath, "rb")
#把模型从文件中读取出来
rf_model = pickle.load(file)
#关闭文件
file.close()
#用读入的模型进行预测
#  在与测试前要调整一下数据的格式
data = np.zeros((Landset_data.shape[0],Landset_data.shape[1]*Landset_data.shape[2]))
for i in range(Landset_data.shape[0]):
    data[i] = Landset_data[i].flatten()
data = data.swapaxes(0,1)
#  对调整好格式的数据进行预测
pred = rf_model.predict(data)
print("Unique predictions:", np.unique(pred))
print("Max prediction:", np.max(pred))
print("Min prediction:", np.min(pred))

#  同样地,我们对预测好的数据调整为我们图像的格式
pred = pred.reshape(Landset_data.shape[1],Landset_data.shape[2])
pred = pred.astype(np.uint8)
#  将结果写到tif图像里
writeTiff(pred,Tif_geotrans,Tif_proj,SavePath)

在这里插入图片描述

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

记录清除挖矿病毒 solrd 过程

1、发现solrd病毒 端午节期间,kafka 服务器被黑客攻击了,植入了挖矿病毒 solrd,这个病毒很聪明,内存,CPU并没有异常升高,以致于上班第一天完全没有察觉。 上班第一天 正常登录服务器查看 flink ,消费kafka…

Eclipse创建Spring项目

第一步&#xff1a;先用Eclipse创建一个tomcat项目 打开eclipse 配置tomcat 这里点击add去添加tomcat 创建项目 写好项目名字&#xff0c;点击next 将这个Deploy path修改一下 配置一下项目&#xff0c;将项目部署到tomcat上面去 写个html测试一下 <html><h1>Hel…

tensorboard终于不报错了!

之前tensorboard笔记,记录2种使用方法&#xff0c;可以参考&#xff01; 有图这也没有数据啊这也。实际是没点对&#xff0c;干了个大噶。选择上方scalars就能看见图了&#xff01;&#xff01;&#xff01;&#xff01;&#xff01;&#xff01;&#xff01;&#xff01;&…

GitHub新手使用基本流程(保姆级教程)

GitHub&#xff0c; 一个聚合了海量开源免费的软件、电子书、视频课等资源的神仙网站&#xff0c;如果你还不会用GitHub&#xff0c;这条保姆级教程&#xff0c;您千万不要错过。 首先打开浏览器搜索GitHub, 点击进入官网 如果遇到无法加载的问题&#xff0c;可以试试这个名叫…

机器视觉:工业相机的主要参数

工业相机是将目标物体的表面特征信息转化为数字信号&#xff08;或者模拟信号&#xff09;的一种采集设备。 一、工业相机的成像原理 工业相机主要由光电传感器和转换电路组成。 光线照射到被检测物体的表面&#xff0c;反射光经过透镜&#xff0c;再进入相机的光电传感器&a…

从报名到领证:软考初级【信息系统运行管理员】报名考试全攻略

本文共计9991字&#xff0c;预计阅读33分钟。包括七个篇章&#xff1a;报名、准考证打印、备考、考试、成绩查询、证书领取及常见问题。 一、报名篇 报名条件要求&#xff1a; 1.凡遵守中华人民共和国宪法和各项法律&#xff0c;恪守职业道德&#xff0c;具有一定计算机技术…

flask基础3-蓝图-cookie-钩函数-flask上下文-异常处理

目录 一&#xff1a;蓝图 1.蓝图介绍 2.使用步骤 3.蓝图中的静态资源和模板 二.cookie和session 1.cookie 2.flask中操作cookie 3.session 4.session操作步骤 三.请求钩子 四.flask上下文 1.介绍 2.请求上下文&#xff1a; 3.应用上下文 3.g对象 五&#xff1a;…

STM32高级控制定时器(STM32F103):TIM1和TIM8介绍

目录 概述 1 认识TIM1和TIM8 2 TIM1和TIM8的特性 3 TIM1和TIM6时基和分频 3.1 时基单元 3.2 预分频 3.3 时基和分频相关寄存器 3.3.1TIMx_CR1 3.3.2 TIMx_PSC 概述 本文主要介绍STM32高级定时器TIM1和TIM8的功能&#xff0c;还介绍了与之相关的寄存器的配置参数。包括…

如何在3天内开发一个鸿蒙app

华为鸿蒙操作系统&#xff08;HarmonyOS&#xff09;自2.0版本正式上线以来&#xff0c;在短时间内就部署超过了2亿台设备&#xff0c;纵观全球操作系统的发展史&#xff0c;也是十分罕见的。与其他手机操作系统不同&#xff0c;HarmonyOS自诞生之日起&#xff0c;就是一款面向…

layui一个页面多个table显示时工具栏被下方的table遮挡

记录&#xff1a;layui一个页面多个table显示时工具栏被下方的table遮挡 css代码&#xff1a; [lay-idcurrentTableId] .layui-table-tool {position: relative;z-index: 9999;width: 100%;min-height: 50px;line-height: 30px;padding: 10px 15px;border-width: 0;border-bot…

c#中上传超过30mb的文件,接口一直报404,小于30mb的却可以上传成功

在一次前端实现上传视频文件时,超过30mb的文件上传,访问接口一直报404,但是在Swagger中直接访问接口确是正常的,且在后端控制器中添加了限制特性,如下 但是却仍然报404,在apifox中请求接口也是报404, 网上说: 在ASP.NET Core中,配置请求过来的文件上传的大小限制通常…

jfif格式怎么转换成jpg?关于将jfif转成jpg的几种方法

jfif格式怎么转换成jpg&#xff1f;JFIF格式是一种常见的图像文件格式&#xff0c;通常用于存储数字照片。然而&#xff0c;在某些情况下&#xff0c;你可能需要将JFIF格式转换为JPG格式。JPG格式是一种广泛使用的图像格式&#xff0c;它被支持和接受的程度比JFIF更高。PNG是一…

C++迈向精通:当我尝试修改虚函数表

尝试修改虚函数表 本期纯整活儿好吧&#xff01;&#xff01;&#xff01;&#xff01; 初衷 有一天我突然开始好奇虚函数表是否真的存在&#xff0c;于是我开始想是否能够从C中查看或者调用虚函数表中的内容。&#xff0c;于是有了下面的操作。 操作过程 起初我并没有思路…

加入牛导研究团队|普通高校老师获得香港理工大学访问学者邀请函

随着国内高校高层次人才引进机制的日益完善&#xff0c;本校教师也倍感竞争压力日趋激烈&#xff0c;而出国访学&#xff0c;加入牛导的科研团队&#xff0c;发表高质量的论文&#xff0c;是提升自己学术水平的有效途径。本案例中的O老师就是借助知识人网的帮助&#xff0c;实现…

docker-compose harbor 2.11

harbor 前言 “Harbor” 是一个用于管理容器镜像的开源仓库项目。由 VMware 开发和维护,Harbor 提供一个企业级的 Docker 镜像仓库,具有丰富的功能,包括: 镜像管理:提供存储和分发 Docker 镜像的能力。安全性:支持镜像签名和漏洞扫描,确保镜像的安全性。身份认证:集成…

SECS/GEM 底层协议解析

SECS是什么&#xff1f; SEMI电子半导体联盟,为实现设备与工厂系统的快速对接数据,状态,配方,程序的标准化协议,SECS具有多个版本,本文主要介绍E5协议 HSMS通信方式,设备端的处理流程(Passive模式)。 SECS关键字 Host 主机一般指向工厂控制系统EQP 单机设备Active 在Tcp通信…

SAP 价格金额信息控制

1)migo / mb51/mb51/mb59 关于价格和金额的显示&#xff0c;需要权限控制&#xff0c;当权限对象F_BKPF_BUK,检查对应【公司代码】 和 ACTVT有03’的权限&#xff0c;如果没有03的权限&#xff0c;对应行的价格和金额显示为空 关于价格和金额的显示&#xff0c;需要权限控制&a…

Java——重载

一、重载&#xff08;Overload&#xff09; 1、重载是什么 方法重载&#xff08;Method Overloading&#xff09;是Java中实现多态的一种方式。它允许在同一个类中定义多个同名的方法&#xff0c;只要这些方法的参数列表不同。这些不同的参数列表可以通过不同的参数类型、参数…

【制作100个unity游戏之27】使用unity复刻经典游戏《植物大战僵尸》,制作属于自己的植物大战僵尸随机版和杂交版12(附带项目源码)

最终效果 系列导航 文章目录 最终效果系列导航前言UI框架先绘制一些常用UI面板&#xff0c;设置为预制件提示弹窗用户列表菜单输入框弹窗 创建各个面板的脚本控制代码控制菜单界面按钮事件 源码结束语 前言 本节主要实现UI框架调用不同的面板界面 UI框架 不懂UI框架的设计思路…

visdom使用时所遇的问题及解决方法

最近在用visdom进行可视化的过程中&#xff0c;虽然可有效的避免主机拒绝访问&#xff08;该问题的解决方法&#xff0c;请参考深度学习可视化工具visdom使用-CSDN博客&#xff09;即在终端输入python -m visom.server 1.训练过程中visdom出现ValueError: too many file descr…