You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

VBA邮件发送宏报错:执行时提示‘元素已移动或删除’

解决VBA发送邮件时“元素已移动或删除”的错误

问题根源

你碰到的这个报错其实很好理解:整个循环里你只创建了一个objMail邮件对象,第一次调用.Send之后,Outlook已经完成了这个邮件的发送流程,并且自动释放了该对象的资源。后续循环再试图修改这个已经被“处理掉”的对象属性,自然就会触发“元素已移动或删除”的错误。

修复方案(推荐)

把创建邮件对象的代码放到For循环内部,让每次循环都生成一个全新的邮件对象,这样就不会出现复用已释放对象的问题了。修改后的代码如下:

Sub EmailSend()
    Dim objOutlook As Object
    Dim objMail As Object
    Dim i As Integer
    
    '只初始化一次Outlook应用,避免重复创建浪费资源
    Set objOutlook = CreateObject("Outlook.Application")
    
    For i = 1 To 10
        '每次循环新建一个独立的邮件对象
        Set objMail = objOutlook.CreateItem(0)
        
        With objMail
            .To = ThisWorkbook.Sheets("Test").Range("A" & i).Value
            .Subject = "hi"
            '处理B列可能为空的情况,避免邮件内容出现突兀的空白
            .Body = "Hi " & IIf(ThisWorkbook.Sheets("Test").Range("B" & i).Value <> "", ThisWorkbook.Sheets("Test").Range("B" & i).Value & vbCrLf, "") & _
                    ThisWorkbook.Sheets("links").Range("G1").Value
            .Send
        End With
        
        '手动释放当前邮件对象的资源
        Set objMail = Nothing
    Next i
    
    '最后释放Outlook应用的资源
    Set objOutlook = Nothing
End Sub

额外优化建议

  • 不要固定循环到10行,可以改成动态判断A列最后一行有内容的单元格,避免发送空邮件:
    Dim lastRow As Integer
    lastRow = ThisWorkbook.Sheets("Test").Cells(ThisWorkbook.Sheets("Test").Rows.Count, "A").End(xlUp).Row
    For i = 1 To lastRow
    
  • 如果你的邮件不需要个性化内容,也可以考虑把所有收件人放到BCC字段一次性发送,但如果每个邮件需要对应B列的个性化称呼,还是建议每次新建邮件对象。

内容的提问来源于stack exchange,提问作者Jj Blevins

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.13 08:21:59