准备工作:

1、首先需要提供一个word模板,并且标记好您要插入书签的位置,定义书签的命名。如图

2、模拟您要插入的Excel原始数据和图表对象

插入代码如下:

Private Sub CommandButton1_Click()

    Dim App, WrdDoc, Mypath As String

    On Error Resume Next
'定义原始模板的储存路径,默认和excel在同一路径
Mypath = ThisWorkbook.Path & "\模板.doc"
'用Set关键字创建Word应用成序对象!
Set App = CreateObject("Word.Application")
App.Visible = True
'打开这个Word文件!
Set WrdDoc = App.Documents.Open(Mypath)
'以当前模板创建一个新的模板
Set word = App.Documents.Add(Mypath)
'将excel指定单元格的数据写入之前已经编辑定位好的word书签位置
word.Bookmarks("书签1").Range = Range("b2")
word.Bookmarks("书签2").Range = Range("b3")
word.Bookmarks("书签3").Range = Range("b4")
word.Bookmarks("书签4").Range = Range("b5")
word.Bookmarks("书签5").Range = Range("b6") ''插入当前工作表的2个图表对象到指定位置,并显示出来
''更改word 插入对象的环绕方式
''http://www.debugease.com/vb/2205943.html
With App
ThisWorkbook.Worksheets("底稿数据").ChartObjects().Activate
ActiveChart.ChartArea.Copy
.ActiveDocument.Bookmarks("收入情况图").Range.Select
.Selection.Paste
.ActiveDocument.InlineShapes.Item().ConvertToShape
.ActiveDocument.Shapes.Item().WrapFormat.Type = wdWrapTight ThisWorkbook.Worksheets("底稿数据").ChartObjects().Activate
ActiveChart.ChartArea.Copy
.ActiveDocument.Bookmarks("支出情况图").Range.Select
.Selection.Paste
.ActiveDocument.InlineShapes.Item().ConvertToShape
.ActiveDocument.Shapes.Item().WrapFormat.Type = wdWrapTight '更改环绕方式
End With Paths = CreateObject("WScript.Shell").SpecialFolders("Desktop") & "\" '记录“桌面”文件夹的路径
word.SaveAs Filename:=Paths & "2019年X月XXXX食堂收支分析报告" & ".doc" '另存为word报告成品
word.Close ' 关闭文件
App.Quit
Set App = Nothing
MsgBox "2019年X月XXXX食堂收支分析报告", vbInformation, "报告已生成到桌面"
Shell "EXPLORER.EXE " & Left(Paths, Len(Paths) - ), vbMaximizedFocus '打开桌面
End Sub

附件下载地址:

https://files.cnblogs.com/files/ty1216jhy/%E8%87%AA%E5%8A%A8%E7%94%9F%E6%88%90%E9%A3%9F%E5%A0%82%E6%8A%A5%E5%91%8A.rar

联系QQ:609682901

2020年5月日志:

-----------------------------------------不久之后我将这个小工具做成了VSTO外接程序,小学生代码如下-------------------------------------------------------------

做成excel 外接程序好处就是,代码不容易被篡改,使用相对更稳定,就代码升级没有VBA方便

主要有二段核心代码:

