Microsoft.Interop.Excel 无法读取单元格值

Microsoft.Interop.Excel can't read cell value

我写了一个小方法,它将给我 excel 中的 table 的 headers:

private List<string> GetCurrentHeaders(int headerRow, Excel.Worksheet ws)
{
    //List where specific values get saved if they exist
    List<string> headers = new List<string>();
    //List of all the values that need to exist as headers
    var headerlist = columnName.GetAllValues();

    for (int i = 0; i < headerlist.Count; i++)
    {
        //GetData() is a Method that outputs the Data from a cell.
        //headerRow is defining one row under the row I actually need, therefore -1 )
        string header = GetData(i + 1, headerRow - 1, ws);

        if (headerlist.Contains(header) && !headers.Contains(header))
        {
            headers.Add(header);
        }
    }

    return headers;
}

现在我得到一个 Excel-table,其中我需要的第一个值在单元格 A11(或第 11 行第 1 列)中。

当我在string header = GetData(i + 1, headerRow - 1, ws);之后设置断点,其中i+1 = 1headerRow - 1 = 11,可以看到他读到的值是空的,不是这样的

GetData-Method 只做一件简单的事情:

public string GetData(int row, int col, Excel.Worksheet ws)
{
    string val = "";

    val = Convert.ToString(ws.Cells[row, col].Value) != null 
        ? ws.Cells[row, col].Value.ToString() :  "";

    val = val.Replace("\n", " ");

    return val;
}

我不明白为什么这不能让我得到我需要的价值,而它也适用于所有其他 excel table。 excel 本身与其他的没有什么不同。它的文件扩展名为 .xls,数据与其他 tables 等

中的布局相同

需要几个步骤才能做到这一点。您需要知道 table 的尺寸才能知道 headers 的位置。您的方法有两种了解这一点的方法:1) 将 table Range 传递给该方法,或 2) 给出 table 中单元格的坐标(通常是 top-left 单元格)并信任 CurrentRegion 属性 为您完成这项工作。最可靠的方法是第一种方法,因为您将明确告诉方法在哪里查看,但它需要消费者找出并不总是直截了当的地址。 CurrentRegion 方法也可以正常工作,但请注意,如果您的 table 范围内有一个空列,它只会寻址到该空列。说了这么多,你可以有以下内容:

List<string> GetHeaders(Worksheet worksheet, int row, int column)
    {
        Range currentRegion = worksheet.Cells[row, column].CurrentRegion;
        Range headersRow = currentRegion.Rows[1];
        var headers = headersRow
            .Cast<Range>() // We cast so we can use LINQ
            .Select(c => c.Text is DBNull ? null : c.Text as string) //The null value of c.Text is not null but DBNull
            .ToList();
        return headers;
    }

然后你可以简单地测试一下你是否遗漏了headers。以下代码假定 ActiveCell 是 table Range 中的一个单元格,但您可以轻松更改它以解决特定单元格。

List<string> GetMissingHeaders(List<string> expectedHeaders)
{
    var worksheet = App.ActiveSheet; //App is your Excel application
    Range activeCell = worksheet.ActiveCell;
    var headers = GetHeaders(worksheet, activeCell.Row, activeCell.Column);
    return expectedHeaders.Where(h => headers.Any(i => i == h) == false).ToList();
}