第02章 - 快速入门与环境配置
第02章 - 快速入门与环境配置
2.1 环境要求
2.1.1 .NET版本
OGU4Net基于 .NET Standard 2.0 构建,兼容以下目标框架:
| 目标框架 | 最低版本 | 推荐版本 |
|---|---|---|
| .NET | 5.0 | 8.0+ |
| .NET Core | 2.0 | 3.1+ |
| .NET Framework | 4.6.1 | 4.8 |
检查.NET SDK版本:
dotnet --version
期望输出:
8.0.x
2.1.2 操作系统支持
OGU4Net通过 MaxRev.Gdal.Universal 实现跨平台支持:
| 操作系统 | 支持状态 | 说明 |
|---|---|---|
| Windows x64 | ✅ 完全支持 | 推荐Windows 10/11 |
| Linux x64 | ✅ 完全支持 | Ubuntu 18.04+, CentOS 7+ |
| macOS x64 | ✅ 完全支持 | macOS 10.15+ |
| macOS ARM64 | ✅ 完全支持 | Apple Silicon (M1/M2/M3) |
2.1.3 开发工具
推荐使用以下开发工具:
- Visual Studio 2022(Windows推荐)
- Visual Studio Code + C# 扩展(跨平台推荐)
- JetBrains Rider(跨平台IDE)
- .NET CLI(命令行开发)
2.2 NuGet包安装
2.2.1 使用.NET CLI安装
# 创建新项目
dotnet new console -n MyGisApp
cd MyGisApp
# 安装OGU4Net
dotnet add package OpenGIS.Utils
# 恢复依赖
dotnet restore
2.2.2 使用Package Manager Console安装
在Visual Studio的包管理器控制台中执行:
Install-Package OpenGIS.Utils
2.2.3 编辑.csproj文件安装
直接编辑项目文件添加包引用:
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net8.0</TargetFramework>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="OpenGIS.Utils" Version="1.0.0" />
</ItemGroup>
</Project>
2.2.4 依赖项说明
安装 OpenGIS.Utils 后,以下依赖将自动安装:
| 依赖包 | 版本 | 用途 |
|---|---|---|
| MaxRev.Gdal.Core | 3.12.0 | GDAL核心绑定 |
| MaxRev.Gdal.Universal | 3.12.0 | 跨平台GDAL运行时 |
| System.Text.Json | 10.0.0 | JSON处理 |
| System.Text.Encoding.CodePages | 10.0.0 | 编码支持 |
| SharpZipLib | 1.4.2 | ZIP压缩 |
| Microsoft.Extensions.Logging.Abstractions | 10.0.0 | 日志 |
2.3 IDE配置
2.3.1 Visual Studio 2022配置
创建新项目:
- 文件 → 新建 → 项目
- 选择"控制台应用"模板
- 项目名称:
OguNetDemo - 框架选择:
.NET 8.0
安装NuGet包:
- 右键项目 → 管理NuGet程序包
- 搜索
OpenGIS.Utils - 点击安装
配置生成选项:
- 右键项目 → 属性
- 生成 → 平台目标:x64
- 生成 → 允许不安全代码:是(可选)
2.3.2 Visual Studio Code配置
安装扩展:
- 安装 C# Dev Kit 扩展
- 安装 .NET Install Tool 扩展
创建项目:
# 创建项目目录
mkdir OguNetDemo && cd OguNetDemo
# 初始化项目
dotnet new console
# 安装OGU4Net
dotnet add package OpenGIS.Utils
# 打开VS Code
code .
配置launch.json:
{
"version": "0.2.0",
"configurations": [
{
"name": ".NET Core Launch (console)",
"type": "coreclr",
"request": "launch",
"preLaunchTask": "build",
"program": "${workspaceFolder}/bin/Debug/net8.0/OguNetDemo.dll",
"args": [],
"cwd": "${workspaceFolder}",
"console": "internalConsole",
"stopAtEntry": false
}
]
}
2.3.3 JetBrains Rider配置
- 文件 → 新建解决方案
- 选择 .NET / .NET Core → Console Application
- 框架选择:net8.0
- 右键项目 → 管理NuGet包
- 搜索并安装 OpenGIS.Utils
2.4 第一个程序
2.4.1 Hello OGU4Net
创建一个简单的程序来验证环境配置:
using OpenGIS.Utils.Configuration;
using OpenGIS.Utils.Geometry;
// 验证GDAL配置
Console.WriteLine("OpenGIS Utils for .NET Demo");
Console.WriteLine("===========================");
// 获取GDAL版本
var gdalVersion = GdalConfiguration.GetGdalVersion();
Console.WriteLine($"GDAL Version: {gdalVersion}");
// 获取支持的驱动
var drivers = GdalConfiguration.GetSupportedDrivers();
Console.WriteLine($"Supported Drivers: {drivers.Count}");
// 列出部分驱动
Console.WriteLine("\nSome supported drivers:");
foreach (var driver in drivers.Take(10))
{
Console.WriteLine($" - {driver}");
}
// 测试几何操作
Console.WriteLine("\nGeometry Test:");
var wkt = "POINT (116.404 39.915)";
Console.WriteLine($" WKT: {wkt}");
var geojson = GeometryUtil.Wkt2Geojson(wkt);
Console.WriteLine($" GeoJSON: {geojson}");
Console.WriteLine("\nEnvironment configured successfully!");
运行程序:
dotnet run
期望输出:
OpenGIS Utils for .NET Demo
===========================
GDAL Version: 3.12.0
Supported Drivers: 85
Some supported drivers:
- ESRI Shapefile
- MapInfo File
- UK .NTF
- LVBAG
- OGR_SDTS
- S57
- DGN
- OGR_VRT
- Memory
- CSV
Geometry Test:
WKT: POINT (116.404 39.915)
GeoJSON: { "type": "Point", "coordinates": [ 116.404, 39.915 ] }
Environment configured successfully!
2.4.2 创建简单图层
using OpenGIS.Utils.Engine.Enums;
using OpenGIS.Utils.Engine.Model.Layer;
Console.WriteLine("Creating a simple layer...");
// 创建图层
var layer = new OguLayer
{
Name = "Cities",
GeometryType = GeometryType.POINT,
Wkid = 4326 // WGS84
};
// 添加字段
layer.AddField(new OguField
{
Name = "ID",
DataType = FieldDataType.INTEGER
});
layer.AddField(new OguField
{
Name = "Name",
DataType = FieldDataType.STRING,
Length = 50
});
layer.AddField(new OguField
{
Name = "Population",
DataType = FieldDataType.LONG
});
// 添加要素
var beijing = new OguFeature
{
Fid = 1,
Wkt = "POINT (116.404 39.915)"
};
beijing.SetValue("ID", 1);
beijing.SetValue("Name", "北京");
beijing.SetValue("Population", 21540000L);
layer.AddFeature(beijing);
var shanghai = new OguFeature
{
Fid = 2,
Wkt = "POINT (121.473 31.230)"
};
shanghai.SetValue("ID", 2);
shanghai.SetValue("Name", "上海");
shanghai.SetValue("Population", 24870000L);
layer.AddFeature(shanghai);
// 验证图层
layer.Validate();
// 输出信息
Console.WriteLine($"Layer: {layer.Name}");
Console.WriteLine($"Geometry Type: {layer.GeometryType}");
Console.WriteLine($"Fields: {layer.Fields.Count}");
Console.WriteLine($"Features: {layer.GetFeatureCount()}");
Console.WriteLine("\nFeatures:");
foreach (var feature in layer.Features)
{
var name = feature.GetValue("Name");
var pop = feature.GetAttribute("Population")?.GetLongValue();
Console.WriteLine($" - {name}: Population {pop:N0}");
}
// 转换为JSON
Console.WriteLine("\nLayer JSON:");
Console.WriteLine(layer.ToJson());
2.4.3 读写Shapefile
准备测试数据后,测试数据读写:
using OpenGIS.Utils.DataSource;
using OpenGIS.Utils.Engine.Enums;
// 假设已有测试Shapefile
var inputPath = "data/test.shp";
var outputPath = "output/result.geojson";
// 确保输出目录存在
Directory.CreateDirectory("output");
// 读取Shapefile
Console.WriteLine($"Reading: {inputPath}");
var layer = OguLayerUtil.ReadLayer(DataFormatType.SHP, inputPath);
Console.WriteLine($"Layer Name: {layer.Name}");
Console.WriteLine($"Feature Count: {layer.GetFeatureCount()}");
Console.WriteLine($"Fields: {string.Join(", ", layer.Fields.Select(f => f.Name))}");
// 写入GeoJSON
Console.WriteLine($"\nWriting: {outputPath}");
OguLayerUtil.WriteLayer(DataFormatType.GEOJSON, layer, outputPath);
Console.WriteLine("Conversion completed!");
2.5 项目模板
2.5.1 控制台应用模板
// Program.cs
using OpenGIS.Utils.Configuration;
using OpenGIS.Utils.DataSource;
using OpenGIS.Utils.Engine.Enums;
using OpenGIS.Utils.Geometry;
namespace OguNetApp;
class Program
{
static void Main(string[] args)
{
try
{
// 确保GDAL已初始化
GdalConfiguration.ConfigureGdal();
Console.WriteLine($"GDAL Version: {GdalConfiguration.GetGdalVersion()}");
// 你的业务逻辑
ProcessGisData();
}
catch (Exception ex)
{
Console.Error.WriteLine($"Error: {ex.Message}");
Environment.Exit(1);
}
}
static void ProcessGisData()
{
// 实现你的GIS数据处理逻辑
}
}
2.5.2 ASP.NET Core Web API模板
// Program.cs
using OpenGIS.Utils.Configuration;
var builder = WebApplication.CreateBuilder(args);
// 初始化GDAL
GdalConfiguration.ConfigureGdal();
builder.Services.AddControllers();
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();
var app = builder.Build();
if (app.Environment.IsDevelopment())
{
app.UseSwagger();
app.UseSwaggerUI();
}
app.MapControllers();
app.Run();
// Controllers/GeoController.cs
using Microsoft.AspNetCore.Mvc;
using OpenGIS.Utils.Geometry;
using OpenGIS.Utils.Engine.Util;
namespace OguNetApi.Controllers;
[ApiController]
[Route("api/[controller]")]
public class GeoController : ControllerBase
{
[HttpPost("wkt2geojson")]
public IActionResult Wkt2Geojson([FromBody] string wkt)
{
try
{
var geojson = GeometryUtil.Wkt2Geojson(wkt);
return Ok(new { geojson });
}
catch (Exception ex)
{
return BadRequest(new { error = ex.Message });
}
}
[HttpPost("buffer")]
public IActionResult Buffer([FromBody] BufferRequest request)
{
try
{
var buffered = GeometryUtil.BufferWkt(request.Wkt, request.Distance);
return Ok(new { wkt = buffered });
}
catch (Exception ex)
{
return BadRequest(new { error = ex.Message });
}
}
[HttpPost("transform")]
public IActionResult Transform([FromBody] TransformRequest request)
{
try
{
var result = CrsUtil.Transform(request.Wkt, request.SourceWkid, request.TargetWkid);
return Ok(new { wkt = result });
}
catch (Exception ex)
{
return BadRequest(new { error = ex.Message });
}
}
}
public record BufferRequest(string Wkt, double Distance);
public record TransformRequest(string Wkt, int SourceWkid, int TargetWkid);
2.5.3 类库项目模板
<!-- MyGisLibrary.csproj -->
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
<LangVersion>latest</LangVersion>
<Nullable>enable</Nullable>
<GenerateDocumentationFile>true</GenerateDocumentationFile>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="OpenGIS.Utils" Version="1.0.0" />
</ItemGroup>
</Project>
2.6 常见问题
2.6.1 GDAL初始化失败
问题: 运行时提示找不到GDAL库或初始化失败。
解决方案:
- 确保安装了正确版本的 MaxRev.Gdal.Universal
- 检查目标平台是否为x64
- 清理并重新生成项目:
dotnet clean dotnet restore dotnet build
2.6.2 中文乱码问题
问题: 读取Shapefile时中文属性显示乱码。
解决方案:
using OpenGIS.Utils.Utils;
using System.Text;
// 注册编码提供程序(通常在程序启动时执行一次)
Encoding.RegisterProvider(CodePagesEncodingProvider.Instance);
// 检测文件编码
var encoding = EncodingUtil.GetFileEncoding("data.dbf");
Console.WriteLine($"Detected encoding: {encoding.WebName}");
// 使用ShpUtil读取(自动处理编码)
var layer = ShpUtil.ReadShapefile("data.shp");
2.6.3 Linux部署问题
问题: 在Linux上运行时提示缺少依赖库。
解决方案:
Ubuntu/Debian:
sudo apt-get update
sudo apt-get install -y libgdal-dev gdal-bin libproj-dev
CentOS/RHEL:
sudo yum install -y gdal gdal-devel proj proj-devel
2.6.4 内存占用过高
问题: 处理大数据时内存占用过高。
解决方案:
// 使用分批处理
foreach (var batch in layer.Features.Chunk(1000))
{
ProcessBatch(batch);
GC.Collect(); // 适当时机手动GC
}
// 及时释放大对象
layer = null;
GC.Collect();
2.6.5 FileGDB驱动不可用
问题: 尝试读取FileGDB时提示驱动不可用。
解决方案:
// 检查FileGDB驱动是否可用
if (GdalConfiguration.IsDriverAvailable("FileGDB"))
{
Console.WriteLine("FileGDB driver is available");
}
else if (GdalConfiguration.IsDriverAvailable("OpenFileGDB"))
{
Console.WriteLine("OpenFileGDB driver is available (read-only)");
}
else
{
Console.WriteLine("No FileGDB driver available");
}
2.7 下一步
环境配置完成后,建议按以下顺序学习:
- 第03章 - 核心架构解析:深入理解OGU4Net的内部结构
- 第04章 - 统一图层模型详解:掌握OguLayer、OguFeature等核心类
- 第06章 - 数据格式转换实战:学习各种格式的读写操作
2.8 小结
本章介绍了OGU4Net的环境配置:
- 环境要求:.NET Standard 2.0兼容,支持Windows/Linux/macOS
- 包安装:通过NuGet安装OpenGIS.Utils
- IDE配置:Visual Studio、VS Code、Rider配置指南
- 第一个程序:验证环境配置,创建简单图层
- 项目模板:控制台应用、Web API、类库模板
- 常见问题:解决GDAL初始化、中文编码等问题
配置好开发环境后,就可以开始深入学习OGU4Net的核心功能了。

浙公网安备 33010602011771号