一、生成主要书签数据和生成饼状图

   public void 刷新主要数据()
{
try
{
app = Globals.ThisAddIn.Application;
excel.Workbook wbk = app.Workbooks["食堂报告模板2019.xls"];
excel.Worksheet wst1 = wbk.Worksheets["本月数据"];
excel.Worksheet wst2 = wbk.Worksheets["上月数据"];
excel.Worksheet wst3 = wbk.Worksheets["生成数据"];
excel.Worksheet wst4 = wbk.Worksheets["对比数据"];
wst3.Range["b2:b6"].ClearContents();
//提取收入说明
int lr1 = wst1.Range["a3"].get_End(excel.XlDirection.xlDown).Row;
string str1 = string.Empty;
if (checkBox2.Checked == true)
{
for (int i = ; i < lr1 + ; i++)
{
if ((String)wst1.Range["b" + i].Text != "")
{
str1 = str1 + "," + "\n" + wst1.Range["a" + i].Text + ":" + wst1.Range["b" + i].Text + "元"; ;
}
}
}
else
{
for (int i = ; i < lr1 + ; i++)
{
if ((String)wst1.Range["b" + i].Text != "")
{
str1 = str1 + "," + wst1.Range["a" + i].Text + ":" + wst1.Range["b" + i].Text + "元";
}
}
}
int len1 = str1.Length;
string str1_1 = str1.Substring(, len1 - ) + "。";
wst3.Range["b2"].Value2 = str1_1.Replace(" ", "");//替换字符串中产生的空格 //提取支出说明
int lr2 = wst1.Range["d2"].get_End(excel.XlDirection.xlDown).Row;
string str2 = string.Empty;
if (checkBox2.Checked == true)
{
for (int i = ; i < lr2 + ; i++)
{
if ((String)wst1.Range["e" + i].Text != "")
{
str2 = str2 + "," + "\n" + wst1.Range["d" + i].Text + ":" + wst1.Range["e" + i].Text + "元"; ;
}
}
}
else
{
for (int i = ; i < lr2 + ; i++)
{
if ((String)wst1.Range["e" + i].Text != "")
{
str2 = str2 + "," + wst1.Range["d" + i].Text + ":" + wst1.Range["e" + i].Text + "元"; ;
}
}
} int len2 = str2.Length;
string str2_1 = str2.Substring(, len2 - ) + "。";
wst3.Range["b3"].Value2 = str2_1.Replace(" ", ""); //MessageBox.Show(str1_1);
//提取结余数据
int a = wst1.Range["b100"].get_End(excel.XlDirection.xlUp).Row;
int b = wst2.Range["b100"].End[excel.XlDirection.xlUp].Row;
string str3 = "上月结余数:" + wst2.Range["b" + b].Value2 + "元;";
string str4 = "本月结余数:" + string.Format("{0:N2}", wst1.Range["b" + a].Value2) + "元;";
string str5 = "上年结余数:" + wst1.Range["c4"].Value2 + "元;";
string str6 = "上月累计结余数:" + wst2.Range["c" + b].Value2 + "元;";
string str7 = "本月累计结余数:" + wst1.Range["c" + a].Value2 + "元";
string res = str3 + "\n" + str4 + "\n" + str5 + "\n" + str6 + "\n" + str7 + "。";
wst3.Range["b4"].Value2 = res; //收入分析
if (wst4.Range["d2"].Value < )
{
wst4.Range["f2"].Value2 = "本月收入下滑:" + string.Format("{0:N2}", -wst4.Range["d2"].Value2) +
"元,环比下滑" + string.Format("{0:P}", -wst4.Range["e2"].Value2) + "。";
}
else
if (wst4.Range["d2"].Value > )
{
wst4.Range["f2"].Value2 = "本月收入上涨:" + string.Format("{0:N2}", wst4.Range["d2"].Value2) +
"元,环比上涨" + string.Format("{0:P}", wst4.Range["e2"].Value2) + "。";
}
else
{
wst4.Range["f2"].Value2 = "本月收入与上月持平。";
}
string res1 = wst4.Range["f2"].Value2;
//MessageBox.Show(res1);
//支出分析
if (wst4.Range["d3"].Value < )
{
wst4.Range["f3"].Value2 = "本月支出下滑:" + string.Format("{0:N2}", -wst4.Range["d3"].Value2) +
"元,环比下滑" + string.Format("{0:P}", -wst4.Range["e3"].Value2) + "。";
}
else
if (wst4.Range["d3"].Value > )
{
wst4.Range["f3"].Value2 = "本月支出上涨:" + string.Format("{0:N2}", wst4.Range["d3"].Value2) +
"元,环比上涨" + string.Format("{0:P}", wst4.Range["e3"].Value2) + "。";
}
else
{
wst4.Range["f3"].Value2 = "本月支出与上月持平。";
}
string res2 = wst4.Range["f3"].Value2;
//MessageBox.Show(res2);
//结余分析
if (wst4.Range["d4"].Value < )
{
wst4.Range["f4"].Value2 = "本月收支结余下滑:" + string.Format("{0:N2}", -wst4.Range["d4"].Value2) +
"元,环比下滑" + string.Format("{0:P}", wst4.Range["e4"].Value2) + "。";
}
else
if (wst4.Range["d4"].Value > )
{
wst4.Range["f4"].Value2 = "本月收支结余上涨:" + string.Format("{0:N2}", wst4.Range["d4"].Value2) +
"元,环比上涨" + string.Format("{0:P}", wst4.Range["e4"].Value2) + "。";
}
else
{
wst4.Range["f4"].Value2 = "本月收支结余与上月持平。";
}
string res3 = wst4.Range["f4"].Value2; string res_1 = res1 + "主要原因:******" + "\n" + res2 + "主要原因:******" + "\n" + res3 + "主要原因:******";
//MessageBox.Show(res_1);
wst3.Range["b5"].Value2 = res_1; string res_2 = "【写报告就像拜菩萨一样,全靠诚心!所以为表心意,建议大家还是手动写报告】";
wst3.Range["b6"].Value2 = res_2;
}
catch (Exception ex)
{
MessageBox.Show(ex.ToString());
}
}
   public void 生成饼状图()
{
try
{
app = Globals.ThisAddIn.Application;
excel.Workbook wbk = app.Workbooks["食堂报告模板2019.xls"];
excel.Worksheet wst = wbk.Worksheets["本月数据"];
excel.Worksheet wst4 = wbk.Worksheets["对比数据"];
wst4.Range["j1:n100"].ClearContents(); //收入项目和金额
int lr = wst.Range["a3"].get_End(excel.XlDirection.xlDown).Row;
int i = ;
foreach (excel.Range rng in wst.Range["a6:a" + lr])
{
string str = rng.Value2.ToString();
String str1 = (String)rng.Offset[, ].Text;
string stri = "[^\u4e00-\u9fa5]";
//if (str.Substring(2, 1) != "(" && str1 != "")//
//2020年5月新报表格式修改,收入项提取不包含带括号的子项目
if (!str.Contains("(") && str1 != "" &&!str.Contains("收入合计") && !str.Contains("收支结余"))
{
//MessageBox.Show(str);
string result = Regex.Replace(str, stri, "");
wst4.Cells[i, "j"] = result;
wst4.Cells[i, "k"] = (String)rng.Offset[, ].Text;
i += ;
}
}
//支出项目和金额
int j = ;
int lr1 = wst.Range["d4"].get_End(excel.XlDirection.xlDown).Row - ;
foreach (excel.Range rng in wst.Range["d5:d" + lr1])
{
string str = rng.Value2.ToString();
String str1 = (String)rng.Offset[, ].Text;
string stri = "[^\u4e00-\u9fa5]";
//2020年5月新报表格式修改,收入项提取不包含带括号的子项目
//强制添加不包含str != "1、水电支出" && str != "2、基本伙食支出",因为下面的维修费和其他支出又必须提取,我靠,做表的人真是随心所欲
if (!str.Contains("(") && str1 != "" && !str.Contains("水电支出") && !str.Contains("基本伙食支出") && !str.Contains("人员支出"))
{
//MessageBox.Show(str);
string result = Regex.Replace(str, stri, "");
wst4.Cells[j, "m"] = result;
wst4.Cells[j, "n"] = (String)rng.Offset[, ].Text;
j += ;
}
}
if ((String)wst.Range["e" + lr1].Text != "")
{
int m = wst4.Range["m2"].get_End(excel.XlDirection.xlDown).Row + ;
wst4.Range["m" + m].Value2 = wst.Range["d" + lr1].Value2;
wst4.Range["n" + m].Value2 = wst.Range["d" + lr1].Offset[, ].Value;
}
wst4.Range["j1"].Value2 = "收入项目";
wst4.Range["k1"].Value2 = "收入金额";
int r = wst4.Range["j2"].get_End(excel.XlDirection.xlDown).Row;
#region 此段同样可以生成饼状图,只是同样都是XlChartType.xl3DPie,为何形状会不一样
/*
*/
//excel.ChartObjects chartObjects = (excel.ChartObjects)wst4.ChartObjects();
//excel.ChartObject chartObject = chartObjects.Add(wst4.Range["a8"].Left, wst4.Range["a8"].Top, 362, 200);
//excel.Chart chart = chartObject.Chart;
//chart.ChartType = excel.XlChartType.xl3DPie;
//chart.SetSourceData(wst4.Range["j1:k" + r]);
//chart.SetElement(MsoChartElementType.msoElementLegendRight);
//chart.Legend.Top = 8.5;
//chart.Legend.Height = 200;
//wst4.ChartObjects(1).Name = "收入xl3DPie";
/*
*
*/
#endregion
wst4.Activate();
wst4.Range["j1:k" + r].Select();
//office版本语法差异
if (Single.Parse(app.Version) >= )
{
wst4.Shapes.AddChart2(-, XlChartType.xl3DPie, wst4.Range["a8"].Left, wst4.Range["a8"].Top, , , true);
}
else
{
wst4.Shapes.AddChart(XlChartType.xl3DPie, wst4.Range["a8"].Left, wst4.Range["a8"].Top, , );
}
wst4.ChartObjects().Name = "收入xl3DPie";
wst4.ChartObjects("收入xl3DPie").Chart.SetElement(MsoChartElementType.msoElementLegendRight);
wst4.ChartObjects("收入xl3DPie").Chart.Legend.Top = 6.5;
wst4.ChartObjects("收入xl3DPie").Chart.Legend.Height = ;
//excel.Chart chart_s = wst4.ChartObjects("收入xl3DPie").Chart;
//string style = Interaction.InputBox("请输入1-7之间(包含)的数字", "图形样式", "文本内容", -1, -1);
//chart_s.ApplyLayout(int.Parse(style),chart_s.ChartType);
//获取图像的标题,当更改成无标题的图像是会报错
//string sr = wst4.ChartObjects("收入xl3DPie").Chart.ChartTitle.Text;
//MessageBox.Show(sr); wst4.Range["m1"].Value2 = "支出项目";
wst4.Range["n1"].Value2 = "支出金额";
int k = wst4.Range["m2"].get_End(excel.XlDirection.xlDown).Row; wst4.Range["m1:n" + k].Select();
if (Single.Parse(app.Version) >= )
{
wst4.Shapes.AddChart2(-, XlChartType.xl3DPie, wst4.Range["f8"].Left, wst4.Range["f8"].Top, , , true);
}
else
{
wst4.Shapes.AddChart(XlChartType.xl3DPie, wst4.Range["f8"].Left, wst4.Range["f8"].Top, , );
} wst4.ChartObjects().Name = "支出xl3DPie";
wst4.ChartObjects("支出xl3DPie").Chart.SetElement(MsoChartElementType.msoElementLegendRight);
wst4.ChartObjects("支出xl3DPie").Chart.Legend.Top = 6.5;
wst4.ChartObjects("支出xl3DPie").Chart.Legend.Height = ;
string zc = wst4.ChartObjects("支出xl3DPie").Chart.ChartTitle.Text;
app.ScreenUpdating = true;
//MessageBox.Show(zc);
}
catch (Exception ex)
{
MessageBox.Show(ex.ToString());
} finally
{
//检验图表名称
string res = "";
excel.Worksheet wst = Globals.ThisAddIn.Application.Workbooks["食堂报告模板2019.xls"].Worksheets["对比数据"];
foreach (excel.Shape shape in wst.Shapes)
{
if (shape.Type == MsoShapeType.msoChart)
{
res = shape.Name + ":" + shape.Chart.ChartTitle.Text + "\n" + res;
//MessageBox.Show(shape.Chart.ChartTitle.Text);
}
}
MessageBox.Show(res, "已生成图表");
}
}

