使用Excel Interop对行中使用的单元格进行计数
我想在工作表中的每一行中获取最后使用的单元格的索引。 我可以得到最后使用整个工作表的列,但我有每个行中有不同的使用单元格的表,如下所示:
我试过这个:
var excelApp = new Excel.Application(); var workBook = excelApp.Workbooks.Open(excelFilePath); Excel._Worksheet worksheet = workBook.Worksheets[worksheetName]; int rowsCount = worksheet.UsedRange.Rows.Count; for (int i = 1; i <= rowsCount; i++) { Excel.Range range = worksheet.Rows[i]; int lastColumn = range.Columns.Count; Console.WriteLine(lastColumn); }
我期待输出:
3 5 2 7
但实际产出是:
16384 16384 16384 16384
我使用Excel Interop库。 任何build议,将不胜感激。 谢谢!
你可以使用这样的东西:
var usedRange = worksheet.UsedRange; int startRow = usedRange.Row; int endRow = startRow + usedRange.Rows.Count - 1; int startColumn = usedRange.Column; int endColumn = startColumn + usedRange.Columns.Count - 1; for (int row = startRow; row <= endRow; row++) { Excel.Range lastCell = worksheet.Cells[row, endColumn]; if (lastCell.Value2 == null) lastCell = lastCell.End[Excel.XlDirection.xlToLeft]; var lastColumn = lastCell.Column; Console.WriteLine($"{row}: {lastColumn}"); }
基本上诀窍是获得最后一个单元格,如果它是空的,使用Range.End
属性(或方法?)与XlDirection.xlToLeft
(空的检查是必要的,因为似乎从起始单元格被排除在End
调用) 。
下面显示了获取一行最后使用的单元格的逻辑。 它不会循环遍历所有的行,但是你应该能够将它用于迭代器。
using System; using Excel = Microsoft.Office.Interop.Excel; using System.Runtime.InteropServices; using System.IO; namespace Example { public class ExcelUsed { /// <summary> /// Get last used column for a row /// </summary> /// <param name="fileName">Excel file to read</param> /// <param name="sheetName">Sheet to work on</param> /// <param name="row">Row in sheet to get last used column</param> /// <returns></returns> public int LastColumnForRow(string fileName, string sheetName, int row) { int lastColumn = -1; if (File.Exists(fileName)) { Excel.Application xlApp = null; Excel.Workbooks xlWorkBooks = null; Excel.Workbook xlWorkBook = null; Excel.Worksheet xlWorkSheet = null; Excel.Sheets xlWorkSheets = null; xlApp = new Excel.Application(); xlApp.DisplayAlerts = false; xlWorkBooks = xlApp.Workbooks; xlWorkBook = xlWorkBooks.Open(fileName); xlApp.Visible = false; xlWorkSheets = xlWorkBook.Sheets; for (int x = 1; x <= xlWorkSheets.Count; x++) { xlWorkSheet = (Excel.Worksheet)xlWorkSheets[x]; if (xlWorkSheet.Name == sheetName) { Excel.Range xlCells = null; xlCells = xlWorkSheet.Cells; Excel.Range workRange = xlCells.SpecialCells(Excel.XlCellType.xlCellTypeLastCell); Excel.Range xlColumns = xlWorkSheet.Columns; int count = xlColumns.Count; Marshal.FinalReleaseComObject(xlColumns); xlColumns = null; Excel.Range xlLastRange = (Excel.Range)xlWorkSheet.Cells[row, count]; Excel.Range xlDirRange = xlLastRange.End[Excel.XlDirection.xlToLeft]; Marshal.FinalReleaseComObject(xlLastRange); xlLastRange = null; lastColumn = xlDirRange.Column; Marshal.FinalReleaseComObject(xlDirRange); xlDirRange = null; Marshal.FinalReleaseComObject(workRange); workRange = null; Marshal.FinalReleaseComObject(xlCells); xlCells = null; break; } Marshal.FinalReleaseComObject(xlWorkSheet); xlWorkSheet = null; } xlWorkBook.Close(); xlApp.UserControl = true; xlApp.Quit(); Release(xlWorkSheets); Release(xlWorkSheet); Release(xlWorkBook); Release(xlWorkBooks); Release(xlApp); return lastColumn; } else { throw new Exception("'" + fileName + "' not found."); } } /// <summary> /// /// </summary> public void CallGarbageCollector() { GC.Collect(); GC.WaitForPendingFinalizers(); } /// <summary> /// Method to release object used in Excel operations /// </summary> /// <param name="sender"></param> private void Release(object sender) { try { if (sender != null) { Marshal.ReleaseComObject(sender); sender = null; } } catch (Exception) { sender = null; } } } }
例
int row = 1; int results = eu.LastColumnForRow(fileName, sheetName,row); MessageBox.Show($"Row {row}: {results}");
试试看https://code.msdn.microsoft.com/Excel-get-last-row-and-fe764cfc