C#字符串拼接的6种方式及其性能分析对比
前言
在C#编程中字符串拼接是一种常见且基础的操作,广泛应用于各种场景,如动态生成SQL查询、构建日志信息、格式化用户显示内容等。然而,不同的字符串拼接方式在性能和内存使用上可能存在显著差异。今天咱们一起来看看在C#中字符串拼接的常见6种方式及其使用BenchmarkDotNet进行性能分析对比。
BenchmarkDotNet
BenchmarkDotNet是一个基于.NET开源、功能全面、易于使用的性能基准测试框架,它为.NET开发者提供了强大的性能评估和优化能力。通过自动化测试、多平台支持、高级统计分析和自定义配置等特性,BenchmarkDotNet帮助开发者更好地理解和优化软件系统的性能表现。
拼接基础数据
private const int IterationCount = 1000;
private const string StringPart1 = "追逐时光者";
private const string StringPart2 = "DotNetGuide";
private const string StringPart3 = "DotNetGuide技术社区";
private readonly string[] _stringPartsArray = { "追逐时光者", "DotNetGuide", "DotNetGuide技术社区" };
+操作符
/// <summary>
/// 使用 + 操作符拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string PlusOperator()
{
string result = StringPart1 + " " + StringPart2 + " " + StringPart3;
return result;
}
$内插字符串
/// <summary>
/// 使用 $ 内插字符串拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string InterpolatedString()
{
string result = $"{StringPart1} {StringPart2} {StringPart3}";
return result;
}
String.Format
/// <summary>
/// 使用string.Format()拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string StringFormat()
{
string result = string.Format("{0} {1} {2}", StringPart1, StringPart2, StringPart3);
return result;
}
String.Concat
/// <summary>
/// 使用string.Concat()拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string StringConcat()
{
string result = string.Concat(StringPart1, " ", StringPart2, " ", StringPart3);
return result;
}
String.Join
/// <summary>
/// 使用string.Join()拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string StringJoin()
{
string result = string.Join(" ", _stringPartsArray);
return result;
}
StringBuilder
Append拼接字符串
/// <summary>
/// 使用StringBuilder.Append拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string StringBuilderAppend()
{
StringBuilder stringBuilder = new StringBuilder();
stringBuilder.Append(StringPart1);
stringBuilder.Append(" ");
stringBuilder.Append(StringPart2);
stringBuilder.Append(" ");
stringBuilder.Append(StringPart3);
return stringBuilder.ToString();
}
AppendFormat拼接字符串
/// <summary>
/// 使用StringBuilder.AppendFormat拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string StringBuilderAppendFormat()
{
StringBuilder stringBuilder = new StringBuilder();
stringBuilder.AppendFormat("{0} {1} {2}", StringPart1, StringPart2, StringPart3);
return stringBuilder.ToString();
}
性能基准对比测试完整代码
咱们分别以少量字符串拼接和大量字符串拼接为例,进行性能基准对比测试:
说明:
- Mean: 所有测量值的算术平均值。
- Error: 99.9% 置信区间的一半。
- StdDev: 所有测量值的标准差。
- Gen0: 第 0 代 GC 每 1000 次操作收集一次。
- Gen1: 第 1 代 GC 每 1000 次操作收集一次。
- Gen2: 第 2 代 GC 每 1000 次操作收集一次。
- Allocated: 每次操作分配的内存(仅托管内存,包含所有内容,1KB = 1024B)。
- 1 ms: 1 毫秒(0.001 秒)。
少量字符串拼接
using BenchmarkDotNet.Attributes;
using System.Text;
namespace BenchmarkDotNetExercise
{
[MemoryDiagnoser]//记录内存分配情况
public class StringConcatenationBenchmark
{
private const int IterationCount = 1000;
private const string StringPart1 = "追逐时光者";
private const string StringPart2 = "DotNetGuide";
private const string StringPart3 = "DotNetGuide技术社区";
private readonly string[] _stringPartsArray = { "追逐时光者", "DotNetGuide", "DotNetGuide技术社区" };
#region 少量字符串拼接
/// <summary>
/// 使用 + 操作符拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string PlusOperator()
{
string result = StringPart1 + " " + StringPart2 + " " + StringPart3;
return result;
}
/// <summary>
/// 使用 $ 内插字符串拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string InterpolatedString()
{
string result = $"{StringPart1} {StringPart2} {StringPart3}";
return result;
}
/// <summary>
/// 使用string.Format()拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string StringFormat()
{
string result = string.Format("{0} {1} {2}", StringPart1, StringPart2, StringPart3);
return result;
}
/// <summary>
/// 使用string.Concat()拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string StringConcat()
{
string result = string.Concat(StringPart1, " ", StringPart2, " ", StringPart3);
return result;
}
/// <summary>
/// 使用string.Join()拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string StringJoin()
{
string result = string.Join(" ", _stringPartsArray);
return result;
}
/// <summary>
/// 使用StringBuilder.Append拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string StringBuilderAppend()
{
StringBuilder stringBuilder = new StringBuilder();
stringBuilder.Append(StringPart1);
stringBuilder.Append(" ");
stringBuilder.Append(StringPart2);
stringBuilder.Append(" ");
stringBuilder.Append(StringPart3);
return stringBuilder.ToString();
}
/// <summary>
/// 使用StringBuilder.AppendFormat拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string StringBuilderAppendFormat()
{
StringBuilder stringBuilder = new StringBuilder();
stringBuilder.AppendFormat("{0} {1} {2}", StringPart1, StringPart2, StringPart3);
return stringBuilder.ToString();
}
#endregion
}
}