二、导出报告

    private void Button3_Click(object sender, RibbonControlEventArgs e)
{
try
{
app = Globals.ThisAddIn.Application;
app.StatusBar = "报告生成中,请勿关闭工作簿...";
System.Windows.Forms.Application.DoEvents();
//DataTable dt = LoadDataFromExcel("D:\\用户目录\\原始数据.xls");
//object oMissing = System.Reflection.Missing.Value;
//创建一个Word应用程序实例
word._Application oWord = new word.Application();
//设置为不可见
oWord.Visible = false;
//模板文件地址,这里假设在X盘根目录
string localpath = Path.GetDirectoryName(new Uri(Assembly.GetExecutingAssembly().CodeBase).LocalPath);
string filename = localpath + "\\模板.doc";
string year = DateTime.Now.Year.ToString();
//object oTemplate = "D:\\用户目录\\模板.doc";
//以模板为基础生成文档
//Word._Document oDoc = oWord.Documents.Add(ref oTemplate, ref oMissing, ref oMissing, ref oMissing);
//新版本VS已经取消了对参数的限制,可以不用谢missing
word._Document oDoc = oWord.Documents.Add(filename); //声明书签数组
object[] oBookMark = new object[];
//赋值书签名
oBookMark[] = "书签1";
oBookMark[] = "书签2";
oBookMark[] = "书签3";
oBookMark[] = "书签4";
oBookMark[] = "书签5";
//赋值任意数据到书签的位置
app = Globals.ThisAddIn.Application;
excel.Workbook wbk = app.Workbooks["食堂报告模板2019.xls"];
excel.Worksheet wst1 = wbk.Worksheets["本月数据"];
excel.Worksheet wst2 = wbk.Worksheets["上月数据"];
excel.Worksheet wst3 = wbk.Worksheets["生成数据"];
excel.Worksheet wst4 = wbk.Worksheets["对比数据"];
oDoc.Bookmarks["书签1"].Range.Text = wst3.Range["b2"].Value2;
oDoc.Bookmarks["书签2"].Range.Text = wst3.Range["b3"].Value2;
oDoc.Bookmarks["书签3"].Range.Text = wst3.Range["b4"].Value2;
oDoc.Bookmarks["书签4"].Range.Text = wst3.Range["b5"].Value2;
oDoc.Bookmarks["书签5"].Range.Text = wst3.Range["b6"].Value2;
//oDoc.Bookmarks.get_Item(ref oBookMark[0]).Range.Text = dt.Rows[0][1].ToString();
//oDoc.Bookmarks.get_Item(ref oBookMark[1]).Range.Text = dt.Rows[1][1].ToString();
//oDoc.Bookmarks.get_Item(ref oBookMark[2]).Range.Text = dt.Rows[2][1].ToString();
//oDoc.Bookmarks.get_Item(ref oBookMark[3]).Range.Text = dt.Rows[3][1].ToString();
//oDoc.Bookmarks.get_Item(ref oBookMark[4]).Range.Text = dt.Rows[4][1].ToString();
/*对WOrd文档的操作大全
* https://www.cnblogs.com/xh6300/p/5915717.html
*/
wst4.ChartObjects("收入xl3DPie").Activate();
wst4.ChartObjects("收入xl3DPie").Chart.ChartArea.Copy();
oWord.ActiveDocument.Bookmarks["收入情况图"].Range.Select();
oWord.Selection.Paste();
word.Shape shape1 = oDoc.Application.ActiveDocument.InlineShapes[].ConvertToShape();
shape1.WrapFormat.Type = word.WdWrapType.wdWrapTight; wst4.ChartObjects("支出xl3DPie").Activate();
wst4.ChartObjects("支出xl3DPie").Chart.ChartArea.Copy();
oWord.ActiveDocument.Bookmarks["支出情况图"].Range.Select();
oWord.Selection.Paste();
word.Shape shape2 = oDoc.Application.ActiveDocument.InlineShapes[].ConvertToShape();
shape2.WrapFormat.Type = word.WdWrapType.wdWrapTight; //弹出保存文件对话框,保存生成的Word
SaveFileDialog sfd = new SaveFileDialog
{
Title = "请选择保存您的新报告",
Filter = "Word Document(*.doc)|*.doc",
DefaultExt = "Word Document(*.doc)|*.doc",
FileName = year + "年X月XXXX食堂收支分析报告"
};
if (sfd.ShowDialog() == DialogResult.OK)
{
object file_name = sfd.FileName;
oDoc.SaveAs(file_name);
oDoc.Close();
//关闭word
oWord.Quit();
MessageBox.Show("报告已导出", "温馨提示", MessageBoxButtons.OK, MessageBoxIcon.Information);
app.StatusBar = "报告已导出。";
}
else
{
MessageBox.Show("导出取消", "温馨提示", MessageBoxButtons.OK, MessageBoxIcon.Error);
app.StatusBar = "报告未导出。";
}
}
catch (Exception ex)
{
MessageBox.Show(ex.ToString());
}
}

