6.8 Dispose

dispose

csharp 复制代码
public void Dispose()
{
    lock (_disposeLock)
    {
        if (_isDisposed) return;
        _isDisposed = true;
    }

    // 释放定时器
    try { _statusTimer?.Dispose(); } catch { }

    Task runningTask = null;
    // 取消扫描任务
    lock (_scanLock)
    {
        try { _cts?.Cancel(); } catch { }
        runningTask = _runningScanTask;
    }

    // 等待任务完成/超时强制停轴
    if (runningTask != null)
    {
        try
        {
            var completed = Task.WhenAny(runningTask, Task.Delay(1000)).Result;
            if (!runningTask.IsCompleted)
            {
                try { lock (_scanLock) { _scanAxis?.NormalStop(); } } catch { }
                try { WeakReferenceMessenger.Default.Send(new LogMessage("Dispose:运行任务未在超时内完成,已强制轴停止")); } catch { }
            }
            try { runningTask.Wait(); } catch { }
        }
        catch (Exception ex)
        {
            try { WeakReferenceMessenger.Default.Send(new LogMessage($"Dispose后台等待异常:{ex.Message}")); } catch { }
        }
    }

    // 销毁CTS,清空任务
    lock (_scanLock)
    {
        try { _cts?.Dispose(); } catch { }
        _cts = null;
        _runningScanTask = null;
    }

    // 关闭总线硬件
    try { _ecatMaster?.CloseMaster(); } catch { }

    // ===================== 【你是对的!官方标准顺序】 =====================
    // 1. 先注销自己:杜绝生命周期竞态,自己不再接收任何消息
    try { WeakReferenceMessenger.Default.UnregisterAll(this); } catch { }
    // 2. 再发停止消息:仅通知其他模块(视觉/主界面),安全无并发问题
    try { WeakReferenceMessenger.Default.Send(new StopScanMessage()); } catch { }
    // ====================================================================

    GC.SuppressFinalize(this);
}

核心安全规则

先 UnregisterAll(this)

立刻把自己从消息订阅列表删除

→ 自己绝对不会再接收任何消息

→ 杜绝「VM 正在销毁,还收到消息」导致的崩溃 / 空指针 / 竞态

再 Send(StopScanMessage)

只给其他独立模块发通知

→ 完全不影响发送

→ 其他模块正常接收、正常停止

→ 自己已经注销,不会重复处理,完美安全

bash 复制代码
11400@▒▒ MINGW64 ~
$ cd D:\vsprogram\WpfApp6
bash: cd: D:vsprogramWpfApp6: No such file or directory

11400@▒▒ MINGW64 ~
$ cd D:/vsprogram/WpfApp6

11400@ MINGW64 /d/vsprogram/WpfApp6 (master)
$ git checkout feature/bug
M       WpfApp6/ViewModel/AxisEcatVM.cs
M       WpfApp6/ViewModel/MainShellVM.cs
M       WpfApp6/ViewModel/XrayImageVM.cs
Switched to branch 'feature/bug'

11400@ MINGW64 /d/vsprogram/WpfApp6 (feature/bug)
$ git add .

11400@ MINGW64 /d/vsprogram/WpfApp6 (feature/bug)
$ git commit -m "dispose"
[feature/bug 735b69e] dispose
 3 files changed, 54 insertions(+), 24 deletions(-)

11400@ MINGW64 /d/vsprogram/WpfApp6 (feature/bug)
$ git checkout master
Switched to branch 'master'

11400@ MINGW64 /d/vsprogram/WpfApp6 (master)
$ git merge feature/bug
Updating b6fa6ec..735b69e
Fast-forward
 WpfApp6/ViewModel/AxisEcatVM.cs  | 53 +++++++++++++++++++++++++++++++---------
 WpfApp6/ViewModel/MainShellVM.cs |  5 ++--
 WpfApp6/ViewModel/XrayImageVM.cs | 20 +++++++--------
 3 files changed, 54 insertions(+), 24 deletions(-)

11400@ MINGW64 /d/vsprogram/WpfApp6 (master)
$ gir checkout -b feature/mysql
bash: gir: command not found

11400@ MINGW64 /d/vsprogram/WpfApp6 (master)
$ git checkout -b feature/mysql
Switched to a new branch 'feature/mysql'

11400@ MINGW64 /d/vsprogram/WpfApp6 (feature/mysql)
$ git add .

11400@ MINGW64 /d/vsprogram/WpfApp6 (feature/mysql)
$ git commit -m "mysql"
[feature/mysql 6b68b66] mysql
 4 files changed, 62 insertions(+)
 create mode 100644 WpfApp6/Data/MySqlDetectionRepository.cs
 create mode 100644 WpfApp6/Models/DetectionResult.cs
 create mode 100644 WpfApp6/Models/IDetectionRepository.cs

11400@ MINGW64 /d/vsprogram/WpfApp6 (feature/mysql)
$ git checkout master
Switched to branch 'master'

11400@ MINGW64 /d/vsprogram/WpfApp6 (master)
$ git merge feature/mysql
Updating 735b69e..6b68b66
Fast-forward
 WpfApp6/Data/MySqlDetectionRepository.cs | 24 ++++++++++++++++++++++++
 WpfApp6/Models/DetectionResult.cs        | 22 ++++++++++++++++++++++
 WpfApp6/Models/IDetectionRepository.cs   | 13 +++++++++++++
 WpfApp6/WpfApp6.csproj                   |  3 +++
 4 files changed, 62 insertions(+)
 create mode 100644 WpfApp6/Data/MySqlDetectionRepository.cs
 create mode 100644 WpfApp6/Models/DetectionResult.cs
 create mode 100644 WpfApp6/Models/IDetectionRepository.cs

11400@ MINGW64 /d/vsprogram/WpfApp6 (master)
$
相关推荐
JohnnyDeng942 天前
【Android】RecyclerView性能优化与缓存机制:从卡顿到丝滑的完整指南
android·性能优化·kotlin·mvvm
故渊at3 天前
系列三:组件化与模块化进阶 | 第11篇 组件化项目规范与问题根治:依赖、资源、Manifest 与混淆的全链路管控
android·架构·mvvm·模块化·组件化
czhc11400756633 天前
6.5 注入
mvvm·运控
小满Autumn4 天前
MVVM Light 架构笔记:定位器、命令、消息与 IoC 实践
笔记·学习·架构·c#·上位机·mvvm
小满Autumn4 天前
CommunityToolkit.Mvvm 架构笔记:现代 MVVM、源生成器与工程化实践
笔记·架构·c#·.net·wpf·mvvm
杊页4 天前
系列二:MVVM 深度实战与项目重构 | 第6篇 DataBinding & ViewBinding 实战落地:告别 findViewById 的“刀耕火种”
架构·mvvm
小满Autumn5 天前
依赖注入设计模式速查手册
开发语言·c#·wpf·mvvm·依赖注入
小满Autumn5 天前
WPF 依赖属性速查手册
笔记·c#·wpf·上位机·mvvm
czhc11400756638 天前
531 扫描模式
mvvm·运控