大量字符串拼接
using BenchmarkDotNet.Attributes;
using System.Text;
namespace BenchmarkDotNetExercise
{
[MemoryDiagnoser]//记录内存分配情况
public class StringConcatenationBenchmark
{
private const int IterationCount = 1000;
private const string StringPart1 = "追逐时光者";
private const string StringPart2 = "DotNetGuide";
private const string StringPart3 = "DotNetGuide技术社区";
private readonly string[] _stringPartsArray = { "追逐时光者", "DotNetGuide", "DotNetGuide技术社区" };
#region 大量字符串拼接
/// <summary>
/// 使用 + 操作符拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string BigDataPlusOperator()
{
string result = string.Empty;
for (int i = 0; i < IterationCount; i++)
{
result += StringPart1 + " " + StringPart2 + " " + StringPart3;
}
return result;
}
/// <summary>
/// 使用StringBuilder.Append拼接字符串
/// </summary>
/// <returns></returns>
[Benchmark]
public string BigDataStringBuilderAppend()
{
StringBuilder stringBuilder = new StringBuilder();
for (int i = 0; i < IterationCount; i++)
{
stringBuilder.Append(StringPart1);
stringBuilder.Append(" ");
stringBuilder.Append(StringPart2);
stringBuilder.Append(" ");
stringBuilder.Append(StringPart3);
}
return stringBuilder.ToString();
}
#endregion
}
}

