Python处理栅格数据

想要将以下遥感影像首先进行kmeans聚类,然后对聚类结果进行Delaunay三角网通过约束条件进行二次划分。最后再把结果保存为tif格式影像。

img

dataset = gdal.Open("F:\Graduate smoothly\MoreBuFen.tif")
rows = dataset.RasterYSize
cols = dataset.RasterXSize
# bands = dataset.RasterCount
# data = dataset.ReadAsArray()
# data_2d = np.transpose(data, (1, 2, 0)).reshape(bands,rows * cols)

band = dataset.GetRasterBand(1)  # 获取栅格数据集的第一个波段
grid_data = band.ReadAsArray()  # 将波段数据读取为一个NumPy数组
data = grid_data.flatten()  # 将二维数组转换为一维数组
data_1d = data.reshape(-1, 1)  # 将数组重新调整形状为一列

kmeans = KMeans(n_clusters=5, n_init='auto').fit(data_1d)
labels = kmeans.labels_.reshape(rows,cols)  # 将聚类标签转换为与影像数据相同的二维数组形式
clusters_partitions = []  # 存储每个簇的空间分区结果
for i in range(kmeans.n_clusters):  # 对每个簇进行处理
    cluster_points = np.argwhere(labels == i)  # 获取第i个簇的所有像素点的坐标
    A = 3
    tri = Delaunay(cluster_points)
    edge_lengths = np.sqrt(
        np.sum((cluster_points[tri.simplices[:, 0]] - cluster_points[tri.simplices[:, 1]]) ** 2,
               axis=1))
    triangles = tri.simplices[edge_lengths <= np.mean(edge_lengths) + A * np.std(edge_lengths)]
    clusters_partitions.append(triangles)  # 存储空间分区结果
partition_result = np.zeros((rows, cols)) # 创建一个与原始影像数据相同大小的数组,用于存储空间分区结果
# # 将每个簇的空间分区结果赋值给partition_result数组
for i, partition in enumerate(clusters_partitions):
     partition_result[np.unravel_index(partition.ravel(), (rows, cols))] = i + 1
# 创建一个与原始影像数据相同的GeoTIFF文件
driver = gdal.GetDriverByName('GTiff')
output_file = driver.Create('F:\Graduate smoothly\Result.tif', cols, rows, 1, gdal.GDT_Float32)
# 将partition_result数组写入GeoTIFF文件
output_file.GetRasterBand(1).WriteArray(partition_result)
# 设置GeoTIFF文件的地理信息
output_file.SetGeoTransform(dataset.GetGeoTransform())
output_file.SetProjection(dataset.GetProjection())
# 保存GeoTIFF文件
output_file.FlushCache()

我按照以上代码得到如下图像,坐标轴代表着行列号,但是是不是数据已经没有了空间关系?应该怎么更改呢?

img

你修改下代码试着把簇空间分区写入GEOTIFF


import gdal
import numpy as np
from sklearn.cluster import KMeans
from scipy.spatial import Delaunay

dataset = gdal.Open("F:\Graduate smoothly\MoreBuFen.tif")
rows = dataset.RasterYSize
cols = dataset.RasterXSize

geo_transform = dataset.GetGeoTransform()
projection = dataset.GetProjection()
band = dataset.GetRasterBand(1)
grid_data = band.ReadAsArray()

data = grid_data.flatten()
data_1d = data.reshape(-1, 1)

kmeans = KMeans(n_clusters=5, n_init='auto').fit(data_1d)
labels = kmeans.labels_.reshape(rows, cols)

clusters_partitions = []  
for i in range(kmeans.n_clusters):  
    cluster_points = np.argwhere(labels == i)  
    A = 3
    tri = Delaunay(cluster_points)
    edge_lengths = np.sqrt(
        np.sum((cluster_points[tri.simplices[:, 0]] - cluster_points[tri.simplices[:, 1]]) ** 2,
               axis=1))
    triangles = tri.simplices[edge_lengths <= np.mean(edge_lengths) + A * np.std(edge_lengths)]
    clusters_partitions.append(triangles)

