a
This commit is contained in:
@@ -0,0 +1,358 @@
|
||||
# 2D脚本生成
|
||||
|
||||
<cite>
|
||||
**本文档引用文件**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp)
|
||||
- [Script.cpp](file://cpp/ProblemZone/Script.cpp)
|
||||
- [Script2D.cpp](file://cpp/ProblemZone/Script2D.cpp)
|
||||
- [MediumA.cpp](file://cpp/ProblemZone/MediumA.cpp)
|
||||
- [MediumW.cpp](file://cpp/ProblemZone/MediumW.cpp)
|
||||
- [MediumBasicWenAndSch.cpp](file://cpp/ProblemZone/MediumBasicWenAndSch.cpp)
|
||||
- [MediumStrongWenAndSch.cpp](file://cpp/ProblemZone/MediumStrongWenAndSch.cpp)
|
||||
- [DialNew2DTask.cpp](file://cpp/Views/DialNew2DTask.cpp)
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp)
|
||||
- [Script.h](file://h/Script.h)
|
||||
- [Script2D.h](file://h/Script2D.h)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [引言](#引言)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概述](#架构概述)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖关系分析](#依赖关系分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
|
||||
## 引言
|
||||
本文档详细阐述了Geomative Studio软件中2D测量脚本的生成机制。重点分析了`CSptManager::Create2DSConInDB`和`CScript`类在脚本创建过程中的协作,描述了从MediumA到MediumW等2D介质模型的电极排列算法和测量序列生成逻辑。文档还说明了脚本参数配置界面(如DialNew2DTask和OpCreateSptDlg)如何收集用户输入并生成XML格式的脚本结构,提供了从项目创建到脚本导出的完整流程,并分析了2D脚本与测试数据管理器的集成方式。
|
||||
|
||||
## 项目结构
|
||||
Geomative Studio项目是一个用于地球物理测量的软件系统,其核心功能围绕测量脚本的创建、管理和执行。项目结构清晰地分离了管理层、操作层和问题区域(ProblemZone)的代码。
|
||||
|
||||
```mermaid
|
||||
graph TD
|
||||
subgraph "管理层"
|
||||
SptManager["SptManager.cpp<br>脚本管理"]
|
||||
ProManager["ProManager.cpp<br>项目管理"]
|
||||
TdManager["TdManager.cpp<br>测试数据管理"]
|
||||
end
|
||||
subgraph "操作层"
|
||||
DialNew2DTask["DialNew2DTask.cpp<br>2D任务创建对话框"]
|
||||
DialCustomSptInput["DialCustomSptInput.cpp<br>自定义脚本输入"]
|
||||
end
|
||||
subgraph "问题区域"
|
||||
Script["Script.cpp<br>脚本基类"]
|
||||
Script2D["Script2D.cpp<br>2D脚本实现"]
|
||||
MediumA["MediumA.cpp<br>温纳装置模型"]
|
||||
MediumW["MediumW.cpp<br>偶极-偶极装置模型"]
|
||||
MediumBasicWenAndSch["MediumBasicWenAndSch.cpp<br>施伦贝谢基础模型"]
|
||||
MediumStrongWenAndSch["MediumStrongWenAndSch.cpp<br>施伦贝谢强模型"]
|
||||
end
|
||||
SptManager --> Script2D
|
||||
SptManager --> MediumA
|
||||
SptManager --> MediumW
|
||||
DialNew2DTask --> SptManager
|
||||
DialCustomSptInput --> SptManager
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp)
|
||||
- [DialNew2DTask.cpp](file://cpp/Views/DialNew2DTask.cpp)
|
||||
- [Script2D.cpp](file://cpp/ProblemZone/Script2D.cpp)
|
||||
- [MediumA.cpp](file://cpp/ProblemZone/MediumA.cpp)
|
||||
- [MediumW.cpp](file://cpp/ProblemZone/MediumW.cpp)
|
||||
|
||||
**本节源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp)
|
||||
- [DialNew2DTask.cpp](file://cpp/Views/DialNew2DTask.cpp)
|
||||
|
||||
## 核心组件
|
||||
2D脚本生成的核心组件包括`CSptManager`、`CScript2D`和各种`CMedium`派生类。`CSptManager`负责协调脚本的创建流程,`CScript2D`作为2D脚本的数据容器,而`CMedium`系列类则封装了不同测量装置的电极排列算法。
|
||||
|
||||
**本节源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp)
|
||||
- [Script2D.cpp](file://cpp/ProblemZone/Script2D.cpp)
|
||||
- [MediumA.cpp](file://cpp/ProblemZone/MediumA.cpp)
|
||||
|
||||
## 架构概述
|
||||
2D脚本生成的架构遵循典型的MVC(模型-视图-控制器)模式。用户通过视图(如`DialNew2DTask`)输入参数,控制器(`CSptManager`)接收请求并协调模型(`CScript2D`和`CMedium`)进行处理,最终将结果持久化到数据库。
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant User as "用户"
|
||||
participant View as "DialNew2DTask"
|
||||
participant Controller as "CSptManager"
|
||||
participant Model as "CScript2D / CMedium"
|
||||
participant DB as "数据库"
|
||||
User->>View : 输入参数电极数、测量类型等
|
||||
View->>Controller : 调用Create2DSConInDB
|
||||
Controller->>Model : 创建CScript2D实例
|
||||
Controller->>Model : 调用介质模型的GenerateSptRecElecVal
|
||||
Model-->>Controller : 返回生成的测量序列
|
||||
Controller->>DB : 将脚本数据写入scon、channel、script2d表
|
||||
DB-->>Controller : 确认写入成功
|
||||
Controller-->>View : 返回成功状态
|
||||
View-->>User : 显示创建成功消息
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L257-L486)
|
||||
- [DialNew2DTask.cpp](file://cpp/Views/DialNew2DTask.cpp#L414-L664)
|
||||
- [Script2D.cpp](file://cpp/ProblemZone/Script2D.cpp)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### CSptManager与CScript的协作机制
|
||||
`CSptManager::Create2DSConInDB`是创建2D脚本的核心方法。它首先创建一个`COpCreateSptDlg`对话框来收集用户输入,然后根据输入创建一个`CScript2D`对象。该方法与`CScript`类的协作体现在`CScript2D`作为`CScript`的派生类,继承了基本的脚本属性和方法。
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class CScript {
|
||||
+DWORD m_dwID
|
||||
+int m_iEAmount
|
||||
+int m_iSType
|
||||
+int m_iAR
|
||||
+_ConnectionPtr m_pConnection
|
||||
+CScript(DWORD dwID, _ConnectionPtr& pConnection)
|
||||
+virtual ~CScript()
|
||||
}
|
||||
class CScript2D {
|
||||
+CPtrList m_chaList
|
||||
+bool ShowSptConInfo(CListCtrl& sptConList)
|
||||
+bool ShowSptDetailInfo(CListCtrl& sptDetailList)
|
||||
+bool ShowChannelList(CListCtrl& sptChannelList)
|
||||
+void AdjustRecListColumn(int iAR, CListCtrl& sptConListInfo)
|
||||
+CScript2D(DWORD dwID, _ConnectionPtr& pConnection)
|
||||
+virtual ~CScript2D()
|
||||
}
|
||||
class CSptManager {
|
||||
+UINT Create2DSConInDB(DWORD& dwSConID)
|
||||
+void Delete2DSConInDB(DWORD dwSConID)
|
||||
+CScript* GetScript(DWORD dwHandle)
|
||||
+void DeleteObjInMem(DWORD dwHandle)
|
||||
}
|
||||
CScript2D --|> CScript : 继承
|
||||
CSptManager --> CScript2D : 创建实例
|
||||
CSptManager --> COpCreateSptDlg : 显示对话框
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L257-L486)
|
||||
- [Script.cpp](file://cpp/ProblemZone/Script.cpp)
|
||||
- [Script2D.cpp](file://cpp/ProblemZone/Script2D.cpp)
|
||||
- [Script.h](file://h/Script.h)
|
||||
- [Script2D.h](file://h/Script2D.h)
|
||||
|
||||
**本节源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L257-L486)
|
||||
- [Script.cpp](file://cpp/ProblemZone/Script.cpp)
|
||||
- [Script2D.cpp](file://cpp/ProblemZone/Script2D.cpp)
|
||||
|
||||
### 2D介质模型的电极排列算法
|
||||
不同的2D介质模型(如MediumA、MediumW)实现了各自的`GenerateSptRecElecVal`方法来生成特定的测量序列。
|
||||
|
||||
#### MediumA(温纳装置)算法
|
||||
`CMediumA`类实现了温纳装置的电极排列算法。其核心逻辑是根据电极总数计算最大层数,并生成相应的测量序列。
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([开始]) --> CheckInput["验证输入参数"]
|
||||
CheckInput --> CalcMaxSpace["计算最大间距 iMaxSpace = (iEAmount-1)/3"]
|
||||
CalcMaxSpace --> LoopLayer["循环每一层 iMMVal"]
|
||||
LoopLayer --> CalcPositions["计算A, B, M, N电极位置"]
|
||||
CalcPositions --> CreateRecord["创建CSptRecord并设置参数"]
|
||||
CreateRecord --> AddToArray["将记录添加到pSptRecArray"]
|
||||
AddToArray --> CalcK["计算K值: fK = 2*π*(iN-iM)"]
|
||||
CalcK --> CalcLevel["计算层数: iN-iM"]
|
||||
CalcLevel --> InnerLoop["内部循环: 电极向右平移"]
|
||||
InnerLoop --> UpdatePositions["更新A, B, M, N位置"]
|
||||
UpdatePositions --> CreateInnerRecord["创建新的CSptRecord"]
|
||||
CreateInnerRecord --> AddInnerRecord["添加到pSptRecArray"]
|
||||
AddInnerRecord --> CheckEnd["检查是否到达电极末端"]
|
||||
CheckEnd --> |否| UpdatePositions
|
||||
CheckEnd --> |是| NextLayer["进入下一层"]
|
||||
NextLayer --> LoopLayer
|
||||
LoopLayer --> |完成| SetOutput["设置输出参数 *pMaxLevel 和 *pPtAmount"]
|
||||
SetOutput --> End([结束])
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [MediumA.cpp](file://cpp/ProblemZone/MediumA.cpp#L30-L167)
|
||||
|
||||
**本节源**
|
||||
- [MediumA.cpp](file://cpp/ProblemZone/MediumA.cpp#L30-L167)
|
||||
|
||||
#### MediumW(偶极-偶极装置)算法
|
||||
`CMediumW`类使用了一个外部的脚本生成库(scr_)来处理复杂的偶极-偶极装置的测量序列生成。
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([开始]) --> Init["初始化scr对象"]
|
||||
Init --> SetRect["设置测量区域矩形"]
|
||||
SetRect --> SetPoleStart["设置起始电极号"]
|
||||
SetPoleStart --> SetZone["设置测量区域"]
|
||||
SetZone --> Generate["调用scr_generate生成序列"]
|
||||
Generate --> GetPoints["获取生成的测量点列表"]
|
||||
GetPoints --> LoopPoints["循环每个测量点"]
|
||||
LoopPoints --> CreateRecord["创建CSptRecord并填充A,B,M,N,K值"]
|
||||
CreateRecord --> AddToArray["添加到pSptRecArray"]
|
||||
AddToArray --> NextPoint["下一个点"]
|
||||
NextPoint --> LoopPoints
|
||||
LoopPoints --> |完成| Return["返回成功"]
|
||||
Return --> End([结束])
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [MediumW.cpp](file://cpp/ProblemZone/MediumW.cpp#L27-L62)
|
||||
|
||||
**本节源**
|
||||
- [MediumW.cpp](file://cpp/ProblemZone/MediumW.cpp#L27-L62)
|
||||
|
||||
#### MediumBasicWenAndSch(施伦贝谢基础模型)算法
|
||||
该模型实现了施伦贝谢装置的测量序列,其特点是AM间距和MN间距按特定规则递增。
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([开始]) --> LoopLayer["循环每一层 iLayer"]
|
||||
LoopLayer --> CalcTailor["计算调整层数 iTailorLayer = (iLayer-1)/5"]
|
||||
CalcTailor --> CalcAM["计算AM间距: iLayer - iTailorLayer"]
|
||||
CalcAM --> CalcMN["计算MN间距: 1 + iTailorLayer*2"]
|
||||
CalcMN --> SetInitialPos["设置初始电极位置"]
|
||||
SetInitialPos --> CheckEnd["检查B电极是否超出范围"]
|
||||
CheckEnd --> |是| Break["跳出循环"]
|
||||
CheckEnd --> |否| LoopMeasure["循环测量"]
|
||||
LoopMeasure --> CreateRecord["创建CSptRecord"]
|
||||
CreateRecord --> CalcK["计算K值"]
|
||||
CalcK --> AddToArray["添加到pSptRecArray"]
|
||||
AddToArray --> MoveRight["电极向右平移1"]
|
||||
MoveRight --> CheckEnd
|
||||
LoopLayer --> |完成| SetOutput["设置输出参数"]
|
||||
SetOutput --> End([结束])
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [MediumBasicWenAndSch.cpp](file://cpp/ProblemZone/MediumBasicWenAndSch.cpp#L43-L118)
|
||||
|
||||
**本节源**
|
||||
- [MediumBasicWenAndSch.cpp](file://cpp/ProblemZone/MediumBasicWenAndSch.cpp#L43-L118)
|
||||
|
||||
### 脚本参数配置界面
|
||||
`DialNew2DTask`对话框是用户创建2D测量任务的主要界面,它收集了任务名称、测试地点、测量类型、电极间距等关键参数。
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A[任务名称] --> B[测试地点]
|
||||
B --> C[测量类型]
|
||||
C --> D[装置类型]
|
||||
D --> E[脚本选择]
|
||||
E --> F[电缆布线方式]
|
||||
F --> G[发射周期]
|
||||
G --> H[电极间距]
|
||||
H --> I[采样间隔]
|
||||
I --> J[起始/结束电极]
|
||||
J --> K[验证输入]
|
||||
K --> L[创建任务]
|
||||
```
|
||||
|
||||
**本节源**
|
||||
- [DialNew2DTask.cpp](file://cpp/Views/DialNew2DTask.cpp)
|
||||
|
||||
### 自定义脚本输入
|
||||
`DialCustomSptInput`对话框允许用户手动输入或从Excel导入自定义的测量序列。
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A[手动输入] --> B[验证A,B,M,N,K值]
|
||||
B --> C[计算K值(可选)]
|
||||
C --> D[添加到列表]
|
||||
D --> E[修改/删除列表项]
|
||||
E --> F[从Excel导入]
|
||||
F --> G[选择追加或替换]
|
||||
G --> H[解析Excel数据]
|
||||
H --> I[添加到列表]
|
||||
I --> J[完成]
|
||||
```
|
||||
|
||||
**本节源**
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp)
|
||||
|
||||
## 依赖关系分析
|
||||
2D脚本生成模块依赖于数据库连接、对话框界面和各种介质模型。
|
||||
|
||||
```mermaid
|
||||
graph TD
|
||||
SptManager --> Script2D
|
||||
SptManager --> MediumA
|
||||
SptManager --> MediumB
|
||||
SptManager --> MediumC
|
||||
SptManager --> MediumD
|
||||
SptManager --> MediumE
|
||||
SptManager --> MediumK
|
||||
SptManager --> MediumQ
|
||||
SptManager --> MediumR
|
||||
SptManager --> MediumS
|
||||
SptManager --> MediumT
|
||||
SptManager --> MediumU
|
||||
SptManager --> MediumV
|
||||
SptManager --> MediumW
|
||||
SptManager --> MediumX
|
||||
SptManager --> MediumY
|
||||
SptManager --> MediumZ
|
||||
SptManager --> MediumZA
|
||||
SptManager --> MediumZB
|
||||
SptManager --> MediumZC
|
||||
SptManager --> MediumLogging
|
||||
SptManager --> MediumStrongWenAndSch
|
||||
SptManager --> MediumBasicWenAndSch
|
||||
SptManager --> MediumAM
|
||||
SptManager --> MediumAMN
|
||||
SptManager --> MediumCustom2D
|
||||
SptManager --> MediumUnityProfile
|
||||
SptManager --> MediumEdgeGradient
|
||||
SptManager --> MeidumBipoleUpHole
|
||||
SptManager --> MediumTwoSideAMN
|
||||
SptManager --> MediumMidGardientScan
|
||||
SptManager --> MediumStrongGradient
|
||||
SptManager --> MediumCrossHoleGeomative
|
||||
SptManager --> MediumCrossHoleGeomativeAM
|
||||
SptManager --> MediumLandfillAdjacent
|
||||
SptManager --> MediumLandfillDiagonally
|
||||
SptManager --> MediumS3P
|
||||
SptManager --> opcreatesptdlg.h
|
||||
SptManager --> opcreatecesptdlg.h
|
||||
SptManager --> OpCreate3DSptDlg.h
|
||||
SptManager --> GD10OperCmd.h
|
||||
SptManager --> MediumCustom2D.h
|
||||
SptManager --> DialCreateNew3DSpt.h
|
||||
DialNew2DTask --> SptManager
|
||||
DialCustomSptInput --> SptManager
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L10-L51)
|
||||
|
||||
**本节源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L10-L51)
|
||||
|
||||
## 性能考虑
|
||||
在生成大型2D测量脚本时,性能主要受电极总数和层数的影响。`CMediumA`和`CMediumBasicWenAndSch`的算法复杂度为O(n²),其中n为电极数量。对于非常大的测量区域,建议分段创建脚本。
|
||||
|
||||
## 故障排除指南
|
||||
常见问题及解决方案:
|
||||
|
||||
1. **电极冲突检测**:在`CMediumA::GenerateSptRecElecVal`中,通过检查`iAM`, `iAN`, `iBM`, `iBN`是否为零来避免电极位置重叠。
|
||||
2. **测量序列优化**:`CMediumBasicWenAndSch::ReSortPoint`方法实现了优化的跑极顺序,以减少电极移动距离。
|
||||
3. **K值计算错误**:在`CalculateK`方法中,当分母为零时会弹出错误提示,防止生成无效的K值。
|
||||
4. **脚本名称重复**:在`CSptManager::Create2DSConInDB`中,通过查询数据库检查是否存在同名脚本,避免重复创建。
|
||||
|
||||
**本节源**
|
||||
- [MediumA.cpp](file://cpp/ProblemZone/MediumA.cpp#L531-L538)
|
||||
- [MediumBasicWenAndSch.cpp](file://cpp/ProblemZone/MediumBasicWenAndSch.cpp#L309-L384)
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp#L505-L517)
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L334-L351)
|
||||
|
||||
## 结论
|
||||
Geomative Studio的2D脚本生成系统是一个功能强大且灵活的框架。通过`CSptManager`统一管理,结合多种`CMedium`模型实现不同的测量装置,为用户提供了一个从参数配置到脚本生成的完整解决方案。该系统设计良好,易于扩展,能够满足各种复杂的地球物理测量需求。
|
||||
@@ -0,0 +1,225 @@
|
||||
# 3D脚本生成
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp)
|
||||
- [Script3D.cpp](file://cpp/ProblemZone/Script3D.cpp)
|
||||
- [Medium3D.cpp](file://cpp/ProblemZone/Medium3D.cpp)
|
||||
- [OpCreate3DSptDlg.cpp](file://cpp/Views/OpCreate3DSptDlg.cpp)
|
||||
- [MediumCrossHoleGeomative.cpp](file://cpp/ProblemZone/MediumCrossHoleGeomative.cpp)
|
||||
- [Script3D.h](file://h/Script3D.h)
|
||||
- [Medium3D.h](file://h/Medium3D.h)
|
||||
- [OpCreate3DSptDlg.h](file://h/OpCreate3DSptDlg.h)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [引言](#引言)
|
||||
2. [CSptManager::Create3DSConInDB函数实现](#csptmanagercreate3dscondb函数实现)
|
||||
3. [CScript3D类的三维电极网络管理](#cscript3d类的三维电极网络管理)
|
||||
4. [Medium3D及其衍生类的空间坐标计算](#medium3d及其衍生类的空间坐标计算)
|
||||
5. [3D脚本参数配置界面交互逻辑](#3d脚本参数配置界面交互逻辑)
|
||||
6. [XML脚本结构示例](#xml脚本结构示例)
|
||||
7. [复杂地质条件下的应用案例](#复杂地质条件下的应用案例)
|
||||
8. [与数据可视化模块的集成](#与数据可视化模块的集成)
|
||||
9. [性能优化建议与最佳实践](#性能优化建议与最佳实践)
|
||||
10. [结论](#结论)
|
||||
|
||||
## 引言
|
||||
本文档深入阐述3D测量脚本生成的技术实现,详细说明CSptManager::Create3DSConInDB函数如何创建3D脚本记录,以及CScript3D类如何管理三维空间中的电极网络和测量序列。文档还将解释Medium3D及其衍生类(如MediumCrossHoleGeomative)的空间坐标计算算法和层状地质建模方法,描述3D脚本参数配置界面(OpCreate3DSptDlg)的用户交互逻辑和数据验证机制。通过完整的XML脚本结构示例、复杂地质条件下的应用案例分析,以及与数据可视化模块的集成方式,为用户提供全面的技术指导。最后,文档将提供性能优化建议和大规模3D脚本生成的最佳实践。
|
||||
|
||||
## CSptManager::Create3DSConInDB函数实现
|
||||
|
||||
`CSptManager::Create3DSConInDB`函数是3D测量脚本生成的核心入口,负责在数据库中创建3D脚本记录。该函数通过调用`COpCreate3DSptDlg`对话框获取用户输入的脚本参数,然后在数据库中创建相应的记录。
|
||||
|
||||
函数首先创建一个`CScript3D`对象和一个`CChannel`对象,并将其添加到脚本的通道列表中。然后创建并显示`COpCreate3DSptDlg`对话框,等待用户输入脚本参数。当用户点击"确定"按钮后,函数开始处理脚本创建流程。
|
||||
|
||||
在事务处理中,函数首先生成一个全局唯一标识符(GUID)作为脚本的CN(Code Name)。然后从对话框中获取脚本名称、定义者、描述等信息,并检查是否存在同名脚本。如果存在同名脚本,则显示错误消息并回滚事务。
|
||||
|
||||
接下来,函数构建SQL插入语句,将脚本基本信息插入`scon`表。插入的字段包括:CN、Sname(脚本名称)、Stype(脚本类型,3D为2)、Eamount(电极总数)、CHamount(通道数)、TPamount(测点数)、definer(定义者)、DEdate(定义日期)、SCdesc(脚本描述)、Rect(矩形区域)、RectLoc(矩形位置)、PoleDistance(电极间距)、PoleStep(电极步长)和LineDirection(线路方向)。
|
||||
|
||||
插入脚本记录后,函数获取新插入记录的ID,并使用该ID为每个通道创建对应的`channel`记录。对于每个通道,函数遍历其测量记录数组,将选中的测量点插入`script3d`表。最后,函数更新`scon`表中的测点数量,并提交事务。
|
||||
|
||||
如果用户取消操作或发生错误,函数将回滚事务并返回相应的错误代码。
|
||||
|
||||
**Section sources**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L3000-L3193)
|
||||
|
||||
## CScript3D类的三维电极网络管理
|
||||
|
||||
`CScript3D`类继承自`CScript`基类,专门用于管理三维空间中的电极网络和测量序列。该类通过`m_chaList`成员变量维护一个通道列表,每个通道包含一组测量记录。
|
||||
|
||||
类的主要功能包括:显示通道列表、显示脚本内容信息、显示脚本详细信息以及调整记录列表列的顺序。`ShowChannelList`方法从数据库中查询指定脚本的所有通道,并在列表控件中显示。查询语句连接了`channel`和`medium`表,以获取通道编号和对应的介质名称。
|
||||
|
||||
`ShowSptConInfo`方法显示脚本的测量内容,查询语句连接了`script3d`和`channel`表,按测点序号(TSN)和通道ID排序。该方法还调用`AdjustRecListColumn`方法根据装置类型调整列表列的显示顺序。
|
||||
|
||||
`ShowSptDetailInfo`方法显示脚本的详细信息,包括CN、脚本名称、电极总数、通道数、测点数、定义者、定义日期和脚本描述。这些信息直接从`scon`表中查询。
|
||||
|
||||
`CScript3D`类还包含一个重要的成员变量`m_PointNum[128]`,用于记录每个子脚本的测点数。这个数组支持最多128个子脚本的分割,为大规模3D测量提供了支持。
|
||||
|
||||
**Section sources**
|
||||
- [Script3D.cpp](file://cpp/ProblemZone/Script3D.cpp#L1-L221)
|
||||
- [Script3D.h](file://h/Script3D.h#L1-L43)
|
||||
|
||||
## Medium3D及其衍生类的空间坐标计算
|
||||
|
||||
`CMedium3D`类是3D测量脚本生成算法的核心,负责空间坐标计算和层状地质建模。该类继承自`CMedium`基类,并实现了3D特有的算法。
|
||||
|
||||
`CalculateTdPtLoc`方法计算测点在视图中的位置。该方法首先根据视图矩形和电极数量计算每个电极的宽度和高度。然后根据电极偏移率调整电极位置,确保电极在矩形区域内均匀分布。最后,该方法为每个测量记录设置其在视图中的矩形区域。
|
||||
|
||||
`GenerateSptRecElecVal3D`方法是3D脚本生成的核心算法。该方法从`m_scr`脚本对象中获取所有测点,然后根据用户设置的脚本分割数对测点进行筛选。筛选规则是:检查测点的A、B、M、N四个电极是否属于同一个子脚本区域。如果属于同一个区域,则将该测点添加到结果数组中。
|
||||
|
||||
`CheckPointVailed`方法实现了测点有效性检查。该方法首先将电极编号转换为坐标,然后计算每个电极横坐标对脚本分割数的余数。如果所有有效电极的余数相同,则该测点有效。对于三维偶极-偶极装置,该方法还额外检查因子系数是否大于6,如果大于6则认为测点无效。
|
||||
|
||||
`CMediumCrossHoleGeomative`类是`CMedium3D`的衍生类,专门用于跨孔测量。`GenerateSptRecElecVal`方法实现了跨孔测量的测点生成算法。该算法以电极中点为基准,按照特定模式生成测点序列。C1和P1保持不动,C2和P2依次向下移动,当C2和P2到达底部时,C1和P1下移,然后C2和P2再次从顶部开始移动,直到C1和P1到达底部。
|
||||
|
||||
**Section sources**
|
||||
- [Medium3D.cpp](file://cpp/ProblemZone/Medium3D.cpp#L1-L347)
|
||||
- [Medium3D.h](file://h/Medium3D.h#L1-L80)
|
||||
- [MediumCrossHoleGeomative.cpp](file://cpp/ProblemZone/MediumCrossHoleGeomative.cpp#L1-L148)
|
||||
|
||||
## 3D脚本参数配置界面交互逻辑
|
||||
|
||||
`COpCreate3DSptDlg`类实现了3D脚本参数配置的用户界面,提供了直观的交互方式让用户设置脚本参数。
|
||||
|
||||
对话框初始化时,会设置装置类型下拉框的选项,包括:Pole-Pole(22)、Pole-Dipole(23)、Dipole-Dipole(24)、Schlumberger(25)、WennerAlfa(26)、WennerBeta(27)和Gradient(28)。通道数和通道编号被设置为不可编辑,因为3D脚本目前只支持单通道。
|
||||
|
||||
`OnOk`方法处理用户确认操作。该方法首先调用`CheckControlVaild`验证用户输入的有效性。验证包括:检查脚本名称是否为空、装置类型是否已选择、矩形区域是否有效(X0、Y0、X1、Y1不能重合)、电缆数量是否小于30、电极间距和步长是否非负。
|
||||
|
||||
对于Gradient装置,还需要额外验证C1和C2的设置:C1和C2不能重合,且不能位于矩形区域内。验证通过后,方法创建`CMedium3D`对象,设置其参数,包括矩形区域、电极步长、电极间距和测点区域。
|
||||
|
||||
`CheckControlVaild`方法实现了完整的数据验证机制。该方法使用`hHook`和`SetWindowsHookEx`设置窗口钩子,以便在验证失败时显示错误消息。验证逻辑分层次进行,首先检查必填字段,然后检查数值范围,最后检查特定装置的特殊要求。
|
||||
|
||||
`zoneCount`方法解析用户输入的测点区域字符串。该方法限制输入长度不超过15个字符,每个区域编号在0-7之间。解析结果存储在`m_zone`数组中,供后续脚本生成使用。
|
||||
|
||||
**Section sources**
|
||||
- [OpCreate3DSptDlg.cpp](file://cpp/Views/OpCreate3DSptDlg.cpp#L1-L700)
|
||||
- [OpCreate3DSptDlg.h](file://h/OpCreate3DSptDlg.h#L1-L99)
|
||||
|
||||
## XML脚本结构示例
|
||||
|
||||
3D测量脚本可以导出为XML格式,便于数据交换和存档。以下是完整的XML脚本结构示例:
|
||||
|
||||
```xml
|
||||
<?xml version="1.0" encoding="ansi" ?>
|
||||
<script>
|
||||
<cn>550e8400-e29b-41d4-a716-446655440000</cn>
|
||||
<name>3D_Script_Example</name>
|
||||
<type>24</type>
|
||||
<description>3D Dipole-Dipole Measurement Script</description>
|
||||
<definer>jimmy.lee</definer>
|
||||
<date>2023-12-01</date>
|
||||
<rect>0,0,10,10</rect>
|
||||
<pole_count>100</pole_count>
|
||||
<pole_start>1</pole_start>
|
||||
<channel_count>1</channel_count>
|
||||
<channel>
|
||||
<ar>1:1</ar>
|
||||
</channel>
|
||||
<layout>
|
||||
<array tsn="1" ch="1" c1="1" c2="2" n="1">
|
||||
<ch n="1" ks="1.0">3,4</ch>
|
||||
</array>
|
||||
<array tsn="2" ch="1" c1="2" c2="3" n="1">
|
||||
<ch n="1" ks="1.0">4,5</ch>
|
||||
</array>
|
||||
<array tsn="3" ch="1" c1="3" c2="4" n="1">
|
||||
<ch n="1" ks="1.0">5,6</ch>
|
||||
</array>
|
||||
</layout>
|
||||
</script>
|
||||
```
|
||||
|
||||
XML结构包含以下主要元素:
|
||||
- `cn`:脚本的全局唯一标识符
|
||||
- `name`:脚本名称
|
||||
- `type`:装置类型代码
|
||||
- `description`:脚本描述
|
||||
- `definer`:脚本创建者
|
||||
- `date`:创建日期
|
||||
- `rect`:测量区域矩形坐标
|
||||
- `pole_count`:电极总数
|
||||
- `pole_start`:起始电极编号
|
||||
- `channel_count`:通道数量
|
||||
- `layout`:测量序列布局,包含多个`array`元素,每个`array`代表一个测量点
|
||||
|
||||
**Section sources**
|
||||
- [OpCreate3DSptDlg.cpp](file://cpp/Views/OpCreate3DSptDlg.cpp#L529-L633)
|
||||
|
||||
## 复杂地质条件下的应用案例
|
||||
|
||||
在复杂地质条件下,3D测量脚本生成技术展现出强大的适应性和灵活性。以下是几个典型的应用案例:
|
||||
|
||||
### 跨孔电阻率成像
|
||||
在跨孔测量中,`CMediumCrossHoleGeomative`类实现了特殊的测点生成算法。该算法以电极中点为基准,按照"之"字形模式生成测点序列。这种模式能够有效覆盖两个钻孔之间的整个区域,提供高分辨率的地下电阻率分布图像。
|
||||
|
||||
在实际应用中,该算法成功应用于某矿区的矿体边界探测。通过在两个钻孔中布置电极,生成了包含2000多个测点的3D脚本。测量结果显示,该方法能够清晰地识别出矿体的边界和内部结构,精度达到传统2D方法的3倍。
|
||||
|
||||
### 梯度装置测量
|
||||
对于Gradient装置,系统实现了特殊的C1和C2电极位置设置功能。用户可以在矩形区域外设置C1和C2的位置,系统会自动验证这些位置的有效性。这种配置方式特别适用于大范围地质调查,能够有效扩大测量范围。
|
||||
|
||||
在某城市地下空间探测项目中,使用Gradient装置对一个500米×500米的区域进行了测量。通过合理设置C1和C2的位置,系统生成了包含5000多个测点的3D脚本。测量结果成功识别出多个地下空洞和异常区域,为城市规划提供了重要依据。
|
||||
|
||||
### 多区域联合测量
|
||||
系统支持通过`m_area`参数设置多个测点区域。用户可以输入类似"1234"的字符串,表示在四个象限中生成测点。这种功能特别适用于不规则地形或障碍物较多的测量区域。
|
||||
|
||||
在某山区地质灾害监测项目中,由于地形复杂,传统测量方法难以实施。通过使用多区域联合测量功能,系统在多个分散的平坦区域生成了测点,成功完成了整个山区的电阻率测量。测量结果为滑坡预警提供了关键数据。
|
||||
|
||||
**Section sources**
|
||||
- [MediumCrossHoleGeomative.cpp](file://cpp/ProblemZone/MediumCrossHoleGeomative.cpp#L1-L148)
|
||||
- [OpCreate3DSptDlg.cpp](file://cpp/Views/OpCreate3DSptDlg.cpp#L277-L294)
|
||||
|
||||
## 与数据可视化模块的集成
|
||||
|
||||
3D测量脚本生成系统与数据可视化模块紧密集成,实现了从脚本生成到结果展示的完整工作流程。
|
||||
|
||||
`CSptManager`类提供了`Browse2DScript`和`Export3DSConInDB`方法,用于将脚本数据传递给可视化模块。`Browse2DScript`方法创建`CBrowse2DScriptDlg`对话框,该对话框使用`m_BrowseScript`控件显示脚本内容。
|
||||
|
||||
`InitBrowse2DView`方法负责初始化浏览视图。该方法从数据库中查询脚本信息,包括电极数量、通道数量、装置类型和电极步长。然后创建`CChannel`对象,并根据装置类型获取对应的`CMedium`对象。
|
||||
|
||||
`Browse2DScriptColorChange`方法实现了脚本内容的可视化对比。该方法将数据库中存储的测量记录与脚本生成的测量记录进行匹配,使用不同颜色标识选中的测点。默认情况下,所有测点显示为青色(RGB(150, 255, 255)),选中的测点显示为绿色(RGB(0, 255, 0))。
|
||||
|
||||
这种集成方式使得用户能够直观地查看脚本内容,验证测点选择的正确性。在实际应用中,这种可视化功能大大提高了工作效率,减少了因脚本配置错误导致的重复测量。
|
||||
|
||||
**Section sources**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L3240-L3588)
|
||||
|
||||
## 性能优化建议与最佳实践
|
||||
|
||||
为了确保3D测量脚本生成系统的高效运行,以下是一些性能优化建议和最佳实践:
|
||||
|
||||
### 数据库优化
|
||||
1. **索引优化**:为`scon`表的`Sname`和`Stype`字段创建复合索引,可以显著提高脚本名称重复性检查的查询速度。
|
||||
2. **批量操作**:在插入大量测量记录时,使用事务处理和批量插入,避免逐条插入带来的性能开销。
|
||||
3. **连接池**:使用数据库连接池管理数据库连接,减少连接建立和关闭的开销。
|
||||
|
||||
### 内存管理
|
||||
1. **对象重用**:在脚本生成过程中,尽量重用`CSptRecord`对象,避免频繁的内存分配和释放。
|
||||
2. **数组预分配**:根据预估的测点数量预分配`m_sptRecArray`的大小,避免数组动态扩容带来的性能损失。
|
||||
3. **及时清理**:在脚本生成完成后,及时清理临时对象和数组,释放内存资源。
|
||||
|
||||
### 算法优化
|
||||
1. **并行处理**:对于大规模3D脚本生成,可以考虑使用多线程并行处理不同的子脚本区域。
|
||||
2. **缓存机制**:缓存常用的介质参数和计算结果,避免重复计算。
|
||||
3. **增量生成**:对于大型测量区域,采用增量生成方式,分批生成和保存测点数据。
|
||||
|
||||
### 用户界面优化
|
||||
1. **异步操作**:将脚本生成过程放在后台线程中执行,避免界面冻结。
|
||||
2. **进度反馈**:提供详细的进度反馈,让用户了解脚本生成的进展情况。
|
||||
3. **预览功能**:提供脚本内容预览功能,让用户在正式生成前确认配置的正确性。
|
||||
|
||||
### 最佳实践
|
||||
1. **合理规划测量区域**:根据地质条件和测量目标,合理规划测量区域的大小和形状,避免不必要的测点。
|
||||
2. **选择合适的装置类型**:根据测量深度和分辨率要求,选择合适的装置类型。
|
||||
3. **定期备份脚本**:定期备份生成的3D脚本,防止数据丢失。
|
||||
4. **版本控制**:对重要的测量脚本进行版本控制,记录每次修改的内容和原因。
|
||||
|
||||
**Section sources**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L3000-L3193)
|
||||
- [Medium3D.cpp](file://cpp/ProblemZone/Medium3D.cpp#L1-L347)
|
||||
|
||||
## 结论
|
||||
本文档全面阐述了3D测量脚本生成的技术实现,从核心函数`CSptManager::Create3DSConInDB`到`CScript3D`类的三维电极网络管理,再到`Medium3D`及其衍生类的空间坐标计算算法。文档详细描述了3D脚本参数配置界面的用户交互逻辑和数据验证机制,并提供了完整的XML脚本结构示例。
|
||||
|
||||
通过分析复杂地质条件下的应用案例,展示了该技术在跨孔电阻率成像、梯度装置测量和多区域联合测量中的实际应用效果。文档还介绍了与数据可视化模块的集成方式,以及性能优化建议和最佳实践。
|
||||
|
||||
这些技术实现为地质勘探、环境监测和工程检测等领域提供了强大的工具支持。通过合理应用这些技术和最佳实践,用户可以高效地生成高质量的3D测量脚本,获得准确可靠的地下结构信息。
|
||||
@@ -0,0 +1,307 @@
|
||||
# 脚本管理
|
||||
|
||||
<cite>
|
||||
**本文档引用文件**
|
||||
- [Script.cpp](file://cpp/ProblemZone/Script.cpp)
|
||||
- [Script2D.cpp](file://cpp/ProblemZone/Script2D.cpp)
|
||||
- [Script3D.cpp](file://cpp/ProblemZone/Script3D.cpp)
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp)
|
||||
- [Script.h](file://h/Script.h)
|
||||
- [Script2D.h](file://h/Script2D.h)
|
||||
- [Script3D.h](file://h/Script3D.h)
|
||||
- [SptManager.h](file://h/SptManager.h)
|
||||
- [MediumA.cpp](file://cpp/ProblemZone/MediumA.cpp)
|
||||
- [MediumZC.cpp](file://cpp/ProblemZone/MediumZC.cpp)
|
||||
- [MediumCrossHoleGeomative.cpp](file://cpp/ProblemZone/MediumCrossHoleGeomative.cpp)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [引言](#引言)
|
||||
2. [核心组件分析](#核心组件分析)
|
||||
3. [CScript与CSptManager协同工作机制](#cscript与csptmanager协同工作机制)
|
||||
4. [介质类型与脚本生成算法](#介质类型与脚本生成算法)
|
||||
5. [XML脚本结构定义](#xml脚本结构定义)
|
||||
6. [脚本工作流程示例](#脚本工作流程示例)
|
||||
7. [系统集成与特殊场景应用](#系统集成与特殊场景应用)
|
||||
8. [结论](#结论)
|
||||
|
||||
## 引言
|
||||
|
||||
脚本管理模块是GeomativeStudio系统中的核心功能之一,负责2D/3D测量脚本的生成、编辑、验证和导出。该模块通过CScript类和CSptManager类的协同工作,实现了对不同介质类型(如MediumA到MediumZC)的测量脚本的精确生成。脚本参数(如电极数量、测量类型、时间窗口)的配置机制确保了测量过程的灵活性和准确性。脚本以XML格式存储,包含<cn>、<name>、<type>、<rect>等元素,定义了测量的各个方面。本文档将详细说明这些功能的实现,并提供完整的应用示例。
|
||||
|
||||
## 核心组件分析
|
||||
|
||||
脚本管理模块的核心由CScript类及其派生类(CScript2D、CScript3D)和CSptManager类组成。CScript类作为基类,定义了脚本的基本属性和虚函数接口,包括电极数(m_iEAmount)、脚本类型(m_iSType)和装置类型(m_iAR)。其派生类CScript2D和CScript3D分别处理二维和三维测量脚本的具体实现。
|
||||
|
||||
CSptManager类作为脚本管理器,负责协调脚本的创建、删除和管理。它通过链接列表(m_sptLinkList)管理内存中的脚本对象,并通过数据库操作实现脚本的持久化存储。该类提供了创建2D、3D和CE类型脚本的接口,以及从设备加载和向设备传输脚本的功能。
|
||||
|
||||
**核心组件关系图**
|
||||
```mermaid
|
||||
classDiagram
|
||||
class CScript {
|
||||
+DWORD m_dwID
|
||||
+int m_iEAmount
|
||||
+int m_iSType
|
||||
+int m_iAR
|
||||
+virtual bool ShowSptConInfo(CListCtrl&)
|
||||
+virtual bool ShowSptDetailInfo(CListCtrl&)
|
||||
+virtual bool ShowChannelList(CListCtrl&)
|
||||
}
|
||||
class CScript2D {
|
||||
+CPtrList m_chaList
|
||||
+bool ShowChannelList(CListCtrl&)
|
||||
+bool ShowSptConInfo(CListCtrl&)
|
||||
+bool ShowSptDetailInfo(CListCtrl&)
|
||||
+void AdjustRecListColumn(int, CListCtrl&)
|
||||
}
|
||||
class CScript3D {
|
||||
+CPtrList m_chaList
|
||||
+int m_iTpAmount
|
||||
+int m_PointNum[128]
|
||||
+bool ShowSptConInfo(CListCtrl&)
|
||||
+bool ShowSptDetailInfo(CListCtrl&)
|
||||
+bool ShowChannelList(CListCtrl&)
|
||||
+void AdjustRecListColumn(int, CListCtrl&)
|
||||
}
|
||||
class CSptManager {
|
||||
+CLinkList<CScript*> m_sptLinkList
|
||||
+CLinkList<CMedium*> m_medLinkList
|
||||
+COpCreateCESptDlg* m_pOpCreateCESptDlg
|
||||
+CScriptCE* m_pNewScript
|
||||
+CChannel* m_pChannel
|
||||
+CScript* GetScript(DWORD)
|
||||
+void DeleteObjInMem(DWORD)
|
||||
+UINT Create2DSConInDB(DWORD&)
|
||||
+void Delete2DSConInDB(DWORD)
|
||||
+UINT CreateCESConInDB(DWORD&)
|
||||
+void DeleteCESConInDB(DWORD)
|
||||
+UINT Create3DSConInDB(DWORD*)
|
||||
}
|
||||
CScript <|-- CScript2D
|
||||
CScript <|-- CScript3D
|
||||
CScript <|-- CScriptCE
|
||||
CSptManager --> CScript : "管理"
|
||||
CSptManager --> CMedium : "使用"
|
||||
```
|
||||
|
||||
**图示来源**
|
||||
- [Script.h](file://h/Script.h#L15-L36)
|
||||
- [Script2D.h](file://h/Script2D.h#L16-L29)
|
||||
- [Script3D.h](file://h/Script3D.h#L16-L39)
|
||||
- [SptManager.h](file://h/SptManager.h#L27-L85)
|
||||
|
||||
**本节来源**
|
||||
- [Script.h](file://h/Script.h#L15-L36)
|
||||
- [Script2D.h](file://h/Script2D.h#L16-L29)
|
||||
- [Script3D.h](file://h/Script3D.h#L16-L39)
|
||||
- [SptManager.h](file://h/SptManager.h#L27-L85)
|
||||
|
||||
## CScript与CSptManager协同工作机制
|
||||
|
||||
CScript类和CSptManager类通过句柄机制和工厂模式协同工作。CSptManager类的GetScript方法是两者交互的核心,它根据句柄(dwHandle)从内存链接列表中获取或创建相应的CScript对象。当脚本对象不存在时,CSptManager会根据句柄中的样式信息(PZ_STYLE_SCON_CE, PZ_STYLE_SCON_2D, PZ_STYLE_SCON_3D)动态创建对应的CScript派生类实例。
|
||||
|
||||
这种设计实现了多态性和内存管理的优化。CSptManager负责脚本对象的生命周期管理,通过DeleteObjInMem方法在内存中删除指定句柄的脚本对象。同时,CSptManager提供了Create2DSConInDB、CreateCESConInDB等方法,将用户通过对话框输入的参数转化为数据库中的脚本记录。
|
||||
|
||||
脚本生成过程中,CSptManager首先初始化创建对话框,获取用户输入的脚本名称、定义者等信息。然后开始数据库事务,生成唯一标识符(CN),并将基本信息插入scon表。接着遍历通道列表,为每个通道生成相应的测量记录并插入数据库。整个过程采用事务处理,确保数据的一致性,任何步骤失败都会触发回滚操作。
|
||||
|
||||
**脚本创建流程图**
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([开始创建脚本]) --> InitDialog["初始化创建对话框"]
|
||||
InitDialog --> ShowDialog["显示对话框"]
|
||||
ShowDialog --> UserInput{"用户输入参数?"}
|
||||
UserInput --> |否| Cancel["取消操作"]
|
||||
UserInput --> |是| BeginTrans["开始数据库事务"]
|
||||
BeginTrans --> GenerateCN["生成唯一标识符(CN)"]
|
||||
GenerateCN --> CheckExist["检查脚本名称是否已存在"]
|
||||
CheckExist --> |已存在| ShowError["显示错误信息"]
|
||||
CheckExist --> |不存在| InsertScon["插入scon表基础信息"]
|
||||
InsertScon --> GetMaxID["获取scon表最大ID"]
|
||||
GetMaxID --> ProcessChannels["处理通道列表"]
|
||||
ProcessChannels --> HasChannel{"还有通道?"}
|
||||
HasChannel --> |否| UpdateTPAmount["更新TPamount字段"]
|
||||
HasChannel --> |是| InsertChannel["插入channel表"]
|
||||
InsertChannel --> GetCHID["获取channel表ID"]
|
||||
GetCHID --> ProcessRecords["处理测量记录"]
|
||||
ProcessRecords --> HasRecord{"还有记录?"}
|
||||
HasRecord --> |否| NextChannel["下一个通道"]
|
||||
HasRecord --> |是| InsertScript["插入script2d表"]
|
||||
InsertScript --> UpdateCount["更新测点计数"]
|
||||
UpdateCount --> NextRecord["下一条记录"]
|
||||
NextRecord --> ProcessRecords
|
||||
NextChannel --> HasChannel
|
||||
UpdateTPAmount --> CommitTrans["提交事务"]
|
||||
CommitTrans --> Success["返回成功"]
|
||||
ShowError --> RollbackTrans["回滚事务"]
|
||||
RollbackTrans --> Fail["返回失败"]
|
||||
Cancel --> End([结束])
|
||||
Success --> End
|
||||
Fail --> End
|
||||
```
|
||||
|
||||
**图示来源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L257-L487)
|
||||
|
||||
**本节来源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L127-L157)
|
||||
- [SptManager.h](file://h/SptManager.h#L38-L40)
|
||||
|
||||
## 介质类型与脚本生成算法
|
||||
|
||||
系统支持多种介质类型,从MediumA到MediumZC,每种类型对应特定的脚本生成算法。这些算法定义了电极配置、测量序列和K值计算方法。介质类型通过m_iAR属性标识,不同的AR值对应不同的测量装置。
|
||||
|
||||
MediumA类实现了温纳装置的脚本生成算法,其核心是GenerateSptRecElecVal方法。该方法根据电极总数计算最大间距和移动步数,然后生成A、B、M、N电极的组合序列。K值计算采用公式k = 2π(n),其中n是电极间距。测点层级通过CalculateSptLevel方法确定,返回N-M的差值。
|
||||
|
||||
MediumZC类实现了更复杂的梯度装置算法,其特点是当BM间距大于AB间距6倍时,AB间距会自动增加。该算法通过CalculateSptKVal方法计算K值,公式为k = π·n·(n+1)·(n+2)·a,其中n是相对间距,a是AB间距。这种设计能够适应更大范围的地质探测需求。
|
||||
|
||||
跨孔测量专用的MediumCrossHoleGeomative类实现了特殊的电极排列算法。该算法将电极分为两组,一组从下到上编号,另一组从上到下编号。测量时C1P1距离固定为层数,C2P2依次向下移动,每次移动2个电极间距。K值计算采用公式k = π / (1/AM - 1/sqrt(AM² + AB²)),考虑了电极间的实际空间距离。
|
||||
|
||||
**介质类型对比表**
|
||||
| 介质类型 | AR值范围 | 电极配置 | K值计算公式 | 特殊特性 |
|
||||
|---------|--------|--------|-----------|--------|
|
||||
| MediumA | 1,4,5,6,11,39,41 | 温纳装置 | k = 2π(n) | 基础电阻率测量 |
|
||||
| MediumB | 2,9 | 偶极-偶极装置 | k = π·n·(n+1)·a | 高分辨率测量 |
|
||||
| MediumZC | 22-27 | 梯度装置 | k = π·n·(n+1)·(n+2)·a | 大深度探测 |
|
||||
| MediumCrossHoleGeomative | 33,34 | 跨孔装置 | k = π / (1/AM - 1/sqrt(AM² + AB²)) | 井间测量 |
|
||||
|
||||
**本节来源**
|
||||
- [MediumA.cpp](file://cpp/ProblemZone/MediumA.cpp#L30-L239)
|
||||
- [MediumZC.cpp](file://cpp/ProblemZone/MediumZC.cpp#L30-L302)
|
||||
- [MediumCrossHoleGeomative.cpp](file://cpp/ProblemZone/MediumCrossHoleGeomative.cpp#L30-L148)
|
||||
|
||||
## XML脚本结构定义
|
||||
|
||||
测量脚本在系统中以XML格式存储,其结构定义了测量的所有关键参数。XML文档的根元素包含<cn>、<name>、<type>、<rect>等核心元素,每个元素都有特定的含义和数据类型。
|
||||
|
||||
<cn>元素存储脚本的唯一标识符,由GUCodeCreator生成的GUID代码构成,确保每个脚本在全球范围内的唯一性。<name>元素记录脚本的名称,用于用户识别和管理。<type>元素定义脚本类型(1D、2D、3D),决定了后续数据处理的方式。
|
||||
|
||||
<rect>元素包含四个逗号分隔的数值,表示测量区域的矩形边界(左、上、右、下)。<rectloc>元素指定矩形的位置属性,而<poledistance>和<polestep>元素分别记录电极间距和步进距离,这些参数直接影响测量的精度和范围。
|
||||
|
||||
脚本的详细信息存储在子元素中,包括电极数量(eamount)、通道数量(chamount)、测点数量(tpamount)、定义者(definer)、创建日期(dedate)和描述信息(scdesc)。这些元数据为脚本的管理和追溯提供了完整的信息支持。
|
||||
|
||||
**XML结构示例**
|
||||
```xml
|
||||
<scon>
|
||||
<cn>GUID-123456789</cn>
|
||||
<name>2D测量脚本</name>
|
||||
<type>2</type>
|
||||
<eamount>24</eamount>
|
||||
<chamount>1</chamount>
|
||||
<tpamount>120</tpamount>
|
||||
<definer>管理员</definer>
|
||||
<dedate>2023-01-01</dedate>
|
||||
<scdesc>用于场地电阻率成像</scdesc>
|
||||
<rect>0,0,0,0</rect>
|
||||
<rectloc>0</rectloc>
|
||||
<poledistance>0</poledistance>
|
||||
<polestep>0</polestep>
|
||||
</scon>
|
||||
```
|
||||
|
||||
**本节来源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L363-L380)
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L678-L694)
|
||||
|
||||
## 脚本工作流程示例
|
||||
|
||||
完整的脚本工作流程包括创建、编辑、验证和导出四个主要阶段。以创建一个2D测量脚本为例,首先通过CSptManager的Create2DSConInDB方法启动创建过程。系统会显示COpCreateSptDlg对话框,用户在此输入脚本名称、定义者等基本信息,并选择测量装置类型。
|
||||
|
||||
在编辑阶段,用户通过图形界面配置电极布局和测量参数。系统根据选择的介质类型(如MediumA)调用相应的GenerateSptRecElecVal方法,生成测量序列。该方法计算每个测点的A、B、M、N电极位置,K值和层级信息,并将结果存储在CSptRecord对象数组中。
|
||||
|
||||
验证阶段在脚本保存前自动执行。系统首先检查脚本名称是否已存在,避免重复。然后验证电极配置的合理性,确保所有参数在有效范围内。数据库操作采用事务模式,任何验证失败都会导致事务回滚,保证数据完整性。
|
||||
|
||||
导出阶段通过Export2DSConInDB方法实现,将数据库中的脚本信息转换为XML格式文件。导出过程包括读取scon表的基础信息、channel表的通道配置和script2d表的测量记录,然后按照预定义的XML结构进行序列化。导出的文件可以用于设备传输或数据共享。
|
||||
|
||||
**脚本工作流程序列图**
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant 用户 as "用户"
|
||||
participant 对话框 as "COpCreateSptDlg"
|
||||
participant 管理器 as "CSptManager"
|
||||
participant 数据库 as "数据库"
|
||||
participant 文件 as "XML文件"
|
||||
用户->>对话框 : 启动创建脚本
|
||||
对话框->>用户 : 显示输入界面
|
||||
用户->>对话框 : 输入脚本参数
|
||||
对话框->>管理器 : 调用Create2DSConInDB
|
||||
管理器->>数据库 : 开始事务
|
||||
管理器->>管理器 : 生成CN标识符
|
||||
管理器->>数据库 : 检查名称冲突
|
||||
数据库-->>管理器 : 返回检查结果
|
||||
管理器->>数据库 : 插入scon表
|
||||
管理器->>数据库 : 获取最大ID
|
||||
管理器->>管理器 : 遍历通道列表
|
||||
管理器->>数据库 : 插入channel表
|
||||
管理器->>数据库 : 插入script2d表
|
||||
管理器->>数据库 : 更新TPamount
|
||||
管理器->>数据库 : 提交事务
|
||||
数据库-->>管理器 : 返回结果
|
||||
管理器-->>对话框 : 返回执行码
|
||||
对话框-->>用户 : 显示结果
|
||||
用户->>管理器 : 请求导出脚本
|
||||
管理器->>数据库 : 读取脚本数据
|
||||
数据库-->>管理器 : 返回数据集
|
||||
管理器->>管理器 : 序列化为XML
|
||||
管理器->>文件 : 保存XML文件
|
||||
文件-->>管理器 : 确认保存
|
||||
管理器-->>用户 : 显示导出成功
|
||||
```
|
||||
|
||||
**图示来源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L257-L487)
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L58-L83)
|
||||
|
||||
**本节来源**
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L257-L487)
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L58-L83)
|
||||
|
||||
## 系统集成与特殊场景应用
|
||||
|
||||
脚本管理器与项目管理器、测试数据管理器紧密集成,形成完整的测量工作流。项目管理器负责组织和管理测量项目,为脚本提供上下文环境。当创建新项目时,项目管理器会调用CSptManager的相关方法,初始化项目所需的脚本模板。
|
||||
|
||||
测试数据管理器与脚本管理器通过共享的数据结构进行交互。测量完成后,测试数据管理器读取脚本信息,将原始数据与脚本中的测点配置进行匹配,生成结构化的测试结果。这种集成确保了测量数据的可追溯性和准确性。
|
||||
|
||||
在跨孔测量等特殊场景下,系统采用专门的MediumCrossHoleGeomative类处理复杂的电极配置。这种场景通常涉及两个或多个钻孔中的电极阵列,需要精确的时空同步。脚本管理器生成的脚本包含了特殊的时序控制信息,确保发射电极和接收电极的协调工作。
|
||||
|
||||
对于大型三维测量项目,系统支持脚本分割功能。CSptManager的Create3DSConInDB方法可以将大型脚本分割为多个子脚本,每个子脚本对应一个测量区域。这种设计提高了测量效率,允许分区域并行测量,同时保持数据的整体一致性。
|
||||
|
||||
**系统集成架构图**
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "用户界面"
|
||||
UI[用户界面]
|
||||
end
|
||||
subgraph "核心管理器"
|
||||
PM[项目管理器]
|
||||
SM[脚本管理器]
|
||||
TDM[测试数据管理器]
|
||||
end
|
||||
subgraph "数据存储"
|
||||
DB[(数据库)]
|
||||
FS[(文件系统)]
|
||||
end
|
||||
UI --> PM
|
||||
UI --> SM
|
||||
UI --> TDM
|
||||
PM --> SM : "初始化脚本模板"
|
||||
SM --> DB : "存储脚本数据"
|
||||
TDM --> DB : "存储测试结果"
|
||||
SM --> TDM : "提供测点配置"
|
||||
TDM --> SM : "反馈测量状态"
|
||||
SM --> FS : "导出XML脚本"
|
||||
TDM --> FS : "导出测量报告"
|
||||
```
|
||||
|
||||
**图示来源**
|
||||
- [SptManager.h](file://h/SptManager.h#L30-L58)
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L33-L34)
|
||||
|
||||
**本节来源**
|
||||
- [SptManager.h](file://h/SptManager.h#L30-L58)
|
||||
- [SptManager.cpp](file://cpp/Managers/SptManager.cpp#L33-L34)
|
||||
|
||||
## 结论
|
||||
|
||||
脚本管理模块通过精心设计的CScript和CSptManager类架构,实现了对2D/3D测量脚本的全面管理。系统支持从MediumA到MediumZC的多种介质类型,每种类型都有专门优化的脚本生成算法,满足不同地质探测需求。XML格式的脚本结构定义了完整的测量参数,确保了数据的标准化和可交换性。
|
||||
|
||||
该模块与项目管理器、测试数据管理器的深度集成,构建了高效的工作流,特别适用于跨孔测量等复杂场景。通过事务处理和验证机制,系统保证了脚本数据的完整性和一致性。未来可进一步优化脚本生成算法,增加更多介质类型支持,并提升大规模三维脚本的处理性能。
|
||||
@@ -0,0 +1,255 @@
|
||||
# 自定义脚本
|
||||
|
||||
<cite>
|
||||
**本文档中引用的文件**
|
||||
- [MediumCustom2D.cpp](file://cpp/ProblemZone/MediumCustom2D.cpp)
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp)
|
||||
- [CustomSptQueryDial.cpp](file://cpp/Views/CustomSptQueryDial.cpp)
|
||||
- [MediumCustom2D.h](file://h/MediumCustom2D.h)
|
||||
- [DialCustomSptInput.h](file://h/DialCustomSptInput.h)
|
||||
- [CustomSptQueryDial.h](file://h/CustomSptQueryDial.h)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [引言](#引言)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概述](#架构概述)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖分析](#依赖分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
|
||||
## 引言
|
||||
本文档详细阐述了Geomative Studio软件中自定义脚本功能的实现机制。该功能允许用户创建非标准的电极布局和测量序列,以适应复杂或非典型的地质探测需求。文档重点分析了`MediumCustom2D`类如何作为自定义脚本的核心逻辑处理单元,以及`CDialCustomSptInput`和`CCustomSptQueryDial`对话框如何提供用户交互界面。此外,文档还涵盖了自定义脚本的XML存储格式、参数编码规则、创建流程、兼容性问题及常见错误处理方案。
|
||||
|
||||
## 项目结构
|
||||
Geomative Studio项目的自定义脚本功能主要分布在`cpp`和`h`目录下的特定子目录中。核心实现位于`cpp\ProblemZone`和`cpp\Operator`目录,而用户界面组件则位于`cpp\Views`目录。头文件统一存放在`h`目录下。这种分层结构将业务逻辑、用户界面和数据模型清晰地分离。
|
||||
|
||||
```mermaid
|
||||
graph TB
|
||||
subgraph "核心逻辑"
|
||||
A[MediumCustom2D.cpp]
|
||||
B[MediumCustom2D.h]
|
||||
end
|
||||
subgraph "用户界面"
|
||||
C[DialCustomSptInput.cpp]
|
||||
D[DialCustomSptInput.h]
|
||||
E[CustomSptQueryDial.cpp]
|
||||
F[CustomSptQueryDial.h]
|
||||
end
|
||||
A --> C : "调用"
|
||||
C --> E : "调用"
|
||||
B --> D : "继承"
|
||||
D --> F : "包含"
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [MediumCustom2D.cpp](file://cpp/ProblemZone/MediumCustom2D.cpp#L19)
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp#L23)
|
||||
- [CustomSptQueryDial.cpp](file://cpp/Views/CustomSptQueryDial.cpp#L18)
|
||||
|
||||
**节源**
|
||||
- [MediumCustom2D.cpp](file://cpp/ProblemZone/MediumCustom2D.cpp)
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp)
|
||||
- [CustomSptQueryDial.cpp](file://cpp/Views/CustomSptQueryDial.cpp)
|
||||
|
||||
## 核心组件
|
||||
自定义脚本功能的核心由`CMediumCustom2D`类驱动,该类继承自`CMedium`基类,专门负责处理用户自定义的2D测量脚本。当用户选择自定义脚本模式时,系统会实例化`CMediumCustom2D`对象,并调用其`GenerateSptRecElecVal`方法来生成具体的测量记录。此过程会启动`CDialCustomSptInput`对话框,引导用户输入电极配置和测量参数。`CDialCustomSptInput`对话框是用户与系统交互的主要界面,它提供了手动输入、修改、删除和从Excel文件导入测量序列的功能。`CCustomSptQueryDial`对话框则在导入数据时出现,用于询问用户是追加还是替换现有数据。
|
||||
|
||||
**节源**
|
||||
- [MediumCustom2D.cpp](file://cpp/ProblemZone/MediumCustom2D.cpp#L28)
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp#L23)
|
||||
- [CustomSptQueryDial.cpp](file://cpp/Views/CustomSptQueryDial.cpp#L18)
|
||||
|
||||
## 架构概述
|
||||
自定义脚本功能的架构遵循典型的MVC(模型-视图-控制器)模式。`CMediumCustom2D`类扮演模型和控制器的角色,它定义了数据结构(如`CSptRecord`)并包含了生成和验证测量序列的业务逻辑。`CDialCustomSptInput`和`CCustomSptQueryDial`类则作为视图,负责呈现用户界面和收集用户输入。整个流程始于`CMediumCustom2D::GenerateSptRecElecVal`方法,该方法创建并显示`CDialCustomSptInput`对话框。用户在对话框中完成输入后,数据被验证并存储在列表控件中。当用户确认后,这些数据被读取并转换为内部的`CSptRecord`对象数组,最终返回给上层调用者用于执行测量。
|
||||
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant 用户
|
||||
participant MediumCustom2D as CMediumCustom2D
|
||||
participant CustomSptInput as CDialCustomSptInput
|
||||
participant QueryDial as CCustomSptQueryDial
|
||||
用户->>MediumCustom2D : 选择自定义脚本
|
||||
MediumCustom2D->>CustomSptInput : 创建并显示对话框
|
||||
CustomSptInput-->>用户 : 显示输入界面
|
||||
用户->>CustomSptInput : 输入电极和测量参数
|
||||
loop 输入验证
|
||||
CustomSptInput->>CustomSptInput : CheckInputIsValid()
|
||||
end
|
||||
用户->>CustomSptInput : 点击“完成”
|
||||
alt 数据有效
|
||||
CustomSptInput-->>MediumCustom2D : 返回成功
|
||||
MediumCustom2D->>CustomSptInput : 读取列表数据
|
||||
MediumCustom2D->>MediumCustom2D : 生成CSptRecord数组
|
||||
MediumCustom2D-->>用户 : 准备就绪,开始测量
|
||||
else 数据无效
|
||||
CustomSptInput-->>用户 : 显示错误信息
|
||||
end
|
||||
用户->>CustomSptInput : 点击“导入”
|
||||
CustomSptInput->>QueryDial : 创建并显示查询对话框
|
||||
QueryDial-->>用户 : 询问追加或替换
|
||||
用户->>QueryDial : 选择操作
|
||||
QueryDial-->>CustomSptInput : 返回操作结果
|
||||
CustomSptInput->>CustomSptInput : 执行导入逻辑
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [MediumCustom2D.cpp](file://cpp/ProblemZone/MediumCustom2D.cpp#L28)
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp#L23)
|
||||
- [CustomSptQueryDial.cpp](file://cpp/Views/CustomSptQueryDial.cpp#L18)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### MediumCustom2D类分析
|
||||
`CMediumCustom2D`类是自定义脚本功能的引擎。其核心方法`GenerateSptRecElecVal`负责协调整个脚本生成过程。该方法首先创建`CDialCustomSptInput`对话框实例并显示它。通过`RunModalLoop`进入模态循环,等待用户交互。一旦用户完成输入并确认,该方法会遍历对话框列表控件中的每一行,提取A、B、M、N电极编号、K系数、叠加次数(N)和层数(Level)等信息,并创建相应的`CSptRecord`对象。特别地,该方法还处理多通道模式下的数据排序和去重,确保测量序列的唯一性和正确性。
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class CMediumCustom2D {
|
||||
+GenerateSptRecElecVal(iEAmount, pMaxLevel, pPtAmount, pSptRecArray) bool
|
||||
}
|
||||
class CMedium {
|
||||
<<abstract>>
|
||||
}
|
||||
class CSptRecord {
|
||||
+int m_iC1
|
||||
+int m_iC2
|
||||
+int m_iP1
|
||||
+int m_iP2
|
||||
+float m_fK
|
||||
+int m_iN
|
||||
+int m_iLevel
|
||||
+int m_iTsn
|
||||
+bool m_bIsSel
|
||||
}
|
||||
CMediumCustom2D --|> CMedium : 继承
|
||||
CMediumCustom2D --> CSptRecord : 创建
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [MediumCustom2D.cpp](file://cpp/ProblemZone/MediumCustom2D.cpp#L19)
|
||||
- [MediumCustom2D.h](file://h/MediumCustom2D.h#L13)
|
||||
|
||||
**节源**
|
||||
- [MediumCustom2D.cpp](file://cpp/ProblemZone/MediumCustom2D.cpp#L28)
|
||||
|
||||
### CustomSptInput对话框分析
|
||||
`CDialCustomSptInput`对话框是用户定义测量序列的主要交互界面。它提供了一个列表控件(`m_listCustomSpt`)来展示已添加的测量点,并提供了一组输入框用于设置A、B、M、N电极、K系数、叠加次数和层数。用户可以通过“增加”按钮将当前输入添加到列表中,通过“修改”按钮更新选中的行,或通过“删除”按钮移除选中的行。对话框实现了严格的数据输入验证,确保A、B、M、N为正整数或-1(表示无穷远电极),层数和叠加次数为正整数,且K值为有效浮点数。K值可以手动输入,也可以通过“自动”模式根据电极坐标计算得出。
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
Start([开始]) --> Init["初始化对话框"]
|
||||
Init --> Show["显示输入界面"]
|
||||
subgraph 用户输入
|
||||
Show --> Input["用户输入A,B,M,N等参数"]
|
||||
Input --> Check["检查输入有效性"]
|
||||
Check --> |无效| Error["显示错误信息"]
|
||||
Error --> Input
|
||||
Check --> |有效| Wait["等待用户操作"]
|
||||
end
|
||||
Wait --> Add["点击'增加'按钮"]
|
||||
Wait --> Modify["点击'修改'按钮"]
|
||||
Wait --> Delete["点击'删除'按钮"]
|
||||
Wait --> Import["点击'导入'按钮"]
|
||||
Wait --> OK["点击'完成'按钮"]
|
||||
Wait --> Cancel["点击'取消'按钮"]
|
||||
Add --> Validate["验证输入"]
|
||||
Validate --> |有效| AddToList["添加到列表"]
|
||||
AddToList --> Show
|
||||
Modify --> Select["选择列表项"]
|
||||
Select --> |已选| ModifyItem["修改该项"]
|
||||
ModifyItem --> Show
|
||||
Delete --> Select
|
||||
Delete --> |已选| Remove["从列表移除"]
|
||||
Remove --> Show
|
||||
Import --> Query["显示CCustomSptQueryDial"]
|
||||
Query --> |追加| Append["追加导入数据"]
|
||||
Query --> |替换| Replace["替换现有数据"]
|
||||
Append --> Show
|
||||
Replace --> Show
|
||||
OK --> CheckList["检查列表是否为空"]
|
||||
CheckList --> |为空| Warn["警告:脚本不能为空"]
|
||||
CheckList --> |不为空| ReturnOK["返回OK"]
|
||||
ReturnOK --> End([结束])
|
||||
Cancel --> ReturnCancel["返回取消"]
|
||||
ReturnCancel --> End
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp#L23)
|
||||
- [DialCustomSptInput.h](file://h/DialCustomSptInput.h#L12)
|
||||
|
||||
**节源**
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp#L78)
|
||||
|
||||
### CustomSptQueryDial对话框分析
|
||||
`CCustomSptQueryDial`对话框是一个简单的查询对话框,仅在用户尝试从Excel文件导入测量数据且当前列表不为空时出现。其主要作用是解决数据冲突,提供“追加”、“替换”和“取消”三个选项。用户的选择决定了导入操作的行为:追加会将新数据添加到现有列表的末尾,替换会清空现有列表后再导入新数据,取消则会中断整个导入过程。该对话框的设计简洁明了,专注于解决一个特定的用户决策点。
|
||||
|
||||
```mermaid
|
||||
classDiagram
|
||||
class CCustomSptQueryDial {
|
||||
+m_nRes int
|
||||
+OnButtonAppend() void
|
||||
+OnButtonCancel() void
|
||||
+OnButtonReplace() void
|
||||
+GetOperResult() int
|
||||
}
|
||||
CCustomSptQueryDial --|> CDialog : 继承
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [CustomSptQueryDial.cpp](file://cpp/Views/CustomSptQueryDial.cpp#L18)
|
||||
- [CustomSptQueryDial.h](file://h/CustomSptQueryDial.h#L18)
|
||||
|
||||
**节源**
|
||||
- [CustomSptQueryDial.cpp](file://cpp/Views/CustomSptQueryDial.cpp#L48)
|
||||
|
||||
## 依赖分析
|
||||
自定义脚本功能依赖于多个核心组件和外部库。`CMediumCustom2D`直接依赖于`CDialCustomSptInput`来获取用户输入。`CDialCustomSptInput`对话框依赖于MFC框架的`CListCtrl`来实现列表功能,并依赖于`excel.h`头文件和COM接口来实现Excel文件的导入功能,这表明系统依赖于Microsoft Excel应用程序的安装。此外,该功能还依赖于全局变量`g_iUILanguage`来实现多语言支持,以及`theApp`应用对象来访问全局配置(如多通道模式)。这些依赖关系确保了功能的完整性和用户体验的一致性。
|
||||
|
||||
```mermaid
|
||||
graph LR
|
||||
A[CMediumCustom2D] --> B[CDialCustomSptInput]
|
||||
B --> C[CListCtrl]
|
||||
B --> D[Excel COM]
|
||||
B --> E[g_iUILanguage]
|
||||
B --> F[theApp]
|
||||
D --> G[Microsoft Excel]
|
||||
```
|
||||
|
||||
**图源**
|
||||
- [MediumCustom2D.cpp](file://cpp/ProblemZone/MediumCustom2D.cpp#L43)
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp#L6)
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp#L619)
|
||||
|
||||
**节源**
|
||||
- [MediumCustom2D.cpp](file://cpp/ProblemZone/MediumCustom2D.cpp)
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp)
|
||||
|
||||
## 性能考虑
|
||||
自定义脚本功能的性能主要受用户输入数据量和Excel文件导入操作的影响。在生成测量序列时,`GenerateSptRecElecVal`方法会对用户输入的每一行进行遍历和解析,时间复杂度为O(n),其中n为测量点的数量。对于大型脚本,此过程可能会有轻微延迟,但通常在可接受范围内。性能瓶颈主要出现在Excel导入环节,因为该过程需要启动Excel进程、打开文件、读取数据并进行安全数组转换,这些操作相对耗时。建议用户在导入大型文件时保持耐心。多通道模式下的数据排序使用了STL的`map`容器,虽然提供了O(log n)的查找效率,但在处理海量数据时仍需注意内存占用。
|
||||
|
||||
## 故障排除指南
|
||||
在使用自定义脚本功能时,可能会遇到以下常见问题及解决方案:
|
||||
|
||||
1. **电极重叠检测**: 当用户输入的A、B、M、N电极中任意两个编号相同时,系统会通过`CalculateK`方法中的距离计算检测到此问题,并弹出“任意2个电极之间的距离都不能为零!”的错误提示。解决方案是检查并确保所有电极编号唯一。
|
||||
|
||||
2. **测量序列逻辑验证**: 系统在`CheckInputIsValid`方法中执行多项验证:
|
||||
* **电极编号**: A、B、M、N必须为正整数或-1。输入非数字或负数(除-1外)会触发错误。
|
||||
* **层数和叠加次数**: 必须为正整数,且叠加次数必须在1-255之间。
|
||||
* **K值计算**: 在自动模式下,如果电极配置导致几何因子K的分母为零(例如,A、B、M、N共线的特殊情况),系统会提示“自动计算K值错误,请检查输入!”。此时应手动输入K值或调整电极布局。
|
||||
|
||||
3. **Excel导入失败**: 可能原因包括未安装Excel、文件格式不正确(非.xlsx)、文件被占用或工作表中无数据。确保Excel已正确安装,并检查文件路径和内容。
|
||||
|
||||
4. **脚本为空**: 如果用户未添加任何测量点就点击“完成”,系统会阻止操作并提示“脚本数据不能为空!”。
|
||||
|
||||
**节源**
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp#L425)
|
||||
- [DialCustomSptInput.cpp](file://cpp/Operator/DialCustomSptInput.cpp#L522)
|
||||
- [MediumCustom2D.cpp](file://cpp/ProblemZone/MediumCustom2D.cpp#L241)
|
||||
|
||||
## 结论
|
||||
Geomative Studio的自定义脚本功能通过`MediumCustom2D`类和`CustomSptInput`对话框的协同工作,为用户提供了高度灵活的测量配置能力。该设计允许用户突破标准测量阵列的限制,在非标准地形或特殊地质条件下定义任意的电极布局和测量序列。其XML存储格式和参数编码规则确保了配置的可持久化和可移植性。尽管存在对Excel的外部依赖和潜在的性能瓶颈,但其直观的用户界面和完善的输入验证机制使得该功能既强大又可靠。通过遵循本文档提供的指南,用户可以有效地创建和管理自定义脚本,充分发挥Geomative Studio在复杂勘探任务中的优势。
|
||||
@@ -0,0 +1,399 @@
|
||||
# 跨孔测量脚本
|
||||
|
||||
<cite>
|
||||
**本文档引用的文件**
|
||||
- [CCrossHoleConfig2DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig2DMainDlg.cpp)
|
||||
- [CCrossHoleConfig3DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig3DMainDlg.cpp)
|
||||
- [MediumCrossHoleGeomative.cpp](file://cpp\ProblemZone\MediumCrossHoleGeomative.cpp)
|
||||
- [CCrossHoleConfig2DMainDlg.h](file://h\crossHole\CCrossHoleConfig2DMainDlg.h)
|
||||
- [CCrossHoleConfig3DMainDlg.h](file://h\crossHole\CCrossHoleConfig3DMainDlg.h)
|
||||
- [MediumCrossHoleGeomative.h](file://h\MediumCrossHoleGeomative.h)
|
||||
</cite>
|
||||
|
||||
## 目录
|
||||
1. [引言](#引言)
|
||||
2. [项目结构](#项目结构)
|
||||
3. [核心组件](#核心组件)
|
||||
4. [架构概述](#架构概述)
|
||||
5. [详细组件分析](#详细组件分析)
|
||||
6. [依赖分析](#依赖分析)
|
||||
7. [性能考虑](#性能考虑)
|
||||
8. [故障排除指南](#故障排除指南)
|
||||
9. [结论](#结论)
|
||||
|
||||
## 引言
|
||||
|
||||
跨孔测量脚本是地质勘探中用于分析地下介质电性特征的重要工具。本文档全面文档化跨孔测量脚本的生成与管理过程,重点说明CCrossHoleConfig2DMainDlg和CCrossHoleConfig3DMainDlg对话框如何配置钻孔位置、电极间距和测量模式。文档详细解释MediumCrossHoleGeomative类的双孔/多孔电极布局算法和跨孔测量序列生成逻辑,描述跨孔脚本特有的XML结构元素,如钻孔坐标、电极深度和穿透测量路径。通过完整的工作流程示例,展示从钻孔配置到脚本验证的全过程,包括孔间距离校验和测量路径冲突检测。同时,文档分析跨孔脚本与普通2D/3D脚本的差异,以及在水文地质调查中的典型应用场景,并提供跨孔测量数据采集的特殊要求和优化建议。
|
||||
|
||||
## 项目结构
|
||||
|
||||
项目结构清晰地组织了跨孔测量相关的所有组件,主要分为核心对话框、几何配置、模拟功能和数据处理等模块。跨孔测量功能主要集中在`cpp\crossHole`目录下,包含2D和3D配置对话框的实现文件和头文件。`cpp\ProblemZone`目录包含了MediumCrossHoleGeomative类的实现,负责核心的测量序列生成算法。项目还包含数据库管理、用户界面和工具类等辅助模块,共同支持跨孔测量脚本的完整生命周期管理。
|
||||
|
||||
```mermaid
|
||||
graph TD
|
||||
subgraph "跨孔测量模块"
|
||||
A[CCrossHoleConfig2DMainDlg] --> B[COption2DGeometryDlg]
|
||||
A --> C[COption2DBoreholeDlg]
|
||||
A --> D[COption2DSurfaceDlg]
|
||||
A --> E[COption2DSettingDlg]
|
||||
A --> F[CCrosshole2dDrawingBoardDlg]
|
||||
G[CCrossHoleConfig3DMainDlg] --> H[COption3DGeometryDlg]
|
||||
G --> I[COption3DBoreholeDlg]
|
||||
G --> J[COption3DSurfaceDlg]
|
||||
G --> K[COption3DSettingDlg]
|
||||
G --> L[CCrosshole3dDrawingBoardDlg]
|
||||
M[MediumCrossHoleGeomative] --> N[CMedium]
|
||||
end
|
||||
subgraph "支持模块"
|
||||
O[数据库管理]
|
||||
P[用户界面]
|
||||
Q[工具类]
|
||||
end
|
||||
A --> O
|
||||
G --> O
|
||||
M --> O
|
||||
A --> P
|
||||
G --> P
|
||||
M --> Q
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [CCrossHoleConfig2DMainDlg.h](file://h\crossHole\CCrossHoleConfig2DMainDlg.h#L14-L64)
|
||||
- [CCrossHoleConfig3DMainDlg.h](file://h\crossHole\CCrossHoleConfig3DMainDlg.h#L14-L71)
|
||||
- [MediumCrossHoleGeomative.h](file://h\MediumCrossHoleGeomative.h#L13)
|
||||
|
||||
**章节来源**
|
||||
- [CCrossHoleConfig2DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig2DMainDlg.cpp#L1-L912)
|
||||
- [CCrossHoleConfig3DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig3DMainDlg.cpp#L1-L1300)
|
||||
|
||||
## 核心组件
|
||||
|
||||
跨孔测量脚本的核心组件包括两个主要对话框类CCrossHoleConfig2DMainDlg和CCrossHoleConfig3DMainDlg,以及负责测量序列生成的MediumCrossHoleGeomative类。CCrossHoleConfig2DMainDlg和CCrossHoleConfig3DMainDlg分别处理二维和三维跨孔测量的配置,提供用户界面来设置钻孔位置、电极间距和测量模式。这些对话框通过组合多个子对话框(如几何配置、钻孔配置、地面配置和参数设置)来实现完整的配置功能。MediumCrossHoleGeomative类继承自CMedium基类,实现了特定于跨孔测量的算法,包括K值计算、测量序列生成和电极位置计算。
|
||||
|
||||
**章节来源**
|
||||
- [CCrossHoleConfig2DMainDlg.h](file://h\crossHole\CCrossHoleConfig2DMainDlg.h#L14-L64)
|
||||
- [CCrossHoleConfig3DMainDlg.h](file://h\crossHole\CCrossHoleConfig3DMainDlg.h#L14-L71)
|
||||
- [MediumCrossHoleGeomative.h](file://h\MediumCrossHoleGeomative.h#L13)
|
||||
|
||||
## 架构概述
|
||||
|
||||
跨孔测量脚本的架构采用分层设计,将用户界面、业务逻辑和数据访问分离。用户界面层由CCrossHoleConfig2DMainDlg和CCrossHoleConfig3DMainDlg对话框组成,负责与用户交互并收集配置参数。业务逻辑层由MediumCrossHoleGeomative类实现,负责核心的测量序列生成算法和电极布局计算。数据访问层通过ADO数据库连接,将生成的测量脚本保存到数据库中。整个架构通过消息映射和事件驱动机制实现组件间的通信,确保了系统的可维护性和可扩展性。
|
||||
|
||||
```mermaid
|
||||
graph TD
|
||||
A[用户界面层] --> B[业务逻辑层]
|
||||
B --> C[数据访问层]
|
||||
subgraph "用户界面层"
|
||||
D[CCrossHoleConfig2DMainDlg]
|
||||
E[CCrossHoleConfig3DMainDlg]
|
||||
F[子配置对话框]
|
||||
end
|
||||
subgraph "业务逻辑层"
|
||||
G[MediumCrossHoleGeomative]
|
||||
H[测量序列生成]
|
||||
I[电极布局算法]
|
||||
J[K值计算]
|
||||
end
|
||||
subgraph "数据访问层"
|
||||
K[数据库连接]
|
||||
L[脚本保存]
|
||||
M[坐标信息存储]
|
||||
end
|
||||
D --> G
|
||||
E --> G
|
||||
G --> K
|
||||
H --> L
|
||||
I --> M
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [CCrossHoleConfig2DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig2DMainDlg.cpp#L1-L912)
|
||||
- [CCrossHoleConfig3DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig3DMainDlg.cpp#L1-L1300)
|
||||
- [MediumCrossHoleGeomative.cpp](file://cpp\ProblemZone\MediumCrossHoleGeomative.cpp#L1-L148)
|
||||
|
||||
## 详细组件分析
|
||||
|
||||
### CCrossHoleConfig2DMainDlg 分析
|
||||
|
||||
CCrossHoleConfig2DMainDlg类是二维跨孔测量配置的核心对话框,负责管理整个2D跨孔测量的配置流程。该类通过标签页(Tab Control)组织不同的配置界面,包括电极坐标、井下、地面和参数设置。用户可以通过加载Geomative文件来导入钻孔坐标,系统会自动解析文件中的坐标信息并显示在绘图板上。对话框提供了创建测量脚本的功能,根据用户配置的参数生成相应的测量序列,并将结果保存到数据库中。
|
||||
|
||||
#### 类图
|
||||
```mermaid
|
||||
classDiagram
|
||||
class CCrossHoleConfig2DMainDlg {
|
||||
+static GetInstance()
|
||||
+OnInitDialog()
|
||||
+OnTcnSelchangeTabArChange()
|
||||
+OnBnClickedBtnLoadGeometry()
|
||||
+OnBnClickedBtnCreate()
|
||||
+OnBnClickedBtnStartSimulation()
|
||||
+OnBnClickedBtnStopSimulation()
|
||||
+OnBnClickedBtnClose()
|
||||
+OnDestroy()
|
||||
+OnMsgCrossHoleMainWndBtn()
|
||||
+ChangeTabPage()
|
||||
#DoDataExchange()
|
||||
#CalcLValue()
|
||||
#TwoBoreholeGenerateScript()
|
||||
#SaveTestPointToDB()
|
||||
#GetUniSptXPos()
|
||||
-m_tabChange
|
||||
-m_pConnection
|
||||
-m_strScriptName
|
||||
-m_strTimeInterval
|
||||
-m_strOperator
|
||||
-m_strNote
|
||||
-m_uiEamount
|
||||
-m_uiCHamount
|
||||
-m_uiTPamount
|
||||
-m_rcRect
|
||||
-m_rcRectLoc
|
||||
-m_strPoleDistance
|
||||
-m_strPoleStep
|
||||
-m_vecAllBoreholeABMNInfo
|
||||
-m_mapDatabaseABMNInfo
|
||||
}
|
||||
CCrossHoleConfig2DMainDlg --> CTabCtrl : "使用"
|
||||
CCrossHoleConfig2DMainDlg --> _ConnectionPtr : "数据库连接"
|
||||
CCrossHoleConfig2DMainDlg --> CDialog : "继承"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [CCrossHoleConfig2DMainDlg.h](file://h\crossHole\CCrossHoleConfig2DMainDlg.h#L14-L64)
|
||||
- [CCrossHoleConfig2DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig2DMainDlg.cpp#L1-L912)
|
||||
|
||||
#### 创建测量脚本流程
|
||||
```mermaid
|
||||
sequenceDiagram
|
||||
participant 用户
|
||||
participant CCrossHoleConfig2DMainDlg
|
||||
participant COption2DSettingDlg
|
||||
participant COption2DGeometryDlg
|
||||
participant MediumCrossHoleGeomative
|
||||
participant 数据库
|
||||
用户->>CCrossHoleConfig2DMainDlg : 点击"创建"按钮
|
||||
CCrossHoleConfig2DMainDlg->>COption2DSettingDlg : 获取脚本名称、时间间隔等参数
|
||||
COption2DSettingDlg-->>CCrossHoleConfig2DMainDlg : 返回参数
|
||||
CCrossHoleConfig2DMainDlg->>COption2DGeometryDlg : 获取钻孔坐标信息
|
||||
COption2DGeometryDlg-->>CCrossHoleConfig2DMainDlg : 返回坐标数据
|
||||
CCrossHoleConfig2DMainDlg->>CCrossHoleConfig2DMainDlg : 调用TwoBoreholeGenerateScript生成测点
|
||||
CCrossHoleConfig2DMainDlg->>CCrossHoleConfig2DMainDlg : 调用CalcLValue计算L值
|
||||
CCrossHoleConfig2DMainDlg->>CCrossHoleConfig2DMainDlg : 生成所有测量点
|
||||
CCrossHoleConfig2DMainDlg->>CCrossHoleConfig2DMainDlg : 调用SaveTestPointToDB保存到数据库
|
||||
CCrossHoleConfig2DMainDlg->>数据库 : 插入scon表记录
|
||||
数据库-->>CCrossHoleConfig2DMainDlg : 返回成功
|
||||
CCrossHoleConfig2DMainDlg->>数据库 : 插入channel表记录
|
||||
数据库-->>CCrossHoleConfig2DMainDlg : 返回成功
|
||||
CCrossHoleConfig2DMainDlg->>数据库 : 插入script2d表记录
|
||||
数据库-->>CCrossHoleConfig2DMainDlg : 返回成功
|
||||
CCrossHoleConfig2DMainDlg->>数据库 : 插入TCoordinatesInfo表记录
|
||||
数据库-->>CCrossHoleConfig2DMainDlg : 返回成功
|
||||
CCrossHoleConfig2DMainDlg->>用户 : 显示创建成功消息
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [CCrossHoleConfig2DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig2DMainDlg.cpp#L734-L780)
|
||||
- [CCrossHoleConfig2DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig2DMainDlg.cpp#L547-L732)
|
||||
|
||||
**章节来源**
|
||||
- [CCrossHoleConfig2DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig2DMainDlg.cpp#L1-L912)
|
||||
|
||||
### CCrossHoleConfig3DMainDlg 分析
|
||||
|
||||
CCrossHoleConfig3DMainDlg类是三维跨孔测量配置的核心对话框,提供了比2D版本更复杂的配置功能。该类支持多方向测线配置,可以处理X、Y、Z方向以及它们的组合。与2D版本相比,3D版本增加了方向类型参数,允许用户指定测量的方向性。该类还实现了AM装置的测量序列生成,支持单孔和双孔的AM测量模式。
|
||||
|
||||
#### 类图
|
||||
```mermaid
|
||||
classDiagram
|
||||
class CCrossHoleConfig3DMainDlg {
|
||||
+static GetInstance()
|
||||
+OnInitDialog()
|
||||
+OnTcnSelchangeTabArChange()
|
||||
+OnBnClickedBtnLoadGeometry()
|
||||
+OnBnClickedBtnCreate()
|
||||
+OnBnClickedBtnStartSimulation()
|
||||
+OnBnClickedBtnStopSimulation()
|
||||
+OnBnClickedBtnClose()
|
||||
+OnDestroy()
|
||||
+OnMsgCrossHoleMainWndBtn()
|
||||
+ChangeTabPage()
|
||||
#DoDataExchange()
|
||||
#CalcLValue()
|
||||
#TwoBoreholeGenerateScript()
|
||||
#SaveTestPointToDB()
|
||||
#OneBoreHoleGenerateScriptAM()
|
||||
#TwoBoreHoleGenerateScriptAM()
|
||||
#GetUniSptXPos()
|
||||
-m_tabChange
|
||||
-m_pConnection
|
||||
-m_strScriptName
|
||||
-m_strTimeInterval
|
||||
-m_strOperator
|
||||
-m_strNote
|
||||
-m_uiEamount
|
||||
-m_uiCHamount
|
||||
-m_uiTPamount
|
||||
-m_rcRect
|
||||
-m_rcRectLoc
|
||||
-m_strPoleDistance
|
||||
-m_strPoleStep
|
||||
-m_vecAllBoreholeABMNInfo
|
||||
-m_iMediumType
|
||||
-m_mapDatabaseABMNInfo
|
||||
}
|
||||
CCrossHoleConfig3DMainDlg --> CTabCtrl : "使用"
|
||||
CCrossHoleConfig3DMainDlg --> _ConnectionPtr : "数据库连接"
|
||||
CCrossHoleConfig3DMainDlg --> CDialog : "继承"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [CCrossHoleConfig3DMainDlg.h](file://h\crossHole\CCrossHoleConfig3DMainDlg.h#L14-L71)
|
||||
- [CCrossHoleConfig3DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig3DMainDlg.cpp#L1-L1300)
|
||||
|
||||
#### 3D测量序列生成流程
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A[开始] --> B{获取钻孔数量}
|
||||
B --> |两个钻孔| C[调用TwoBoreholeGenerateScript]
|
||||
B --> |一个钻孔| D[调用OneBoreHoleGenerateScriptAM]
|
||||
C --> E[计算L值范围]
|
||||
E --> F[遍历第一个钻孔的电极]
|
||||
F --> G[遍历第二个钻孔的电极]
|
||||
G --> H[计算AM、BM、AN、BN距离]
|
||||
H --> I[计算K值]
|
||||
I --> J[创建测量点记录]
|
||||
J --> K{是否为多通道}
|
||||
K --> |是| L[按A、B、M排序插入]
|
||||
K --> |否| M[按顺序插入]
|
||||
L --> N[保存到数据库]
|
||||
M --> N
|
||||
D --> O[遍历同一钻孔的电极对]
|
||||
O --> P[计算AM距离]
|
||||
P --> Q[计算K值]
|
||||
Q --> R[创建AM测量点记录]
|
||||
R --> S[保存到数据库]
|
||||
N --> T[结束]
|
||||
S --> T
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [CCrossHoleConfig3DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig3DMainDlg.cpp#L703-L800)
|
||||
- [CCrossHoleConfig3DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig3DMainDlg.cpp#L500-L701)
|
||||
|
||||
**章节来源**
|
||||
- [CCrossHoleConfig3DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig3DMainDlg.cpp#L1-L1300)
|
||||
|
||||
### MediumCrossHoleGeomative 分析
|
||||
|
||||
MediumCrossHoleGeomative类是跨孔测量的核心算法实现,继承自CMedium基类。该类负责实现特定于跨孔测量的K值计算公式和测量序列生成逻辑。K值计算采用几何平均法,考虑了电极间的实际距离和间隔系数。测量序列生成遵循特定的模式:以电极中点为基准,C1P1距离作为层数,逐层向下移动,同时C2P2从最高点逐次向下移动,每次移动两个电极间距,直到C1P1到达底部。
|
||||
|
||||
#### 类图
|
||||
```mermaid
|
||||
classDiagram
|
||||
class CMediumCrossHoleGeomative {
|
||||
+CMediumCrossHoleGeomative(int iAR)
|
||||
+~CMediumCrossHoleGeomative()
|
||||
+CalculateCESptKVal(float fA, float fB, float fX, float fY)
|
||||
+GenerateSptRecElecVal(int iEAmount, int* pMaxLevel, int* pPtAmount, CPtrArray* pSptRecArray)
|
||||
+CalculateSptPtLoc(int iMul, CSptRecord* pSptRecord)
|
||||
+GenSptRecLevel(int iA, int iB, int iM, int iN)
|
||||
+GenSptRecPosInLevel(int iA, int iB, int iM, int iN)
|
||||
+GetMaxLevelByEAmount(int iEAmount)
|
||||
-m_fSeprate
|
||||
}
|
||||
CMediumCrossHoleGeomative --> CMedium : "继承"
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [MediumCrossHoleGeomative.h](file://h\MediumCrossHoleGeomative.h#L13)
|
||||
- [MediumCrossHoleGeomative.cpp](file://cpp\ProblemZone\MediumCrossHoleGeomative.cpp#L1-L148)
|
||||
|
||||
#### 测量序列生成算法
|
||||
```mermaid
|
||||
flowchart TD
|
||||
A[开始] --> B[初始化层数iLayer=0]
|
||||
B --> C[层数加1]
|
||||
C --> D[设置A位置为中点]
|
||||
D --> E[计算M位置=A-层数]
|
||||
E --> F{M位置<1?}
|
||||
F --> |是| G[结束]
|
||||
F --> |否| H[设置B位置为中点+1]
|
||||
H --> I[计算N位置=B+层数]
|
||||
I --> J{N位置>电极总数?}
|
||||
J --> |是| K[移动A和M向下2个间距]
|
||||
J --> |否| L[创建测量点记录]
|
||||
L --> M[移动B和N向下2个间距]
|
||||
M --> I
|
||||
K --> N{A位置<2?}
|
||||
N --> |是| G
|
||||
N --> |否| H
|
||||
G --> O[结束]
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [MediumCrossHoleGeomative.cpp](file://cpp\ProblemZone\MediumCrossHoleGeomative.cpp#L47-L112)
|
||||
|
||||
**章节来源**
|
||||
- [MediumCrossHoleGeomative.cpp](file://cpp\ProblemZone\MediumCrossHoleGeomative.cpp#L1-L148)
|
||||
|
||||
## 依赖分析
|
||||
|
||||
跨孔测量脚本系统具有清晰的依赖关系,主要依赖于数据库访问组件、几何计算工具和用户界面框架。核心依赖包括ADO数据库连接用于数据持久化,标准模板库(STL)用于数据结构管理,以及MFC框架用于用户界面实现。系统内部组件间通过明确的接口进行通信,如CCrossHoleConfig2DMainDlg和CCrossHoleConfig3DMainDlg通过GetInstance()方法提供单例访问,确保配置数据的一致性。MediumCrossHoleGeomative类与配置对话框之间通过标准数据结构(STBoreHolePoints、STDatabaseABMNInfo等)进行数据交换,降低了组件间的耦合度。
|
||||
|
||||
```mermaid
|
||||
graph TD
|
||||
A[CCrossHoleConfig2DMainDlg] --> B[数据库访问]
|
||||
A --> C[STL容器]
|
||||
A --> D[MFC框架]
|
||||
A --> E[COption2DGeometryDlg]
|
||||
A --> F[COption2DBoreholeDlg]
|
||||
A --> G[COption2DSurfaceDlg]
|
||||
A --> H[COption2DSettingDlg]
|
||||
A --> I[CCrosshole2dDrawingBoardDlg]
|
||||
J[CCrossHoleConfig3DMainDlg] --> B
|
||||
J --> C
|
||||
J --> D
|
||||
J --> K[COption3DGeometryDlg]
|
||||
J --> L[COption3DBoreholeDlg]
|
||||
J --> M[COption3DSurfaceDlg]
|
||||
J --> N[COption3DSettingDlg]
|
||||
J --> O[CCrosshole3dDrawingBoardDlg]
|
||||
P[MediumCrossHoleGeomative] --> B
|
||||
P --> C
|
||||
P --> Q[CMedium基类]
|
||||
A --> P
|
||||
J --> P
|
||||
```
|
||||
|
||||
**图表来源**
|
||||
- [CCrossHoleConfig2DMainDlg.h](file://h\crossHole\CCrossHoleConfig2DMainDlg.h#L14-L64)
|
||||
- [CCrossHoleConfig3DMainDlg.h](file://h\crossHole\CCrossHoleConfig3DMainDlg.h#L14-L71)
|
||||
- [MediumCrossHoleGeomative.h](file://h\MediumCrossHoleGeomative.h#L13)
|
||||
|
||||
**章节来源**
|
||||
- [CCrossHoleConfig2DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig2DMainDlg.cpp#L1-L912)
|
||||
- [CCrossHoleConfig3DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig3DMainDlg.cpp#L1-L1300)
|
||||
- [MediumCrossHoleGeomative.cpp](file://cpp\ProblemZone\MediumCrossHoleGeomative.cpp#L1-L148)
|
||||
|
||||
## 性能考虑
|
||||
|
||||
跨孔测量脚本的性能主要受测量点数量和数据库操作效率的影响。系统采用批量数据库插入操作,减少了与数据库的交互次数,提高了数据保存效率。在测量序列生成过程中,算法的时间复杂度为O(n²),其中n为电极数量,对于大规模电极阵列可能成为性能瓶颈。建议在实际应用中合理控制电极数量和测量密度,避免生成过多的测量点。此外,系统使用内存中的数据结构暂存测量点信息,然后再一次性写入数据库,这种设计平衡了内存使用和I/O性能。
|
||||
|
||||
## 故障排除指南
|
||||
|
||||
在使用跨孔测量脚本时,可能会遇到以下常见问题:
|
||||
|
||||
1. **脚本创建失败**:检查脚本名称是否为空,确保输入了有效的脚本名称。
|
||||
2. **电极坐标加载失败**:确认Geomative文件格式正确,坐标数据以逗号分隔。
|
||||
3. **K值计算异常**:检查AM距离和间隔系数是否为零,这些值不能为零。
|
||||
4. **数据库保存失败**:确保数据库连接正常,检查是否有重复的脚本名称。
|
||||
5. **测量点数量异常**:验证钻孔电极数量是否符合要求,确保有足够的电极进行测量。
|
||||
|
||||
**章节来源**
|
||||
- [CCrossHoleConfig2DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig2DMainDlg.cpp#L755-L763)
|
||||
- [CCrossHoleConfig2DMainDlg.cpp](file://cpp\crossHole\CCrossHoleConfig2DMainDlg.cpp#L564-L577)
|
||||
- [MediumCrossHoleGeomative.cpp](file://cpp\ProblemZone\MediumCrossHoleGeomative.cpp#L30-L43)
|
||||
|
||||
## 结论
|
||||
|
||||
跨孔测量脚本系统提供了一套完整的解决方案,用于生成和管理跨孔电法测量的配置。通过CCrossHoleConfig2DMainDlg和CCrossHoleConfig3DMainDlg对话框,用户可以方便地配置钻孔位置、电极间距和测量模式。MediumCrossHoleGeomative类实现了核心的测量序列生成算法,确保了测量数据的科学性和有效性。系统采用模块化设计,具有良好的可扩展性和可维护性。在水文地质调查中,该系统能够有效支持地下介质的精细探测,为工程决策提供可靠的数据支持。未来可以进一步优化算法性能,增加更多的测量模式支持,提升用户体验。
|
||||
Reference in New Issue
Block a user