【问题标题】:Openxml cell returns InnerText not the actual valueOpenxml 单元格返回 InnerText 而不是实际值
【发布时间】:2014-12-29 19:31:25
【问题描述】:

我正在开发一个可重复使用的代码来读取 excel 单元格值。我的代码如下:

private string ReadCellValue(WorksheetPart worksheetPart, string cellAddress)
        {
            string value = null;

            Cell theCell = worksheetPart.Worksheet.Descendants<Cell>().
                  Where(c => c.CellReference == cellAddress).FirstOrDefault();

            // If the cell does not exist, return an empty string.
            if (theCell != null)
            {
                value = theCell.InnerText;

                if (theCell.DataType != null)
                {
                    switch (theCell.DataType.Value)
                    {
                        case CellValues.SharedString:

                            var stringTable =
                                worksheetPart.GetPartsOfType<SharedStringTablePart>()
                                .FirstOrDefault();

                            if (stringTable != null)
                            {
                                value =
                                    stringTable.SharedStringTable
                                    .ElementAt(int.Parse(value)).InnerText;
                            }
                            break;

                        case CellValues.Boolean:
                            switch (value)
                            {
                                case "0":
                                    value = "FALSE";
                                    break;
                                default:
                                    value = "TRUE";
                                    break;
                            }
                            break;
                    }
                }
            }
            return value;
        }

我从下面的代码块调用这个方法:

public string IsPackingListValid()
        {           

            // Open the spreadsheet document for read-only access.
            using (SpreadsheetDocument document = SpreadsheetDocument.Open(fileName, false))
            {
                // Retrieve a reference to the workbook part.
                WorkbookPart wbPart = document.WorkbookPart;

                // Find the sheet with the supplied name, and then use that 
                // Sheet object to retrieve a reference to the first worksheet.
                Sheet theSheet = wbPart.Workbook.Descendants<Sheet>().
                  Where(s => s.Name == sheetName).FirstOrDefault();

                // Throw an exception if there is no sheet.
                if (theSheet == null)
                {
                    throw new ArgumentException("Could not find work sheet: " + sheetName);
                }

                // Retrieve a reference to the worksheet part.
                WorksheetPart worksheetPart = (WorksheetPart)(wbPart.GetPartById(theSheet.Id));

                return ReadCellValue(WorksheetPart worksheetPart, "B2")
            }   
}

该方法不返回某些单元格的实际值。对于某些单元格,它返回值,对于某些单元格,它返回内部文本。 我调试并检查了

var stringTable = worksheetPart.GetPartsOfType<SharedStringTablePart>()
                               .FirstOrDefault();

以上代码返回null。

我找不到为什么它对某些单元有效而对某些单元无效。任何有助于解决此问题。

【问题讨论】:

    标签: excel openxml openxml-sdk


    【解决方案1】:

    根据我的理解(至少对于我检查过的文档来说确实如此),SharedStringTablePart 是 WorkbookPart 而不是 WorksheetPart 的后代。因此,修复代码的方法是在 IsPackingListValid() 方法中从 wbPart 获取共享字符串列表:

    List<SharedStringItem> sharedStrings = wbPart.SharedStringTablePart.SharedStringTable.ChildElements.OfType<SharedStringItem>().ToList();
    

    然后将其作为附加参数传递给 ReadCellValue 方法:

    return ReadCellValue(worksheetPart, "B2", sharedStrings);
    

    之后,您可以在 ReadCellValue() 方法中获取您的共享字符串的实际值:

    value = cell.InnerText;
    int sharedStringIndex;
    
    if (int.TryParse(cell.InnerText, out sharedStringIndex) && sharedStrings.Count > sharedStringIndex
        && sharedStrings[sharedStringIndex].Text != null)
    {
        value = sharedStrings[sharedStringIndex].Text.Text;
    }
    

    【讨论】:

    • 嗨,很好的答案!并非所有单元格都被标记为 SharedString DataType,因此您需要额外检查:
    【解决方案2】:

    还需要对 SharedString 数据类型进行额外检查(http://msdn.microsoft.com/en-us/library/office/ff921204(v=office.14).aspx 了解更多信息):

        private static string ReadCellValue(WorksheetPart worksheetPart, string cellAddress, List<SharedStringItem> sharedStrings)
        {
            try
            {
                string value = null;
                var cell = worksheetPart.Worksheet.Descendants<Cell>().Where(c => c.CellReference == cellAddress).FirstOrDefault();
                value = cell.InnerText;
                if (cell.DataType != null && cell.DataType.Value == CellValues.SharedString)
                {
                    int sharedStringIndex;
                    if (int.TryParse(cell.InnerText, out sharedStringIndex) && sharedStrings.Count > sharedStringIndex && sharedStrings[sharedStringIndex].Text != null)
                    {
                        value = sharedStrings[sharedStringIndex].Text.Text;
                    }
                }
                return value;
            }
            catch (Exception ex) { throw ex; }
        }
    

    【讨论】:

      猜你喜欢
      • 2011-07-04
      • 2021-10-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-08-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多