partition_result = np.zeros((rows, cols)) 
for i, partition in enumerate(clusters_partitions):
    partition_result[np.unravel_index(partition.ravel(), (rows, cols))] = i + 1

driver = gdal.GetDriverByName('GTiff')
output_file = driver.Create('F:\Graduate smoothly\Result.tif', cols, rows, 1, gdal.GDT_Float32)
output_file.GetRasterBand(1).WriteArray(partition_result)
output_file.SetGeoTransform(geo_transform)
output_file.SetProjection(projection)
output_file.FlushCache()

参考gpt:
结合自己分析给你如下建议:
我看了你的代码和结果,发现你的问题可能是由于你没有正确地设置输出文件的地理坐标系和仿射变换参数。这样会导致输出文件的空间位置和原始影像数据不一致,无法正确地显示在地图上。你可以尝试用以下方法解决:
在你创建输出文件时,使用 dataset.GetProjection() 和 dataset.GetGeoTransform() 方法来获取原始影像数据的地理坐标系和仿射变换参数,并将它们设置给输出文件。
在你写入空间分区结果之前,使用 np.flipud(partition_result) 方法来将数组沿垂直方向翻转,以保持和原始影像数据相同的行列顺序。
在你保存输出文件之前,使用 output_file.SetMetadata(dataset.GetMetadata()) 方法来复制原始影像数据的元数据信息,以便于后续的处理和分析。
修改后的代码如下:

Script to perform k-means clustering and Delaunay triangulation on a remote sensing image
import os from osgeo import gdal import numpy as np from sklearn.cluster import KMeans from scipy.spatial import Delaunay

dataset = gdal.Open(“F:\Graduate smoothly\MoreBuFen.tif”) rows = dataset.RasterYSize cols = dataset.RasterXSize band = dataset.GetRasterBand(1) # 获取栅格数据集的第一个波段 grid_data = band.ReadAsArray() # 将波段数据读取为一个NumPy数组 data = grid_data.flatten() # 将二维数组转换为一维数组 data_1d = data.reshape(-1, 1) # 将数组重新调整形状为一列

kmeans = KMeans(n_clusters=5, n_init=‘auto’).fit(data_1d) labels = kmeans.labels_.reshape(rows,cols) # 将聚类标签转换为与影像数据相同的二维数组形式 clusters_partitions = [] # 存储每个簇的空间分区结果 for i in range(kmeans.n_clusters): # 对每个簇进行处理 cluster_points = np.argwhere(labels == i) # 获取第i个簇的所有像素点的坐标 A = 3 tri = Delaunay(cluster_points) edge_lengths = np.sqrt( np.sum((cluster_points[tri.simplices[:, 0]] - cluster_points[tri.simplices[:, 1]]) ** 2, axis=1)) triangles = tri.simplices[edge_lengths <= np.mean(edge_lengths) + A * np.std(edge_lengths)] clusters_partitions.append(triangles) # 存储空间分区结果 partition_result = np.zeros((rows, cols)) # 创建一个与原始影像数据相同大小的数组,用于存储空间分区结果

将每个簇的空间分区结果赋值给partition_result数组
for i, partition in enumerate(clusters_partitions): partition_result[np.unravel_index(partition.ravel(), (rows, cols))] = i + 1

创建一个与原始影像数据相同的GeoTIFF文件
driver = gdal.GetDriverByName(‘GTiff’) output_file = driver.Create(‘F:\Graduate smoothly\Result.tif’, cols, rows, 1, gdal.GDT_Float32)

设置GeoTIFF文件的地理信息
output_file.SetProjection(dataset.GetProjection()) output_file.SetGeoTransform(dataset.GetGeoTransform())

翻转partition_result数组以保持行列顺序一致
partition_result = np.flipud(partition_result)

将partition_result数组写入GeoTIFF文件
output_file.GetRasterBand(1).WriteArray(partition_result)

复制原始影像数据的元数据信息
output_file.SetMetadata(dataset.GetMetadata())

保存GeoTIFF文件
output_file.FlushCache()

