读取Excel文件时的异常处理,C#

时间:2016-11-16 19:49:50

标签: c# excel exception-handling

我对C#编码还不熟悉,最近我读到最好使用Try Catch而不是if/else来处理与文件I / O相关的问题。我还在其他主题中读到,应该在循环中避免使用try catch块,因为它们会显着降低性能。

就我而言,我正在使用for循环读取多个(通常超过1,000个)excel文件。目前,我正在使用if / else if处理真正的基本异常(即文件是否存在),但我正在考虑实现try catch,原因我上面解释过。

这是我的一些代码

public void ReadFile(string path)
        {
            Excel.Application xlApp;
            Excel.Workbooks xlBooks;
            Excel.Workbook xlBook;
            Excel.Worksheet xlSheet;

            xlApp = new Excel.Application();
            xlBooks = xlApp.Workbooks;
            xlBook = xlBooks.Open(path);
            xlSheet = xlBook.Sheets[1];

            int rowCount = FindLastRow(xlSheet);
            int colCount = FindLastColumn(xlSheet);

            string header = "";

            string glNum = Path.GetFileNameWithoutExtension(path).Trim();
            for (int row = 1; row <= rowCount; row++)
            {
                bool processDone = false;
                string curationInfo = "";
                List<string> data = new List<string>();
                // If empty line, skip
                if (IsEmpty(xlSheet, row, colCount)) continue;
                // If header line, capture
                if (IsHeader(xlSheet, row, colCount) != "")
                {
                    header = IsHeader(xlSheet, row, colCount);
                    continue;
                }
                // If coloured line, capture
                if (IsColoured(xlSheet, row, colCount))
                {
                    curationInfo = ConstructCurationInfo(xlSheet, row, colCount);
                    data.Add(curationInfo);
                    // If last row, end
                    if (row == rowCount) processDone = true;
                    while (!processDone)
                    {
                        // If last row
                        if (row == rowCount)
                        {
                            // If last row is empty, one section is done
                            if (IsEmpty(xlSheet, row, colCount)) processDone = true;
                            // If last row is header, one section is done
                            else if (IsHeader(xlSheet, row, colCount) != "") processDone = true;
                            // Every other case
                            else
                            {
                                // if coloured, capture
                                if (IsColoured(xlSheet, row, colCount))
                                {
                                    string newCurationInfo = ConstructCurationInfo(xlSheet, row, colCount);
                                    data.Add(newCurationInfo);
                                }
                                processDone = true;
                            }
                        }
                        // If not last row
                        else
                        {
                            int nextRow = row + 1;
                            // If next row is last row, end
                            if (nextRow == rowCount) processDone = true;
                            // If next row is empty, one section is done
                            if (IsEmpty(xlSheet, nextRow, colCount)) processDone = true;
                            // If next row is header, one section is done
                            else if (IsHeader(xlSheet, nextRow, colCount) != "") processDone = true;
                            // Every other case
                            else
                            {
                                // if coloured, capture
                                if (IsColoured(xlSheet, nextRow, colCount))
                                {
                                    string newCurationInfo = ConstructCurationInfo(xlSheet, nextRow, colCount);
                                    data.Add(newCurationInfo);
                                }
                                row++;
                            }
                        }
                    }
                }
                if (processDone && data.Count != 0)
                {
                    Curation cur = new Curation(header, data, glNum);
                    curationList.Add(cur);
                }
            }
            // Terminate background Excel Workers
            xlBook.Close(false, Missing.Value, Missing.Value);
            xlBooks.Close();
            xlApp.Quit();
            xlApp.DisplayAlerts = false;
            Marshal.ReleaseComObject(xlSheet);
            Marshal.ReleaseComObject(xlBook);
            Marshal.ReleaseComObject(xlBooks);
            Marshal.ReleaseComObject(xlApp);
            GC.WaitForPendingFinalizers();
            GC.Collect();
        }

使用ReadFile()方法的Form方法

// Background workers
        private void mergeNew_bgw_DoWork(object sender, DoWorkEventArgs e)
        {
            string input_path = db_input_tb.Text;
            string output_dir_path = output_tb.Text;
            // Status message to be reported to the UI
            string status = "";

            status = "Collecting files to be read.....";
            mergeNew_bgw.ReportProgress(0, status);
            List<string> excelPaths = GetPathToExcel(input_path);

            if (IsEmpty(excelPaths))
            {
                status = "No File to be Processed!";
                mergeNew_bgw.ReportProgress(0, status);
                fileToProcess = false;
            }
            // If not empty list, process
            else
            {
                ExcelInfo info = new ExcelInfo();
                bool doesExist = false;
                string path = "";
                int row = 1;
                for (int i = 0; i < excelPaths.Count; i++)
                {
                    status = "Processing....." + (i + 1).ToString() + "/" + excelPaths.Count.ToString();
                    mergeNew_bgw.ReportProgress(0, status);
                    info.ReadFile(excelPaths[i]);
                    // If last file, write excel file
                    if (i + 1 == excelPaths.Count)
                    {
                        status = "Writing Complete Merged File";
                        mergeNew_bgw.ReportProgress(0, status);
                        info.WriteNew(ref doesExist, ref row, ref path, output_dir_path);
                        info.Clear();
                    }
                    else if ((i + 1) % cutoff == 0)
                    {
                        status = "Writing Partial Merged File";
                        mergeNew_bgw.ReportProgress(0, status);
                        info.WriteNew(ref doesExist, ref row, ref path, output_dir_path);
                        info.Clear();
                    }
                }
            }
        }

我应该在mergeNew_bgw_DoWork方法中的for循环中实现try catch块吗?

for (int i = 0; i < excelPaths.Count; i++)
            {
                status = "Processing....." + (i + 1).ToString() + "/" + excelPaths.Count.ToString();
                mergeNew_bgw.ReportProgress(0, status);
                try
                {
                    info.ReadFile(excelPaths[i]);
                }
                catch(Exception e)
                {
                    throw new Exception(e.ToString());
                }
                finally
                {
                    // If last file, write excel file
                    if (i + 1 == excelPaths.Count)
                    {
                        status = "Writing Complete Merged File";
                        mergeNew_bgw.ReportProgress(0, status);
                        info.WriteNew(ref doesExist, ref row, ref path, output_dir_path);
                        info.Clear();
                    }
                    else if ((i + 1) % cutoff == 0)
                    {
                        status = "Writing Partial Merged File";
                        mergeNew_bgw.ReportProgress(0, status);
                        info.WriteNew(ref doesExist, ref row, ref path, output_dir_path);
                        info.Clear();
                    }
                }                   
            }

感谢您的帮助!

修改

显然,表现不会像其中一条评论所指出的那样改变。但是,我应该在哪里插入try catch块以获得有意义的错误消息? ReadFile()方法很大,所以我认为将整个方法放在try块中可能不会给用户带来意义错误消息。在ReadFile()方法中插入try catch更好吗?

0 个答案:

没有答案