MFC 输出EXCEL文件时卡在m_lpDispatch->Release()

第一次输出是正常的,第二次时就卡在这里了 ,单步执行时,m_lpDispatch->Release()显示无源可用 如果当时电脑的输入法是qq拼音时,会显示未加载qqPINYIN.PDB

img

img

我认为问题可能是您没有正确释放Excel对象的COM接口导致的,在使用完Excel对象后,使用m_lpDispatch->Release()正确释放COM接口。
还有就是输入法程序的问题,一是冲突,二是关闭输入法或者换个输入法。
再或者使用其他方法来输出Excel文件,例如使用第三方库或COM组件。

单步到释放后跳出这个错误

img

换个excel库

release之前需要释放Excel的编辑焦点,使excel处于非编辑状态

以下答案由GPT-3.5大模型与博主波罗歌共同编写:
这个问题可能与COM对象的引用计数有关,当第一次输出时,COM对象被正确释放了,但第二次输出时,可能有某些对象没有正确释放导致引用计数无法降为0,从而导致程序卡在了m_lpDispatch->Release()这里。

可以在程序中加入对COM对象的引用计数进行监控和调试,来找出是哪个对象没有正确释放。以下是一个简单的例子,演示了如何调用COM对象并进行引用计数的监控:

// 定义一个计数宏,用于输出引用计数
#define OutputRefCount(pObj) \
    { \
        ULONG nRef = pObj->AddRef() - 1; \
        printf("AddRef() returns %d, total ref count is %d\n", nRef + 1, nRef + 2); \
        nRef = pObj->Release(); \
        printf("Release() returns %d, total ref count is %d\n", nRef, nRef + 1); \
    }

// 创建Excel对象
_ApplicationPtr pExcelApp;
HRESULT hr = pExcelApp.CreateInstance("Excel.Application");
if (SUCCEEDED(hr))
{
    // 输出引用计数
    OutputRefCount(pExcelApp);
    
    // ...
    
    // 释放COM对象
    pExcelApp.Release();
    
    // 输出引用计数
    OutputRefCount(pExcelApp);
}

当代码执行到OutputRefCount宏时,会依次输出COM对象的引用计数,以检查是否有对象没有正确释放。在释放COM对象后,再次输出引用计数,确保COM对象已被正确释放。

关于输入法的问题,可能会影响到COM对象的加载。可以尝试先关闭QQ输入法,然后再运行程序,看是否能够正常输出EXCEL文件。如果确实是因为输入法的问题导致的加载失败,可以尝试更新或重新安装输入法,或者选择其他输入法来解决这个问题。

以下是一个简单的MFC输出EXCEL文件的例子,希望可以帮助您解决问题:

void CMyDlg::OnButtonExportExcel()
{
    // 创建Excel对象
    _ApplicationPtr pExcelApp;
    HRESULT hr = pExcelApp.CreateInstance("Excel.Application");
    if (SUCCEEDED(hr))
    {
        pExcelApp->Visible = VARIANT_TRUE;

        // 创建一个新的工作簿
        _WorkbookPtr pWorkbook = pExcelApp->Workbooks->Add(XlWBATemplate::xlWBATWorksheet);

        // 获取工作簿的第一个工作表
        _WorksheetPtr pWorksheet = pWorkbook->Worksheets->Item[1];

        // 写入数据
        pWorksheet->Cells[1][1] = "姓名";
        pWorksheet->Cells[1][2] = "年龄";
        pWorksheet->Cells[2][1] = "张三";
        pWorksheet->Cells[2][2] = 18;
        pWorksheet->Cells[3][1] = "李四";
        pWorksheet->Cells[3][2] = 20;

        // 保存文件
        CString strFilePath = "C:\\sample.xlsx";
        VARIANT vtFilePath;
        vtFilePath.vt = VT_BSTR;
        vtFilePath.bstrVal = strFilePath.AllocSysString();
        pWorkbook->SaveAs(vtFilePath);

        // 释放COM对象
        pWorkbook.Release();
        pWorksheet.Release();
        pExcelApp.Quit();
        pExcelApp.Release();
    }
}

如果我的回答解决了您的问题,请采纳!