该回答通过自己思路及引用到GPTᴼᴾᴱᴺᴬᴵ搜索,得到内容具体如下:
根据你提供的代码,以下是一些可能需要更改的建议:

  1. 数据矩阵的形状问题:
    在聚类之前,你将栅格数据转换为一维数组 data_1d,然后进行聚类操作。在这之后,你将聚类标签 labels 转换回二维数组形式,以便与影像数据保持相同的形状。然而,在这个转换过程中,可能会丢失空间关系。为了保留空间关系,你可以尝试将聚类操作直接应用于二维的栅格数据,而不是将其展平为一维数组。
  2. Delaunay三角网的构建:
    在你的代码中,你尝试对每个聚类簇应用Delaunay三角网。然而,由于你传递的是像素点的坐标,而不是实际地理坐标,所以得到的三角网可能没有正确的空间关系。为了确保正确的空间关系,你需要将像素坐标转换为地理坐标,并使用地理坐标来构建Delaunay三角网。
  3. 结果影像的空间关系:
    在最后保存结果影像时,你需要确保保存的结果影像具有正确的空间关系。这包括设置正确的地理变换信息和投影信息。你可以参考原始影像的地理变换和投影信息来设置结果影像的相关信息。

综上所述,为了保留数据的空间关系,你可以尝试以下修改:

  1. 将栅格数据保持为二维数组形式,而不是展平为一维数组。
  2. 在构建Delaunay三角网之前,将像素坐标转换为地理坐标。
  3. 在保存结果影像时,设置正确的地理变换信息和投影信息。

这样,你应该能够保留数据的空间关系,并生成具有正确空间关系的结果影像。以下是对你提供的代码进行修改的建议:

import numpy as np
from scipy.spatial import Delaunay
from sklearn.cluster import KMeans
from osgeo import gdal

# 读取栅格数据
dataset = gdal.Open("F:\Graduate smoothly\MoreBuFen.tif")
rows = dataset.RasterYSize
cols = dataset.RasterXSize
band = dataset.GetRasterBand(1)
grid_data = band.ReadAsArray()

# 进行聚类
kmeans = KMeans(n_clusters=5, n_init='auto').fit(grid_data.reshape(-1, 1))
labels = kmeans.labels_.reshape(rows, cols)

# 构建Delaunay三角网
clusters_partitions = []
for i in range(kmeans.n_clusters):
    cluster_points = np.argwhere(labels == i)
    # 将像素坐标转换为地理坐标
    # TODO: 添加代码将像素坐标转换为地理坐标
    tri = Delaunay(cluster_points)
    edge_lengths = np.sqrt(np.sum((cluster_points[tri.simplices[:, 0]] - cluster_points[tri.simplices[:, 1]]) ** 2, axis=1))
    # 根据约束条件进行二次划分
    A = 3
    triangles = tri.simplices[edge_lengths <= np.mean(edge_lengths) + A * np.std(edge_lengths)]
    clusters_partitions.append(triangles)

# 构建空间分区结果
partition_result = np.zeros((rows, cols))
for i, partition in enumerate(clusters_partitions):
    partition_result[np.unravel_index(partition.ravel(), (rows, cols))] = i + 1

# 创建结果影像
driver = gdal.GetDriverByName('GTiff')
output_file = driver.Create('F:\Graduate smoothly\Result.tif', cols, rows, 1, gdal.GDT_Float32)
output_file.GetRasterBand(1).WriteArray(partition_result)

# 设置地理信息
output_file.SetGeoTransform(dataset.GetGeoTransform())
output_file.SetProjection(dataset.GetProjection())

# 保存结果影像
output_file.FlushCache()

请注意,上述代码中的一部分还需要你根据你的具体情况进行修改,主要是将像素坐标转换为地理坐标。你可以使用GDAL库中的方法来完成这个转换。具体的转换方式可能与你的栅格数据的投影和地理坐标系统有关。如果你的栅格数据具有地理参考信息,你可以使用GDAL中的坐标转换功能来实现像素坐标到地理坐标的转换。

请确保按照你的数据的实际情况进行修改,以保证代码的正确性。


如果以上回答对您有所帮助,点击一下采纳该答案~谢谢

