Перечисление почтового ящика Outlook с использованием Visual Studio - PullRequest
6 голосов
/ 17 сентября 2009

У меня есть следующий класс, который предназначен для возврата строки темы всех писем в папке

Это Visual Studio 2008 против Outlook 2007, работающий в Windows 7 64bit

using System;
using System.Windows;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Office.Interop.Outlook;

namespace MarketingEmails
{
public class MailUtils
{

  public static string[] processMailMessages(object outlookFolder)
    // Given an Outlook folder as an object reference, return
    // a list of all the email subjects in that folder
    {

        // Set a local object from the folder passed in
        Folder theMailFolder = (Folder)outlookFolder;

        string[] listSubjects = new string[theMailFolder.Items.Count];
        int itemCount = 0;

        // Now process the MAIL items
        foreach (MailItem oItem in theMailFolder.Items)
        {
            listSubjects[itemCount] = oItem.Subject.ToString();
            itemCount++;
        }
        return listSubjects;
    }

}

}

Однако код выдает исключение ниже:

Невозможно преобразовать COM-объект типа «System .__ ComObject» в интерфейсный тип «Microsoft.Office.Interop.Outlook.MailItem». Эта операция завершилась неудачно, поскольку вызов QueryInterface для компонента COM для интерфейса с IID '{00063034-0000-0000-C000-000000000046}' не выполнен из-за следующей ошибки: такой интерфейс не поддерживается (Исключение из HRESULT: 0x80004002 (E_NOINTERFACE)) .

Я понимаю, что произошла ошибка, поскольку она пытается обработать элемент ReportItem в выбранном почтовом ящике.

Что я не понимаю, так это , почему пытается обработать элементы, не относящиеся к Почте, когда я указал:

foreach (MailItem oItem in theMailFolder.Items)

Если бы я хотел, чтобы он обрабатывал записи элемента отчета в почтовом ящике, я бы написал:

foreach (ReportItem oItem in theMailFolder.Items) 

Мне бы очень хотелось выяснить, является ли это ошибкой или это просто мое неправильное понимание

С уважением, Найджел Айнско

Ответы [ 2 ]

8 голосов
/ 17 сентября 2009

Причина в том, что элементы Collection содержат экземпляры MailItem и ReportItem. Указание MailItem слева не фильтрует список, оно просто указывает, какой тип вы ожидаете увидеть в списке.

Что вам нужно сделать, так это отфильтровать нужный вам тип

foreach ( MailItem oItem in theMailFolder.Items.OfType<MailItem>()) {
  ..
}

Метод OfType будет возвращать только те значения в коллекции, которые соответствуют этому конкретному типу.

2 голосов
/ 17 сентября 2009

Объявление типа в цикле foreach не фильтрует по типу - вместо этого оно выдает исключение, как вы заметили.

Это происходит потому, что в C # 1.0 была введена foreach, которая не поддерживала дженерики. Следовательно, у компилятора нет способа узнать, какой тип возвращается IEnumerator. (Это все еще верно, если коллекция не реализует IEnumerable<T>). Nitpickers : я знаю, что даже в C # 1 можно написать строго типизированный перечислитель (как это делает List<T>); подавляющее большинство - нет.

Тогда, если вы случайно указали неправильный тип в foreach, вы бы предпочли, чтобы он генерировал исключение, а не таинственным образом ничего не делал.

Как объяснял JaredPar, вы должны использовать метод OfType.

...