Экспорт данных в Microsoft Excel с помощью приложения C # windowsforms - PullRequest
1 голос
/ 09 марта 2010

я получаю исключение при попытке экспортировать данные в Excel .... исключение составляет

COMException: исключение из HRESULT: 0x800A03EC.

Как мне решить эту ошибку? Как мне найти решение? Подскажите решение этой проблемы ...

Заранее спасибо ...

Мой код:

         {
        oxl = new Excel.Application();
        oxl.Visible = true;
        oxl.DisplayAlerts = false;


        wbook = oxl.Workbooks.Add(Missing.Value);

        wsheet = (Excel.Worksheet)wbook.ActiveSheet;
        wsheet.Name = "Customers"; 



        DataTable dt = InstituteTypeDetail();

        int rowCount = 1;
        foreach (DataRow dr in dt.Rows)
        {
            rowCount += 1;
            for (int i = 1; i < dt.Columns.Count + 1; i++)
            {
                // Add the header the first time through
                if (rowCount == 2)
                {
                    wsheet.Cells[1, i] = dt.Columns[i - 1].ColumnName;
                }
                wsheet.Cells[rowCount, i] = dr[i - 1].ToString();
            }
        }

        range = wsheet.get_Range(wsheet.Cells[1, 1],
                      wsheet.Cells[rowCount, dt.Columns.Count]);//In this place i got the exception
        range.EntireColumn.AutoFit();


        wsheet = null;
        range = null;

}

что я сделал не так? Как решить эту исключительную ситуацию ... Кто-нибудь, пожалуйста, скажите мне ...

Ответы [ 4 ]

1 голос
/ 09 марта 2010

Следующий пример кода прекрасно работает для меня. Можешь попробовать? Изменили ваш образец. Кроме того, всегда полезно выпускать ссылки на все com-объекты в конце.

Application oxl = null;
        try
        {
            oxl = new Application( );
            oxl.Visible = true;
            oxl.DisplayAlerts = false;

            string fileName = @"D:\one.xls";
            object missing = Missing.Value;
            Workbook wbook = oxl.Workbooks.Open( fileName, missing, missing, missing, missing, missing,missing,missing,missing,missing,missing,missing,missing,missing,missing );

            Worksheet wsheet = ( Worksheet )wbook.ActiveSheet;
            wsheet.Name = "Customers";


            System.Data.DataTable dt = new System.Data.DataTable( "test" );
            dt.Columns.Add( "col1" );
            dt.Columns.Add( "col2" );
            dt.Columns.Add( "col3" );

            dt.Rows.Add( new object[ ] { "one", "one", "one" } );
            dt.Rows.Add( new object[ ] { "two", "two", "two" } );
            dt.Rows.Add( new object[ ] { "three", "three", "three" } );


            for ( int i = 1 ; i <=  dt.Columns.Count ; i++ )
            {
                wsheet.Cells[ 1, i ] = dt.Columns[ i - 1 ].ColumnName;
            }

            for ( int j = 1 ; j <= dt.Rows.Count ; j++ )
            {
                for ( int k = 0 ; k <  dt.Columns.Count ; k++ )
                {
                    DataRow dr = dt.Rows[ k ];
                    wsheet.Cells[ j +1, k+1 ] = dr[ k ].ToString( );
                }
            }

            Range range = wsheet.get_Range( wsheet.Cells[ 1, 1 ],
                          wsheet.Cells[ dt.Rows.Count + 1, dt.Columns.Count ] );//In this place i got the exception
            range.EntireColumn.AutoFit( );

            wbook.Save( );

            wsheet = null;
            range = null;


        }
        finally
        {
            oxl.Quit( );
            System.Runtime.InteropServices.Marshal.ReleaseComObject( oxl );
            oxl = null;
        }
1 голос
/ 09 марта 2010

Ваш rowCount на самом деле правильный в тот момент, когда вы получаете ошибку? Вы начинаете его с 1, но затем сразу увеличиваете его - поэтому, когда вы проверяете строку 1 в цикле foreach, rowCount фактически равно 2.

Я думаю, что ваш rowCount должен быть инициализирован в 0 (ноль). Тогда проверка строки заголовка должна искать if (rowCount == 1).

0 голосов
/ 09 марта 2010

SpreadsheetGear for .NET позволит вам работать с книгами Excel из .NET без проблем, связанных с Excel COM Interop. SpreadsheetGear также быстрее, чем COM Interop, особенно при циклическом переключении нескольких ячеек, как кажется в вашем коде.

Вот код, который делает то же самое, что и ваш код с использованием SpreadsheetGear API:

using System;
using SpreadsheetGear;

namespace Program
{
    class Program
    {
        static void Main(string[] args)
        {
            string fileName = @"D:\one.xls";
            IWorkbook wbook = SpreadsheetGear.Factory.GetWorkbook(fileName);
            IWorksheet wsheet = wbook.ActiveWorksheet;
            wsheet.Name = "Customers";
            System.Data.DataTable dt = new System.Data.DataTable("test");
            dt.Columns.Add("col1");
            dt.Columns.Add("col2");
            dt.Columns.Add("col3");
            dt.Rows.Add(new object[] { "one", "one", "one" });
            dt.Rows.Add(new object[] { "two", "two", "two" });
            dt.Rows.Add(new object[] { "three", "three", "three" });
            wsheet.Cells[0, 0, dt.Rows.Count - 1, dt.Columns.Count - 1].CopyFromDataTable(dt, SpreadsheetGear.Data.SetDataFlags.None);
            wsheet.UsedRange.EntireColumn.AutoFit();
            wbook.Save();
        }
    }
}

Вы можете посмотреть живые образцы здесь и загрузить бесплатную пробную версию здесь , если хотите попробовать сами.

Отказ от ответственности: я владею SpreadsheetGear LLC

0 голосов
/ 09 марта 2010

get_Range ожидает имя ячейки в виде строки, то есть что-то вроде «A1», «B25» и т. Д. Вы можете попробовать заменить строку следующим кодом:

range = wsheet.Cells(1, 1);
range = range.Resize(rowCount, dt.Columns.Count);
...