在以往的博客中我们介绍过两次Word文档的读写:https://blog.csdn.net/a13407142317/category_9736046.html?spm=1001.2014.3001.5482
本次我将介绍一下在Word中增加表格,并对表格进行合并单元格的操作的记录
1. Docx操作Word文档,增加表并合并单元格
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Aspose.Words;
using Xceed.Words.NET;
namespace DocInsertTableDemo
{
public class DocXHelper
{
public static void Output(string strFilePath, int TableRowCount)
{
try
{
Console.WriteLine("---------------------------------------------");
Console.WriteLine($"-------------DocX:::输出{TableRowCount}-------------------");
Console.WriteLine("---------------------------------------------");
DocX document = DocX.Create(strFilePath);
int index = 0;
Stopwatch sw = new Stopwatch();
sw.Start();
TimeSpan ts2;
var insertTable = document.InsertTable(TableRowCount * 2, 16);
int rowIndex = 0;
for (int i = 0; i < TableRowCount; i++)
{
if (index % 500 == 0)
{
sw.Stop();
ts2 = sw.Elapsed;
Console.WriteLine($"{index}:耗时:【{ts2.TotalSeconds} s】");
sw.Start();
}
index++;
rowIndex = i * 2;
if (i != 0)
{
//合并单元格
for (int columnIndex = 0; columnIndex < 9; columnIndex++)
{
insertTable.MergeCellsInColumn(columnIndex, rowIndex - 1, rowIndex);
}
}
for (int j = 9; j < 16; j++)
{
insertTable.MergeCellsInColumn(j, rowIndex, rowIndex + 1);
}
}
sw.Stop();
ts2 = sw.Elapsed;
Console.WriteLine($"{index}:耗时:【{ts2.TotalSeconds} s】");
document.Save();
Console.WriteLine("---------------------------------------------");
Console.WriteLine("-------------结果输出完成-------------------");
Console.WriteLine("---------------------------------------------");
Console.WriteLine("");
Console.WriteLine("");
Console.WriteLine("");
}
catch (Exception exception)
{
Console.WriteLine(exception);
}
}
}
}
上述代码中我们使用DocX的var insertTable = document.InsertTable(TableRowCount * 2, 16);
插入了TableRowCount*2行数据,每行为16列
在后续的代码中我们将前9列合并(第一行和最后一行的前9列不合并),后7列合并。
测试代码如下:
public string DocFilePath
{
get
{
int i = 0;
string strFilePath = System.IO.Path.Combine(txtOutputFoder.Text,string.Format($"输出文件_{i}.docx"));
while (System.IO.File.Exists(strFilePath))
{
strFilePath = System.IO.Path.Combine(txtOutputFoder.Text, string.Format($"输出文件_{++i}.docx"));
}
return strFilePath;
}
}
public int RowCount
{
get { return Convert.ToInt32(txtRowCount.Text); }
}
private void btnDocxOutput_Click(object sender, EventArgs e)
{
DocXHelper.Output(DocFilePath, 1000);
DocXHelper.Output(DocFilePath, 2000);
DocXHelper.Output(DocFilePath, 4000);
}
从下面我可以发现:
- 随着行数的增加每500行需要操作的时长在不断的增加
4.97676 s
、12.0056664 s
、32.253473 s
---------------------------------------------
-------------DocX:::输出1000-------------------
---------------------------------------------
===================================================================
Thank you for using Xceed's DocX library.
Please note that this software is used for non-commercial use only.
To obtain a commercial license, please visit www.xceed.com.
===================================================================
0:耗时:【0.1417625 s】
500:耗时:【4.97676 s】
1000:耗时:【9.6776909 s】
---------------------------------------------
-------------结果输出完成-------------------
---------------------------------------------
---------------------------------------------
-------------DocX:::输出2000-------------------
---------------------------------------------
0:耗时:【0.2603558 s】
500:耗时:【12.0056664 s】
1000:耗时:【23.719281 s】
1500:耗时:【35.553722 s】
2000:耗时:【47.2550256 s】
---------------------------------------------
-------------结果输出完成-------------------
---------------------------------------------
---------------------------------------------
-------------DocX:::输出4000-------------------
---------------------------------------------
0:耗时:【0.6488167 s】
500:耗时:【32.253473 s】
1000:耗时:【63.7707256 s】
1500:耗时:【95.3657504 s】
2000:耗时:【126.9970141 s】
2500:耗时:【158.8907938 s】
3000:耗时:【191.1327904 s】
3500:耗时:【222.4014558 s】
4000:耗时:【253.8296853 s】
---------------------------------------------
-------------结果输出完成-------------------
---------------------------------------------
以下为代码效率运行分析图:
2. AsposeWord操作Word文档,增加表并合并单元格
2.1. 操作全新的Word文档
private void btnAsposeOutput_Click(object sender, EventArgs e)
{
AsposeWordHelper.Output(DocFilePath, 1000);
AsposeWordHelper.Output(DocFilePath, 2000);
AsposeWordHelper.Output(DocFilePath, 9000);
AsposeWordHelper.Output(DocFilePath, 18000);
}
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Aspose.Words;
using Aspose.Words.Saving;
using Aspose.Words.Tables;
namespace DocInsertTableDemo
{
public class AsposeWordHelper
{
public static void Output(string strFilePath, int TableRowCount)
{
try
{
Console.WriteLine("---------------------------------------------");
Console.WriteLine($"-------------AsposeWord:::输出{TableRowCount}-------------------");
Console.WriteLine("---------------------------------------------");
Document document = new Document();
int index = 0;
Stopwatch sw = new Stopwatch();
sw.Start();
TimeSpan ts2;
DocumentBuilder builder = new DocumentBuilder(document);
// We call this method to start building the table.
Table table=builder.StartTable();
for (int i = 0; i < TableRowCount*2; i++)
{
for (int j = 0; j < 16; j++)
{
builder.InsertCell();
}
builder.EndRow();
}
builder.EndTable();
int rowIndex = 0;
for (int i = 0; i < TableRowCount; i++)
{
if (index % 500 == 0)
{
sw.Stop();
ts2 = sw.Elapsed;
Console.WriteLine($"{index}:耗时:【{ts2.TotalSeconds} s】");
sw.Start();
}
index++;
rowIndex = i * 2;
if (i != 0)
{
//合并单元格
for (int columnIndex = 0; columnIndex < 9; columnIndex++)
{
builder.MoveToCell(0, rowIndex - 1, columnIndex, 0);
builder.CellFormat.VerticalMerge = CellMerge.First;
builder.MoveToCell(0, rowIndex , columnIndex, 0);
builder.CellFormat.VerticalMerge = CellMerge.Previous;
}
builder.MoveToCell(0, rowIndex+1, 0, 0);
builder.Write("100");
}
for (int j = 9; j < 16; j++)
{
builder.MoveToCell(0, rowIndex, j, 0);
builder.CellFormat.VerticalMerge = CellMerge.First;
builder.MoveToCell(0, rowIndex+1, j, 0);
builder.CellFormat.VerticalMerge = CellMerge.Previous;
}
}
sw.Stop();
ts2 = sw.Elapsed;
Console.WriteLine($"{index}:耗时:【{ts2.TotalSeconds} s】");
document.Save(strFilePath);
Console.WriteLine("---------------------------------------------");
Console.WriteLine("-------------结果输出完成-------------------");
Console.WriteLine("---------------------------------------------");
Console.WriteLine("");
Console.WriteLine("");
Console.WriteLine("");
}
catch (Exception exception)
{
Console.WriteLine(exception);
}
}
}
}
---------------------------------------------
-------------AsposeWord:::输出1000-------------------
---------------------------------------------
0:耗时:【0.1399572 s】
500:耗时:【0.3866026 s】
1000:耗时:【0.796063 s】
---------------------------------------------
-------------结果输出完成-------------------
---------------------------------------------
---------------------------------------------
-------------AsposeWord:::输出2000-------------------
---------------------------------------------
0:耗时:【0.2204396 s】
500:耗时:【0.3891188 s】
1000:耗时:【0.7901694 s】
1500:耗时:【1.6458934 s】
2000:耗时:【2.7186411 s】
---------------------------------------------
-------------结果输出完成-------------------
---------------------------------------------
---------------------------------------------
-------------AsposeWord:::输出9000-------------------
---------------------------------------------
0:耗时:【1.2782646 s】
500:耗时:【1.4050466 s】
1000:耗时:【1.8153078 s】
1500:耗时:【2.67353 s】
2000:耗时:【3.7907685 s】
2500:耗时:【5.1684503 s】
3000:耗时:【6.8645515 s】
3500:耗时:【8.9671585 s】
4000:耗时:【11.5212391 s】
4500:耗时:【14.589067 s】
5000:耗时:【18.15755 s】
5500:耗时:【22.3808788 s】
6000:耗时:【26.9534147 s】
6500:耗时:【32.0948572 s】
7000:耗时:【37.6063883 s】
7500:耗时:【43.5952214 s】
8000:耗时:【50.253982 s】
8500:耗时:【57.4801275 s】
9000:耗时:【65.4050901 s】
---------------------------------------------
-------------结果输出完成-------------------
---------------------------------------------
---------------------------------------------
-------------AsposeWord:::输出18000-------------------
---------------------------------------------
0:耗时:【2.6580146 s】
500:耗时:【2.7642107 s】
1000:耗时:【3.2102907 s】
1500:耗时:【4.0396196 s】
2000:耗时:【5.1747061 s】
2500:耗时:【6.6398438 s】
3000:耗时:【8.383739 s】
3500:耗时:【10.6106222 s】
4000:耗时:【13.3069511 s】
4500:耗时:【16.4165112 s】
5000:耗时:【19.9795006 s】
5500:耗时:【24.0851934 s】
6000:耗时:【28.6030566 s】
6500:耗时:【33.6398424 s】
7000:耗时:【39.2927184 s】
7500:耗时:【45.5628425 s】
8000:耗时:【52.6116441 s】
8500:耗时:【60.1593497 s】
9000:耗时:【68.3821347 s】
9500:耗时:【77.4236207 s】
10000:耗时:【88.3623171 s】
10500:耗时:【99.4078679 s】
11000:耗时:【111.3034085 s】
11500:耗时:【124.4237544 s】
12000:耗时:【138.7710668 s】
12500:耗时:【154.5454038 s】
13000:耗时:【171.75947 s】
13500:耗时:【191.3297154 s】
14000:耗时:【214.2328073 s】
14500:耗时:【246.5230414 s】
15000:耗时:【283.0889564 s】
15500:耗时:【325.2570407 s】
16000:耗时:【371.2520703 s】
16500:耗时:【420.3371114 s】
17000:耗时:【472.2193558 s】
17500:耗时:【526.8444906 s】
18000:耗时:【583.8323722 s】
---------------------------------------------
-------------结果输出完成-------------------
---------------------------------------------
2.1. 通过已有Word,增加行并合并单元格
public static void Output(string strModelFilePath,string strFilePath, int TableRowCount)
{
try
{
Console.WriteLine("---------------------------------------------");
Console.WriteLine($"-------------AsposeWord:::输出{TableRowCount}-------------------");
Console.WriteLine("---------------------------------------------");
System.IO.File.Copy(strModelFilePath,strFilePath,true);
Document document = new Document(strFilePath);
DocumentBuilder builder = new DocumentBuilder(document);
Aspose.Words.Tables.Table table = null;
int rowStartIndex = -1;
int tableIndex = 0;
FindLocation(document,ref table, ref tableIndex, ref rowStartIndex);
rowStartIndex = table.Rows.Count-1;
for (int i = 0; i < TableRowCount * 2; i++)
{
Row pAddRow=new Row(document);
for (int j = 0; j < 16; j++)
{
Cell pAddCell=new Cell(document);
Paragraph pParagraph=new Paragraph(document);
pParagraph.AppendChild(new Run(document, ""));
pAddCell.AppendChild(pParagraph);
pAddRow.Cells.Add(pAddCell);
}
table.Rows.Add(pAddRow);
}
int index = 0;
Stopwatch sw = new Stopwatch();
sw.Start();
TimeSpan ts2;
document.Save(strFilePath);
document = new Document(strFilePath);
builder = new DocumentBuilder(document);
FindLocation(document, ref table, ref tableIndex, ref rowStartIndex);
builder.MoveTo(table);
for (int rowIndex = rowStartIndex; rowIndex < table.Rows.Count-1; rowIndex++)
{
if (index % 500 == 0)
{
sw.Stop();
ts2 = sw.Elapsed;
Console.WriteLine($"{index}:耗时:【{ts2.TotalSeconds} s】");
sw.Start();
}
index++;
if (rowIndex % 2== 1)
{
//合并单元格
for (int columnIndex = 0; columnIndex < 9; columnIndex++)
{
builder.MoveToCell(0, rowIndex - 1, columnIndex, 0);
builder.Write("100");
builder.MoveToCell(0, rowIndex - 1, columnIndex, 0);
builder.CellFormat.VerticalMerge = CellMerge.First;
builder.MoveToCell(0, rowIndex, columnIndex, 0);
builder.CellFormat.VerticalMerge = CellMerge.Previous;
}
}
else
{
for (int j = 9; j < 16; j++)
{
builder.MoveToCell(0, rowIndex, j, 0);
builder.CellFormat.VerticalMerge = CellMerge.First;
builder.MoveToCell(0, rowIndex + 1, j, 0);
builder.CellFormat.VerticalMerge = CellMerge.Previous;
}
}
}
sw.Stop();
ts2 = sw.Elapsed;
Console.WriteLine($"{index}:耗时:【{ts2.TotalSeconds} s】");
document.Save(strFilePath);
Console.WriteLine("---------------------------------------------");
Console.WriteLine("-------------结果输出完成-------------------");
Console.WriteLine("---------------------------------------------");
Console.WriteLine("");
Console.WriteLine("");
Console.WriteLine("");
}
catch (Exception exception)
{
Console.WriteLine(exception);
}
}
private static void FindLocation(Aspose.Words.Document document, ref Table table, ref int tableIndex, ref introwIndex)
{
//找到目标行和目标表
string target_str = "{jzbsb_jzdh}";
NodeCollection nodeCollection = document.GetChildNodes(NodeType.Table, true);
foreach (Node pNode in nodeCollection)
{
Aspose.Words.Tables.Table pTable = pNode as Aspose.Words.Tables.Table;
if (pTable == null)
{
break;
}
for (int i = 0; i < pTable.Rows.Count; i++)
{
if (string.Compare(pTable.Rows[i].Cells[0].ToTxt().ToString().Trim(), target_str, true) == 0)
{
rowIndex = i;
table = pTable;
tableIndex = nodeCollection.IndexOf(pNode);
return;
}
}
}
}
我们看到上面的代码在增加行之后,我们对Word文档进行了保存,保存之后使用Save保存Word文档,然后再打开Word文档进行合并单元格。