使用VBA将Excel指定单元格数据、字符串或者图表对象插入到Word模板指定书签处的更多相关文章

  1. python接口自动化测试--数据分离读取Excal指定单元格数据

    上一篇博客讲了怎么批量读取Excal单元格数据,现在咱们说一下怎么读取Excal指定单元格数据. 一.首先建一个Test_Main类 #!/usr/bin/python # -*- coding: U ...

  2. QTableWidget 用法总结(只能使用标准的数据模型,并且其单元格数据是QTableWidgetItem的对象)

    QTableWidget是QT程序中常用的显示数据表格的空间,很类似于VC.C#中的DataGrid.说到QTableWidget,就必须讲一下它跟QTabelView的区别了.QTableWidge ...

  3. VBS读取txt文档数据查找Excel中单元格数据符合条件的剪切到工作表2中

    Dim fso,f,a set oExcel = CreateObject( "Excel.Application" ) oExcel.Visible = false '4) 打开 ...

  4. Python 用load_workbook 读取excel某个单元格数据、读取excel行数、列数

    from openpyxl import load_workbook path = r'D:\pywork\12' # EXCEL信息所在文件夹 e= load_workbook(path + '/' ...

  5. Excel合并单元格数据

    1.=A1&B1 2.=CONCATENATE(A1,B1)

  6. 疑难杂症 | Excel VBA锁定指定单元格区域

    背景:锁定EXCEL表头 一.手动操作流程 其基本逻辑并不赋值,手动操作流程是: 1.取消所有单元格的"锁定"格式 CTRL+A,选中全部的单元格→单击右键→设置单元格格式→保护→ ...

  7. vba打开excel文件遍历sheet的名字和指定单元格的值

    今天项目上有个应用,获取指定Excel文件下的所有sheet的名称以及当前sheet中指定单元格的值,并把他们写到固定的sheet中去,看了下,文件比较多,而且每个文件sheet的个数比较多,也不一样 ...

  8. ASP.NET 导出gridview中的数据到Excel表中,并对指定单元格换行操作

    1. 使用NPOI读取及生成excel表. (1)导出Click事件: 获取DataTable; 给文件加文件名: string xlsxName = "xxx_" + DateT ...

  9. 在Excel里用vba给合并的单元格添加注释

    Excel里使用VBA对已经合并的单元格添加注释,直接使用AddComment会报: 运行时错误 '1004':应用程序定义或者对象定义错误 找了很多文章都没找到怎么解决,最后发现在AddCommen ...

