質問

C#を使用して、Excel 2003のにリスト(すなわち、List<List<T>>)の一覧をエクスポートするための直接的な方法はありますか?

私は大きなテキストファイルを解析すると、Excelにエクスポートしています。一度に一つのセルを書くことはあまりにも多くのオーバーヘッドを作成します。私は、行または列の数を指定する心配する必要はないようにList<T>を使用することを選択します。

現在、私は、ファイルの終わりまで待って、その後、2次元配列に私List<List<object>>の内容を置きます。次いで、アレイはExcel.Rangeオブジェクトの値として設定することができます。それは動作しますが、私はどこに。A1からワークシートに行または列の数を気にすることなく、リストの私のリストを取り、それをダンプすることができるはずのように思える。

ここで私は交換または上改善したいコードの抜粋です。

object oOpt = System.Reflection.Missing.Value; //for optional arguments
Excel.Application oXL = new Excel.Application();
Excel.Workbooks oWBs = oXL.Workbooks;
Excel._Workbook oWB = oWBs.Add(Excel.XlWBATemplate.xlWBATWorksheet);
Excel._Worksheet oSheet = (Excel._Worksheet)oWB.ActiveSheet;

int numberOfRows = outputRows.Count;
int numberOfColumns = int.MinValue;

//outputRows is a List<List<object>>
foreach (List<object> outputColumns in outputRows)
{
        if (numberOfColumns < outputColumns.Count)
        { numberOfColumns = outputColumns.Count; }
}

Excel.Range oRng = oSheet.get_Range("A1", oSheet.Cells[numberOfRows,numberOfColumns]);

object[,] outputArray = new object[numberOfRows,numberOfColumns];

for (int row = 0; row < numberOfRows; row++)
{
        for (int col = 0; col < outputRows[row].Count; col++)
        {
                outputArray[row, col] = outputRows[row][col];
        }
}

oRng.set_Value(oOpt, outputArray);

oXL.Visible = true;
oXL.UserControl = true;

これは動作しますが、私はむしろちょうどエクセルのために配列を作成するの中間ステップを持つよりも、Excelに直接リストを使用すると思います。任意のアイデア?

役に立ちましたか?

解決

戦略的に、あなたは正しくそれをやっています。ジョーが言うように、ワンショットの値のアレイ全体を通過させることによってではなくセルを一つずつループによってセル値の割り当てを実行する超高速である。

ExcelはCOMベースであるので、.NET相互運用を介してExcelで動作します。相互運用は、残念ながら、ジェネリック医薬品の無知であるので、あなたはそれをリストなどを渡すことはできません。 2次元配列は、実際に行くための唯一の方法である。

と、それはもう少し管理しやすくするようにコードをクリーンアップするには、いくつかの方法があります。ここではいくつかの考えがあります:

(1)あなたは、.NET 3.0を使用している場合、あなたからあなたのコードを短くするためにLINQを使用することができます:

int numberOfColumns = int.MinValue;

foreach (List<object> outputColumns in outputRows)
{
        if (numberOfColumns < outputColumns.Count)
        { numberOfColumns = outputColumns.Count; }
}

一行に:

int numberOfColumns = outputRows.Max(list => list.Count);

(2)_Worksheet又は_Workbookインターフェイスを使用しないでください。代わりにWorksheetまたはWorkbookを利用します。議論のためにここを参照してください: Excelの相互運用機能:?_Worksheetまたはワークシート

(3)C#でRange.Resizeよう介してくるRange.get_Resize方法を使用することを検討。これはしかしトスアップである - 私は実際に方法のように、あなたの範囲のサイズを設定しています。しかし、それは私はあなたが知りたいかもしれないと思った何か。たとえば、ここにあなたの行:

Excel.Range oRng = oSheet.get_Range("A1", oSheet.Cells[numberOfRows,numberOfColumns]);

に変更してもらえます:

Excel.Range oRng = 
    oSheet.get_Range("A1", Type.Missing)
        .get_Resize(numberOfRows, numberOfColumns);

(4)あなたはApplication.UserControltrueを設定する必要はありません。ユーザーにExcelが見えるようにするだけでは十分です。 UserControlプロパティは、あなたはそれがないと思う何をしていません。あなたがするかどうかを制御したい場合は(ここではのヘルプファイルを参照してください)あなたのユーザーをロックアウトしたい場合、ユーザーは、ワークシートの保護をutilzeなければならない、またはあなたがをできたのセットApplication.Interactive = falseをExcelを制御したりすることはできません。 (まれに良いアイデア。)しかし、あなたは、ユーザーがExcelを使用できるようにしたい場合は、単にそれを可視化することは十分にあります。

全体的に見て、心の中でこれらを、私はあなたのコードはこのような何かを見ることができると思います

object oOpt = System.Reflection.Missing.Value; //for optional arguments
Excel.Application oXL = new Excel.Application();
Excel.Workbooks oWBs = oXL.Workbooks;
Excel.Workbook oWB = oWBs.Add(Excel.XlWBATemplate.xlWBATWorksheet);
Excel.Worksheet oSheet = (Excel.Worksheet)oWB.ActiveSheet;

//outputRows is a List<List<object>>
int numberOfRows = outputRows.Count;
int numberOfColumns = outputRows.Max(list => list.Count);

Excel.Range oRng = 
    oSheet.get_Range("A1", oOpt)
        .get_Resize(numberOfRows, numberOfColumns);

object[,] outputArray = new object[numberOfRows, numberOfColumns];

for (int row = 0; row < numberOfRows; row++)
{
    for (int col = 0; col < outputRows[row].Count; col++)
    {
        outputArray[row, col] = outputRows[row][col];
    }
}

oRng.set_Value(oOpt, outputArray);

oXL.Visible = true;

この情報がお役に立てば幸い...

マイク

他のヒント

これはの多くのの速い時間で細胞1を更新するよりも、Excelへの2次元配列を渡すことです。

、リストのリストからの値を持つオブジェクトの2次元配列を作成し、あなたの配列の次元にExcelの範囲を宣言し直すし、その後range.set_Valueを呼び出して、あなたの2次元配列を渡します。

List<"classname"> getreport = cs.getcompletionreport();

var getreported = getreport .Select(c => new { demographic = c.rName);

このことができます期待しています

cs.getcompletionreport()がどこにある参照クラスファイルは、アプリケーションのためのビジネスレイヤである

将来サーチャーのために:あなたがobject[,](2次元)を貼り付ける必要があり秀でるためにリストをコピーする場合は事実です。

:念のために誰かがあなたが二dimesion 1でちょうど1 for loopを実行できる1次元のリストを持っています
List<DateTime> listDate; //I'm filling it with data from datagridview
...
object[,] outDate = new object[listDate.Count, 1];
for(int row = 0; row < listDate.Count; row++)
{
    outDate[row, 0] = listDate[row];
}
scroll top