您可以通过以下方式读取感兴趣的区域:
roi = shaperead('study_area_shapefile/studyArea.shp');
截掉尾随的 NaN:
rx = roi.X(1:end-1);
ry = roi.Y(1:end-1);
如果您的 shapefile 中有多个多边形,它们会被 NaN 分隔,您必须单独处理它们。
然后使用卫星图像空间参考中的 worldToIntrinsic 方法将多边形点转换为图像坐标:
[ix, iy] = R.worldToIntrinsic(rx,ry);
这假设两个坐标系相同。
然后你可以通过以下方式制作面具:
mask = poly2mask(ix,iy,R.RasterSize(1),R.RasterSize(2));
在进行任何计算之前,您可以在原始多层图像上使用蒙版:
I(repmat(~mask,[1,1,4])) = nan;
或者通过以下方式在单层(即红色)上使用它:
red(~mask) = nan;
如果区域非常小,则将蒙版图像转换为稀疏矩阵可能会有益(对于内存和计算能力)。我还没有尝试过这是否会产生任何速度差异。
red(~mask) = 0;
sred = sparse(double(red));
不幸的是,稀疏矩阵只能使用双精度数,因此您的 uint8 需要先进行转换。
一般来说,您应该从图像中裁剪出 ROI。查看对象“roi”和“R”以查找有用的参数和方法。我这里没做过。
最后是我的脚本版本,还有一些细微的其他更改:
file = 'doi1m2011_41111h4nw_usda.tif';
[I R] = geotiffread(file);
outputdir = '';
% Read Region of Interest
roi = shaperead('study_area_shapefile/studyArea.shp');
% Remove trailing nan from shapefile
rx = roi.X(1:end-1);
ry = roi.Y(1:end-1);
% convert to image coordinates
[ix, iy] = R.worldToIntrinsic(rx,ry);
% make the mask
mask = poly2mask(ix,iy,R.RasterSize(1),R.RasterSize(2));
% mask sat-image
I(repmat(~mask,[1,1,4])) = 0;
% convert to sparse matrizes
NIR = sparse(double(I(:,:,4)));
red = sparse(double(I(:,:,1)));
% Calculate NDVI
ndvi = (NIR - red) ./ (NIR + red);
% convert back to full matrizes
ndvi = full(ndvi);
imshow(ndvi,'DisplayRange',[-1 1]);
% Stretch to 0 - 255 and convert to 8-bit unsigned integer
ndvi = (ndvi + 1) / 2 * 255; % [-1 1] -> [0 255]
ndvi = uint8(ndvi); % change and round data type from double to uint8
% Write NDVI to .tif file (optional)
tiffdata = geotiffinfo(file);
outfilename = [outputdir 'ndvi_' 'temp' '.tif'];
geotiffwrite(outfilename, ndvi, R, 'GeoKeyDirectoryTag', tiffdata.GeoTIFFTags.GeoKeyDirectoryTag);
mapshow(outfilename);