随机推荐

  1. 06. redis cluster

    目录 Redis Cluster redis cluster 特点 搭建redis cluster 访问redis cluster redis-cli 访问redis cluster 重新分片数据 新 ...

  2. PAT 乙级 1036.跟奥巴马一起编程 C++/Java

    题目来源 美国总统奥巴马不仅呼吁所有人都学习编程,甚至以身作则编写代码,成为美国历史上首位编写计算机代码的总统.2014 年底,为庆祝“计算机科学教育周”正式启动,奥巴马编写了很简单的计算机代码:在屏 ...

  3. wordpress添加post_type自定义文章类型

    wordpress很强大,能当博客也能进行二次开发出很完善的内容管理系统满足企业运营需求,比如可以添加products产品模型.汽车模型等,如何实现呢?添加post_type自定义文章类型就可以了 p ...

  4. Comet OJ - Contest #2题解

    传送门 既然没参加过就没有什么小裙子不小裙子的了-- 顺便全是概率期望真是劲啊-- 因自过去而至的残响起舞 \(k\)增长非常快,大力模拟一下就行了 int main(){ scanf("% ...

  5. html--前端JavaScript基本内容

    一.JavaScript 变量 在 JavaScript 中创建变量通常称为"声明"变量. 使用 var 关键词来声明变量. 注意: 1.变量必须以字母开头 2.变量也能以 $ 和 ...

  6. excel的IRR函数

    office官网找到IRR的介绍 https://support.office.com/zh-cn/article/irr-%E5%87%BD%E6%95%B0-64925eaa-9988-495b- ...

  7. [PHP] JQuery+Layer实现添加删除自定义标签代码

    JQuery+Layer实现添加删除自定义标签代码 实现效果如下: 实现代码如下: <!doctype html> <html> <head> <meta c ...

  8. C#中的Queue集合

    Queue<T>集合 特点:先进先出,简单来说,就是新添加的元素是顺序添加在集合尾部,但是,移除的时候是从顶部开始移除元素. 三个方法: Enqueue(T obj);//顺序添加一个值到 ...

  9. 概率论基础知识(Probability Theory)

    概率(Probability):事件发生的可能性的数值度量. 组合(Combination):从n项中选取r项的组合数,不考虑排列顺序.组合计数法则:. 排列(Permutation):从n项中选取r ...

  10. Java 并发系列之六:java 并发容器(4个)

    1. ConcurrentHashMap 2. ConcurrentLinkedQueue 3. ConcurrentSkipListMap 4. ConcurrentSkipListSet 5. t ...