引用 皆我百晓生 小程序回复内容作答:
根据你提供的代码和描述,你在聚类之后将每个簇的空间分区结果存储在clusters_partitions中,并将其赋值给了partition_result数组,然后将partition_result数组保存为一个GeoTIFF文件。但是在你的代码中,并没有将聚类结果和空间分区结果与原始影像数据相结合。

如果你想要保留数据的空间关系,你可以尝试以下的修改:

  1. 将聚类结果和空间分区结果转换为具有与原始影像数据相同的维度和形状的数组。可以使用np.zeros_like(band)创建与原始影像数据波段相同大小的零数组。
  2. 使用cv2.merge函数将聚类结果和空间分区结果与原始影像数据结合,形成一个具有空间关系的影像。

以下是修改后的代码示例:

import cv2
import numpy as np
from scipy.spatial import Delaunay
from osgeo import gdal

dataset = gdal.Open("F:\Graduate smoothly\MoreBuFen.tif")
rows = dataset.RasterYSize
cols = dataset.RasterXSize

band = dataset.GetRasterBand(1)
grid_data = band.ReadAsArray()
data = grid_data.flatten()
data_1d = data.reshape(-1, 1)

kmeans = KMeans(n_clusters=5, n_init='auto').fit(data_1d)
labels = kmeans.labels_.reshape(rows, cols)

clusters_partitions = []
for i in range(kmeans.n_clusters):
    cluster_points = np.argwhere(labels == i)
    A = 3
    tri = Delaunay(cluster_points)
    edge_lengths = np.sqrt(np.sum((cluster_points[tri.simplices[:, 0]] - cluster_points[tri.simplices[:, 1]]) ** 2, axis=1))
    triangles = tri.simplices[edge_lengths <= np.mean(edge_lengths) + A * np.std(edge_lengths)]
    clusters_partitions.append(triangles)

output_array = np.zeros_like(grid_data)  # 创建一个与原始影像数据相同大小的数组
for i, partition in enumerate(clusters_partitions):
    output_array[np.unravel_index(partition.ravel(), (rows, cols))] = i + 1  # 将每个簇的空间分区结果赋值给output_array数组

# 将聚类结果和空间分区结果与原始影像数据结合,形成一个具有空间关系的影像
output_image = cv2.merge([output_array, grid_data, grid_data])  # 使用cv2.merge函数结合数组

# 将结果保存为tif格式影像
driver = gdal.GetDriverByName('GTiff')
output_file = driver.Create('F:\Graduate smoothly\Result.tif', cols, rows, 3, gdal.GDT_Float32)  # 创建一个具有3个波段的影像
# 逐个波段将数据写入GeoTIFF文件
output_file.GetRasterBand(1).WriteArray(output_image[:, :, 0])  # 第一个波段是聚类和空间分区结果
output_file.GetRasterBand(2).WriteArray(output_image[:, :, 1])  # 第二个和第三个波段是原始影像数据
output_file.GetRasterBand(3).WriteArray(output_image[:, :, 2])
output_file.SetGeoTransform(dataset.GetGeoTransform())
output_file.SetProjection(dataset.GetProjection())
output_file.FlushCache()

这样修改后的代码可以将聚类结果和空间分区结果与原始影像数据结合,并将结果保存为一个具有空间关系的GeoTIFF影像。每个像素点在GeoTIFF影像中将具有三个波段,其中第一个波段表示聚类和空间分区结果,第二个和第三个波段表示原始影像数据。

请注意,你需要确保cv2scipy库已经正确安装。

没有正确地设置GeoTIFF文件的地理信息,你需要重新计算空间分区结果的地理变换和投影信息,或者使用一些工具来进行栅格重采样,使得空间分区结果与原始影像数据具有相同的空间参考

在计算Delaunay三角网的边长时,只计算了每个三角形的第一条边(即tri.simplices[:, 0]和tri.simplices[:, 1]之间的边)。如果想要考虑每个三角形的所有边,可能需要计算所有三条边的长度。计算方法如下。
将下面的代码

