Найти конкретное значение ячейки и затем удалить строку Excel C # - PullRequest
0 голосов
/ 20 февраля 2019

Я работаю над программой, которая читает файл Excel и ищет определенное значение на листе, скажем, sheetname = "sheet3".

После этого программа будет искать в определенном столбце,скажем, столбец «D», и ищет значение данных во всем столбце.Если значение данных существует, вся строка, содержащая это значение данных, будет удалена / скрыта.

В настоящее время мне удалось получить значение данных из файла Excel столбца, но я не смог продолжить работу с кодом.Я пытался около 3 дней, но безрезультатно.Буду признателен за любую помощь!

Это код, который я пробовал в настоящее время:

using System.IO;
using System.Linq;
using System;
using System.Text.RegularExpressions;
using DocumentFormat.OpenXml.Packaging;
using DocumentFormat.OpenXml.Spreadsheet;
using System.Collections.Generic;

namespace Test
{
    class Program
    {
        static void Main(string[] args)
        {
            const string fileName =
            @"D:\test.xlsx";

            // Retrieve the value in cell D2.
            string value = GetCellValue(fileName, "Sheet3", "D2");

        }
        // Retrieve the value of a cell, given a file name, sheet name, 
        // and address name.
        public static string GetCellValue(string fileName,
            string sheetName,
            string addressName)
        {
            string value = null;

            // 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("sheetName");
                }

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

                // Use its Worksheet property to get a reference to the cell 
                // whose address matches the address you supplied.
                Cell theCell = wsPart.Worksheet.Descendants<Cell>().
                  Where(c => c.CellReference == addressName).FirstOrDefault();

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

                    // If the cell represents an integer number, you are done. 
                    // For dates, this code returns the serialized value that 
                    // represents the date. The code handles strings and 
                    // Booleans individually. For shared strings, the code 
                    // looks up the corresponding value in the shared string 
                    // table. For Booleans, the code converts the value into 
                    // the words TRUE or FALSE.
                    if (theCell.DataType != null)
                    {
                        switch (theCell.DataType.Value)
                        {
                            case CellValues.SharedString:

                                // For shared strings, look up the value in the
                                // shared strings table.
                                var stringTable =
                                    wbPart.GetPartsOfType<SharedStringTablePart>()
                                    .FirstOrDefault();

                                // If the shared string table is missing, something 
                                // is wrong. Return the index that is in
                                // the cell. Otherwise, look up the correct text in 
                                // the table.
                                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;
        }
    }
}

PS Я пробовал только OpenXML, поскольку сервер, на котором я собираюсь работать, не имеетлюбое установленное Microsoft Excel или любое другое программное обеспечение.Следовательно, я не могу использовать Microsoft.Office.Interop.Excel для выполнения этой задачи.Буду признателен за любую помощь в этом вопросе, пожалуйста.Спасибо.

1 Ответ

0 голосов
/ 20 февраля 2019

Я рекомендую вам использовать библиотеку NPOI вместо OpenXML.NPOI - это библиотека с открытым исходным кодом для чтения и записи документов Microsoft Office без необходимости установки какого-либо офисного программного обеспечения.Это порт .NET библиотеки Java POI.Вы можете найти много примеров в Интернете.

Следующая консольная программа C # использует NPOI для выполнения того, что вы просили.

using System;
using System.IO;

using NPOI.SS.UserModel;
using NPOI.XSSF.UserModel;

public class Program
{
    public static void Main(string[] args)
    {
        const string FileName = @"d:\test.xlsx";
        IWorkbook workbook = OpenWorkBook(FileName);

        ISheet sheet = workbook.GetSheet("Sheet3");
        HideRows(sheet);
        DeleteRows(sheet);

        SaveWorkBook(workbook, FileName);

        Console.WriteLine("Done. Press any key");
        Console.ReadKey();
    }

    private static IWorkbook OpenWorkBook(string workBookName)
    {
        using (FileStream file = new FileStream(workBookName, FileMode.Open, FileAccess.Read))
        {
            return new XSSFWorkbook(file);
        }
    }

    private static void HideRows(ISheet sheet)
    {

        for (int rowIndex = 0; rowIndex <= sheet.LastRowNum; rowIndex++)
        {
            IRow row = sheet.GetRow(rowIndex);
            if (row == null) continue; // Completely unused row returns null
            ICell cell = row.GetCell(3); // 0-based column index: 0=column A, 1=B, etc
            if (cell != null && cell.StringCellValue == "HideMe")
            {
                row.Hidden = true;
            }
        }
    }

    private static void DeleteRows(ISheet sheet)
    {
        // When deleting we must iterate rows in reverse sequence
        for (int rowIndex = sheet.LastRowNum; rowIndex >= 0; rowIndex--)
        {
            IRow row = sheet.GetRow(rowIndex);
            if (row == null) continue;
            ICell cell = row.GetCell(3);
            if (cell != null && cell.StringCellValue == "DeleteMe")
            {
                // use ShiftRows to actually delete the row:
                sheet.ShiftRows(row.RowNum+1, sheet.LastRowNum, -1);
            }
        }
    }

    private static void SaveWorkBook(IWorkbook workbook, string workBookName)
    {
        string newFileName = Path.ChangeExtension(workBookName, "new.xlsx");
        using (FileStream file = new FileStream(newFileName, FileMode.Create, FileAccess.Write))
        {
            workbook.Write(file);
        }

        string backupFileName = Path.ChangeExtension(workBookName, "bak.xlsx");
        File.Replace(newFileName, workBookName, backupFileName);
    }
}
...