C#字符串拼接的6种方式及其性能分析对比的更多相关文章
- JS几种变量交换方式以及性能分析对比
前言 "两个变量之间的值得交换",这是一个经典的话题,现在也有了很多的成熟解决方案,本文主要是列举几种常用的方案,进行大量计算并分析对比. 起由 最近做某个项目时,其中有一个需求是 ...
- JS几种数组遍历方式以及性能分析对比
前言 这一篇与上一篇 JS几种变量交换方式以及性能分析对比 属于同一个系列,本文继续分析JS中几种常用的数组遍历方式以及各自的性能对比 起由 在上一次分析了JS几种常用变量交换方式以及各自性能后,觉得 ...
- Python中字符串拼接的三种方式
在Python中,我们经常会遇到字符串的拼接问题,在这里我总结了三种字符串的拼接方式: 1.使用加号(+)号进行拼接 加号(+)号拼接是我第一次学习Python常用的方法,我们只需要把我们要加 ...
- Python字符串拼接的五种方式
第一种 通过加号(+)的形式 print('第一种方式通过加号形式连接 :' + 'love'+'Python' + '\n') 第二种 通过逗号(,)的形式 print('第二种方式通过逗号形式连接 ...
- java字符串拼接的几种方式
1. plus方式 当左右两个量其中有一个为String类型时,用plus方式可将两个量转成字符串并拼接. String a="";int b=0xb;String c=a+b;2 ...
- C#字符串拼接的三种方式
static void Main(string[] args) { string name = "asher"; //方法1 string str1 = "hello & ...
- [Golang]字符串拼接方式的性能分析
本文100%由本人(Haoxiang Ma)原创,如需转载请注明出处. 本文写于2019/02/16,基于Go 1.11.至于其他版本的Go SDK,如有出入请自行查阅其他资料. Overview 写 ...
- C 语言字符串连接的 3种方式
C 语言字符串连接的 3种方式 #include<stdio.h> #include<stdlib.h> #include<string.h> char *join ...
- Js 字符串拼接的两种方法
字符串拼接的两种方法 用数组的方法的好处是:避免变量重新定义.赋值 <!DOCTYPE html> <html lang="en"> <head> ...
- C++读取字符串数据的两种方式
C++读取字符串数据的两种方式 对于同样的样例输入: ladder came tape soon leader acme RIDE lone Dreis peat ScAlE orb eye Ride ...
随机推荐
- oracle中id自增长(转)
首先,你要有一张表! CREATE TABLE example( ID Number(4) NOT NULL PRIMARY KEY, NAME VARCHAR(25), PHONE VARCHAR( ...
- Postman无法启动
前情 最近在捣鼓node.js,需要一个接口测试工具,而Postman是业界有名的接口测试工具,自然接口测试就用它了. 坑 已经有一段时间没启动Postman了,突然发现启动一直卡在修复界面,重启也不 ...
- IOS多线程之NSOperation(3)
IOS多线程之NSOperation(3) 操作优先级和服务质量 可以通过QueuePriority属性来设置operation在队列中的执行优先级 public enum QueuePriority ...
- 对 .NET 开发者来说,Azure AD 改名为 Microsoft Entra ID 意味着什么?
对 .NET 开发者来说,Azure AD 改名为 Microsoft Entra ID 意味着什么? 原文地址:https://devblogs.microsoft.com/dotnet/azure ...
- AI视频抠图来了!还可以替换视频背景,附下载链接
虽然人工智能正在飞速发展中,图像处理技术也在不断升级,但视频背景去除一直都是图像处理任务中最具挑战性的难题之一 Clipper是一款专注于高精度图像分割的AI工具,用于图像和视频的背景去除,允许用户直 ...
- FM的正交解调法
1.FM的模拟调制过程 FM信号是一种频率调制信号,其携带的信息保存在其信号的频率中,通过改变载波的频率来实现基带数据的传输. 其函数表达式如下: \[s(t) = A*cos(w_c*t + K ...
- 【报错解决】【Mathtype】lease restart Word to load MathType addin properly
打开Mathtype安装目录 例如我的C:\software\MathModel\MATHTYPE 继续进入目录C:\software\MathModel\MATHTYPE\MathPage\64 找 ...
- 龙哥量化:缠论的笔、线段、中枢以及MACD背离分析实现
声明:看到研究非常细致深入的文章,转载到我的博客园,以便学习和研究. (转载自聚宽的大象咖啡) 本文参考了如下相关文贴: [量化缠论]之分型.笔.线段识别1.1. 在该帖的基础上将线段和调整后的k线绘 ...
- Qt音视频开发17-vlc内核回调拿图片进行绘制
一.前言 在众多播放器中,支持的种类格式众多,并支持DVD影音光盘,VCD影音光盘及各类流式协议,提供了sdk进行开发,这点是至关重要的,尽管很多优秀的播放器很牛逼,由于没有提供sdk第三方开发,少了 ...
- Qt编写物联网管理平台36-通信协议
一.前言 本系统默认采用modbus协议,支持串口和网络rtu模式,后期还会引入其他通信协议比如mqtt等,可以在端口管理中下拉选择通信协议即可. 1.1 通信流程 整体的结构是:控制器挂在通信端口, ...