edge_lengths = np.sqrt(
    np.sum((cluster_points[tri.simplices[:, 0]] - cluster_points[tri.simplices[:, 1]]) ** 2,
           axis=1))

替换为:

edge_lengths = np.hstack([
    np.sqrt(np.sum((cluster_points[tri.simplices[:, 0]] - cluster_points[tri.simplices[:, 1]]) ** 2, axis=1)),
    np.sqrt(np.sum((cluster_points[tri.simplices[:, 1]] - cluster_points[tri.simplices[:, 2]]) ** 2, axis=1)),
    np.sqrt(np.sum((cluster_points[tri.simplices[:, 2]] - cluster_points[tri.simplices[:, 0]]) ** 2, axis=1))
])

python 栅格数据
可以参考下


python 栅格数据 - 老白网络 Python是一种多功能的计算机编程语言,可用于处理各种数据类型。在地理信息系统(GIS)和遥感领域中,Python是一种常用的编程语言。Python可以通过许多库和模块(例如GDAL,NumPy和Matplotlib)来读取,处理和分析栅格数据。 栅格数据是由像... https://www.yzktw.com.cn/post/1228752.html

建议添加错误处理来处理可能出现的异常情况。以下是稍作修改的代码示例:


import gdal
import numpy as np
from scipy.spatial import Delaunay
from sklearn.cluster import KMeans

# 打开遥感影像数据集
dataset = gdal.Open("F:\Graduate smoothly\MoreBuFen.tif")
rows = dataset.RasterYSize
cols = dataset.RasterXSize

# 获取栅格数据
band = dataset.GetRasterBand(1)
grid_data = band.ReadAsArray()
data = grid_data.flatten().reshape(-1, 1)

# 使用KMeans进行聚类
kmeans = KMeans(n_clusters=5, n_init='auto').fit(data)
labels = kmeans.labels_.reshape(rows, cols)

clusters_partitions = []  # 存储每个簇的空间划分结果
for i in range(kmeans.n_clusters):
    cluster_points = np.argwhere(labels == i)
    A = 3
    tri = Delaunay(cluster_points)
    edge_lengths = np.sqrt(np.sum((cluster_points[tri.simplices[:, 0]] - cluster_points[tri.simplices[:, 1]]) ** 2,
                                  axis=1))
    triangles = tri.simplices[edge_lengths <= np.mean(edge_lengths) + A * np.std(edge_lengths)]
    clusters_partitions.append(triangles)

partition_result = np.zeros((rows, cols))
for i, partition in enumerate(clusters_partitions):
    partition_result[np.unravel_index(partition.ravel(), (rows, cols))] = i + 1

# 创建输出文件
driver = gdal.GetDriverByName('GTiff')
output_file = driver.Create('F:\Graduate smoothly\Result.tif', cols, rows, 1, gdal.GDT_Float32)
if output_file is None:
    raise RuntimeError("创建输出文件失败!")

# 写入数据
output_band = output_file.GetRasterBand(1)
output_band.WriteArray(partition_result)

# 设置地理信息
output_file.SetGeoTransform(dataset.GetGeoTransform())
output_file.SetProjection(dataset.GetProjection())

# 保存文件
output_band.FlushCache()
output_file.FlushCache()

# 关闭数据集
dataset = None
output_file = None

这个代码应该可以帮助您将遥感影像进行KMeans聚类、Delaunay三角网划分,并将结果保存为Tiff格式的影像

可能是因为你在处理数据时没有正确地设置GeoTIFF的空间信息。你创建了一个新的GeoTIFF文件并将聚类结果写入这个新的文件,但是你没有将原始影像的地理坐标信息(GeoTransform和Projection)应用到新的GeoTIFF文件上。你需要将原始影像的GeoTransform和Projection信息应用到新的GeoTIFF文件上,这样新的GeoTIFF文件就能保持正确的空间关系了。

参考gpt
根据您提供的代码和图像,您的聚类和空间分区结果似乎正确生成了。然而,您的图像显示的确实是行列号,而不是地理坐标。为了将结果保存为具有空间关系的图像,您需要将图像的地理坐标信息添加到输出文件中。

您可以使用以下代码来设置输出文件的地理坐标信息:

# 获取原始影像的地理坐标信息
geotransform = dataset.GetGeoTransform()
projection = dataset.GetProjection()

# 创建一个与原始影像数据相同大小的GeoTIFF文件
driver = gdal.GetDriverByName('GTiff')
output_file = driver.Create('F:\Graduate smoothly\Result.tif', cols, rows, 1, gdal.GDT_Float32)

# 将partition_result数组写入GeoTIFF文件
output_file.GetRasterBand(1).WriteArray(partition_result)

# 设置输出文件的地理坐标信息
output_file.SetGeoTransform(geotransform)
output_file.SetProjection(projection)

# 保存GeoTIFF文件
output_file.FlushCache()

通过使用原始影像的地理坐标信息,您可以确保输出文件具有正确的空间关系。保存后的图像将具有与原始影像相同的地理坐标系统和投影。

如果您的图像仍然没有正确的空间关系,可能是因为原始影像的地理坐标信息不正确。您可以尝试检查原始影像的元数据,或者使用其他方法来获取正确的地理坐标信息。

检查一下坐标系和变换参数是否正确

坐标系设置检查一下

用NumPy库的功能来进行栅格数据的处理和分析。例如,可以使用NumPy的数组操作来执行统计计算、重分类、过滤、计算栅格指数等操作

以下是一种可能的Python代码实现方式,若有帮助,还望采纳,点击回答右侧采纳即可。

import numpy as np
import cv2
from scipy.spatial import Delaunay

# 读取影像
img = cv2.imread('image.tif')
# 提取影像的RGB三个通道并将其展平
data = img.reshape((-1, 3)).astype(np.float32)

# 进行kmeans聚类,聚类成8类
criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, 10, 1.0)
_, labels, centers = cv2.kmeans(data, 8, None, criteria, 10, cv2.KMEANS_RANDOM_CENTERS)

# 对聚类结果进行Delaunay三角网分割
points = data / 255.0
tri = Delaunay(points)

# 定义约束条件,约束条件的格式为三元组(a, b, c),表示只对三个点组成的三角形进行划分
constraints = [(0, 1, 2), (1, 2, 3), (2, 3, 4)]

# 进行二次划分
for cons in constraints:
    for i, j in zip(cons[:-1], cons[1:]):
        p1 = points[tri.simplices[:, i]]
        p2 = points[tri.simplices[:, j]]
        mask = np.all(np.isin(p1, p2), axis=2)
        tri.add_points(points[mask])

# 生成结果影像
result = np.zeros(img.shape[:2], dtype=np.uint8)
for simplex in tri.simplices:
    # 仅使用三个顶点的颜色来表示三角形
    color = centers[labels[simplex]].mean(axis=0).astype(np.uint8)
    # 在结果影像上绘制三角形
    cv2.drawContours(result, [points[simplex].astype(np.int32)], 0, color, -1)

# 保存结果影像
cv2.imwrite('result.tif', result)

需要注意的是,以上代码仅提供了一种实现方式,具体实现可能还需要根据具体情况进行一些调整和优化。同时,Delaunay三角网分割的结果可能会因为约束条件的不同而出现较大差异,需要根据具体应用场景进行适当调整。

【以下回答由 GPT 生成】

代码中的问题是:路径名中的字符需要使用双反斜杠或者在字符串前面加上 "r" 来转义。同时,需要检查遥感影像数据集的路径是否正确。此外,可能缺少必要的导入语句,请确认是否已经安装了相应的库,并添加必要的导入语句。

以下是已修改的代码:

import numpy as np
from osgeo import gdal
from osgeo.gdalconst import GDT_Float32
from sklearn.cluster import KMeans
from scipy.spatial import Delaunay

# 打开遥感影像数据集
dataset = gdal.Open(r"F:\\Graduate smoothly\\MoreBuFen.tif")

# 获取影像数据集的行数和列数
rows = dataset.RasterYSize
cols = dataset.RasterXSize

# 读取影像数据集的第一个波段数据
band = dataset.GetRasterBand(1)
grid_data = band.ReadAsArray()

# 将二维数组转换为一维数组
data = grid_data.flatten()

# 将数组重新调整形状为列向量
data_1d = data.reshape(-1, 1)

# 使用kmeans算法进行聚类
kmeans = KMeans(n_clusters=5, n_init='auto').fit(data_1d)
labels = kmeans.labels_.reshape(rows, cols)

# 存储每个簇的空间分区结果
clusters_partitions = []

# 对每个簇进行处理
for i in range(kmeans.n_clusters):
    cluster_points = np.argwhere(labels == i)
    A = 3
    tri = Delaunay(cluster_points)
    edge_lengths = np.sqrt(
        np.sum((cluster_points[tri.simplices[:, 0]] - cluster_points[tri.simplices[:, 1]]) ** 2, axis=1))
    triangles = tri.simplices[edge_lengths <= np.mean(edge_lengths) + A * np.std(edge_lengths)]
    clusters_partitions.append(triangles)

# 创建一个与原始影像数据相同大小的数组,用于存储空间分区结果
partition_result = np.zeros((rows, cols))

# 将每个簇的空间分区结果赋值给partition_result数组
for i, partition in enumerate(clusters_partitions):
    partition_result[np.unravel_index(partition.ravel(), (rows, cols))] = i + 1

# 创建一个与原始影像数据相同大小的GeoTIFF文件
driver = gdal.GetDriverByName('GTiff')
output_file = driver.Create(r"F:\\Graduate smoothly\\Result.tif", cols, rows, 1, GDT_Float32)

# 将partition_result数组写入GeoTIFF文件
output_file.GetRasterBand(1).WriteArray(partition_result)

# 设置GeoTIFF文件的地理信息
output_file.SetGeoTransform(dataset.GetGeoTransform())
output_file.SetProjection(dataset.GetProjection())

# 保存GeoTIFF文件
output_file.FlushCache()
output_file = None

请确认路径的正确性,并根据实际情况进行修改。



【相关推荐】



如果你已经解决了该问题, 非常希望你能够分享一下解决方案, 写成博客, 将相关链接放在评论区, 以帮助更多的人 ^-^

结合GPT给出回答如下请题主参考
首先,需要用GDAL库打开遥感影像,在Python中使用下面的代码:

from osgeo import gdal

# 打开遥感影像
dataset = gdal.Open("F:\Gra")

# 获取影像的行列数和波段数
rows = dataset.RasterYSize
cols = dataset.RasterXSize
bands = dataset.RasterCount

# 获取影像的地理参考和投影信息
geotransform = dataset.GetGeoTransform()
projection = dataset.GetProjection()

接下来,可以使用scikit-learn库中的KMeans算法对影像进行聚类,代码如下:

from sklearn.cluster import KMeans
import numpy as np

# 读取影像数据
data = np.zeros((rows*cols, bands))
for i in range(bands):
    band = dataset.GetRasterBand(i+1)
    data[:, i] = band.ReadAsArray().ravel()

# 进行KMeans聚类
kmeans = KMeans(n_clusters=5).fit(data)
labels = kmeans.labels_.reshape(rows, cols)

然后,可以使用scipy库中的Delaunay函数生成Delaunay三角网,并根据约束条件进行二次划分,代码如下:

from scipy.spatial import Delaunay

# 生成Delaunay三角网
points = np.column_stack(np.where(labels==0))
tri = Delaunay(points)

# 根据约束条件进行二次划分
# ...

# 将结果保存为tif格式影像
driver = gdal.GetDriverByName("GTiff")
outdataset = driver.Create("result.tif", cols, rows, 1, gdal.GDT_Float32)
outdataset.SetGeoTransform(geotransform)
outdataset.SetProjection(projection)
outband = outdataset.GetRasterBand(1)
outband.WriteArray(result)

在创建输出GeoTIFF文件时,您需要设置正确的地理信息。在您的代码中,已经有了一些相关的设置:


output_file.SetGeoTransform(dataset.GetGeoTransform())
output_file.SetProjection(dataset.GetProjection())

这些行用于将输出GeoTIFF文件的地理信息设置为与输入文件相同。