引言
字符串处理是编程中最基础也是最常见的任务之一。在C#中,System.String
类提供了丰富的方法来操作字符串,配合.NET框架的其他功能,可以高效地完成各种文本处理需求。本文将全面介绍C#中字符串的核心操作方法,包括创建、修改、比较、搜索、格式化等实用技巧,帮助您掌握文本处理的精髓。
一、字符串基础与创建
1.1 字符串特性
- 不可变性:C#字符串是不可变的,任何”修改”操作都会创建新字符串
- Unicode支持:默认使用UTF-16编码
- 引用类型:但具有值类型的某些特性
1.2 创建字符串的多种方式
// 直接赋值
string str1 = "Hello World";
// 使用构造函数
char[] letters = { 'H', 'e', 'l', 'l', 'o' };
string str2 = new string(letters); // "Hello"
// 从char重复创建
string str3 = new string('*', 10); // "**********"
// 使用StringBuilder构建
var sb = new StringBuilder();
sb.Append("Hello");
sb.Append(" World");
string str4 = sb.ToString(); // "Hello World"
二、字符串常用操作方法
2.1 基本查询方法
string text = "C# String Operations";
// 获取长度
int length = text.Length; // 19
// 访问字符
char firstChar = text[0]; // 'C'
// 检查是否包含
bool contains = text.Contains("String"); // true
// 检查开头/结尾
bool startsWith = text.StartsWith("C#"); // true
bool endsWith = text.EndsWith("Operations"); // true
// 查找位置
int index = text.IndexOf("Str"); // 3
int lastIndex = text.LastIndexOf('o'); // 16
2.2 字符串修改方法
string original = " Hello World ";
// 去除空白
string trimmed = original.Trim(); // "Hello World"
// 大小写转换
string upper = original.ToUpper(); // " HELLO WORLD "
string lower = original.ToLower(); // " hello world "
// 替换内容
string replaced = original.Replace("World", "C#"); // " Hello C# "
// 插入内容
string inserted = original.Insert(5, "Beautiful "); // " Hello Beautiful World "
// 移除内容
string removed = original.Remove(5, 6); // " Hello "
2.3 字符串分割与连接
// 分割字符串
string csv = "apple,orange,banana,grape";
string[] fruits = csv.Split(','); // ["apple", "orange", "banana", "grape"]
// 使用多个分隔符
string text = "apple;orange,banana-grape";
char[] delimiters = { ';', ',', '-' };
string[] fruits2 = text.Split(delimiters);
// 连接字符串数组
string joined = string.Join(" | ", fruits); // "apple | orange | banana | grape"
三、字符串比较与相等性
3.1 比较方法对比
方法 | 区分大小写 | 文化敏感性 | 推荐场景 |
---|---|---|---|
== 运算符 | 是 | 是 | 一般比较 |
Equals() | 可配置 | 可配置 | 精确比较 |
Compare() | 可配置 | 可配置 | 排序 |
CompareOrdinal() | 是 | 否 | 性能敏感场景 |
3.2 实际应用示例
string a = "hello";
string b = "HELLO";
// 区分大小写的比较
bool equal1 = a.Equals(b); // false
bool equal2 = a.Equals(b, StringComparison.OrdinalIgnoreCase); // true
// 文化敏感的比较
bool equal3 = string.Compare(a, b, CultureInfo.CurrentCulture,
CompareOptions.IgnoreCase) == 0; // true
// 性能最优的比较
bool equal4 = string.Equals(a, b, StringComparison.OrdinalIgnoreCase); // true
四、字符串格式化
4.1 传统格式化方法
// String.Format
string formatted = string.Format("Today is {0:yyyy-MM-dd}, temperature is {1}°C",
DateTime.Now, 23.5);
// 复合格式化
string name = "Alice";
int age = 30;
string message = $"My name is {name} and I'm {age} years old";
// 数字格式化
double value = 12345.6789;
string numStr = value.ToString("C"); // "$12,345.68"
string numStr2 = value.ToString("0.00"); // "12345.68"
4.2 字符串插值(C# 6.0+)
var user = new { Name = "Bob", Age = 25 };
// 基本插值
string info = $"{user.Name} is {user.Age} years old";
// 格式化表达式
string price = $"Price: {123.456:C2}"; // "Price: $123.46"
// 对齐和格式化
string table = $"{user.Name,-10} | {user.Age,5}";
五、高性能字符串处理
5.1 StringBuilder的使用
var sb = new StringBuilder(100); // 预分配容量
// 追加内容
sb.Append("Hello");
sb.AppendLine(" World!");
sb.AppendFormat("Today is {0:yyyy-MM-dd}", DateTime.Now);
// 插入和移除
sb.Insert(5, " Beautiful");
sb.Remove(5, 10);
// 获取结果
string result = sb.ToString();
5.2 Span优化(C# 7.2+)
string largeText = GetLargeText();
// 使用Span避免分配
ReadOnlySpan<char> span = largeText.AsSpan();
var slice = span.Slice(start: 5, length: 10);
// 处理子字符串而不分配新内存
foreach (ref readonly char c in slice)
{
// 处理字符
}
六、正则表达式应用
6.1 基本匹配与替换
using System.Text.RegularExpressions;
string input = "Order #1234 placed on 2023-05-15";
// 匹配
Match match = Regex.Match(input, @"#(\d+)");
if (match.Success)
{
string orderNumber = match.Groups[1].Value; // "1234"
}
// 替换
string anonymized = Regex.Replace(input, @"\d{4}-\d{2}-\d{2}", "[DATE]");
// "Order #1234 placed on [DATE]"
6.2 高效正则表达式实践
// 预编译正则表达式(性能敏感场景)
private static readonly Regex OrderRegex =
new Regex(@"#(\d+)", RegexOptions.Compiled);
// 使用缓存的正则表达式
Match match = OrderRegex.Match(input);
// 使用RegexOptions提高性能
var regex = new Regex(pattern,
RegexOptions.IgnoreCase | RegexOptions.CultureInvariant);
七、编码与解码
7.1 常见编码转换
string text = "你好,世界";
// 转换为字节数组
byte[] utf8Bytes = Encoding.UTF8.GetBytes(text);
// 从字节数组还原
string decoded = Encoding.UTF8.GetString(utf8Bytes);
// 检测编码
Encoding detectedEncoding = DetectEncoding(someBytes);
7.2 Base64编码
// 字符串转Base64
string plainText = "Hello Base64";
string base64 = Convert.ToBase64String(Encoding.UTF8.GetBytes(plainText));
// Base64转字符串
string decodedText = Encoding.UTF8.GetString(Convert.FromBase64String(base64));
八、实用扩展方法
8.1 自定义字符串扩展
public static class StringExtensions
{
// 安全截断
public static string Truncate(this string value, int maxLength)
{
return string.IsNullOrEmpty(value)
? value
: value.Length <= maxLength
? value
: value.Substring(0, maxLength) + "...";
}
// 判断是否为数字
public static bool IsNumeric(this string value)
{
return double.TryParse(value, out _);
}
}
// 使用示例
string longText = "This is a very long text";
string shortText = longText.Truncate(10); // "This is a..."
九、常见陷阱与最佳实践
9.1 性能陷阱
- 字符串拼接:避免在循环中使用
+
拼接字符串
// 错误方式
string result = "";
for (int i = 0; i < 100; i++) {
result += i; // 每次循环都创建新字符串
}
// 正确方式
var sb = new StringBuilder();
for (int i = 0; i < 100; i++) {
sb.Append(i);
}
string result = sb.ToString();
- 不必要的分配:避免频繁创建子字符串
9.2 最佳实践
- 使用
StringComparison
指定比较规则 - 处理用户输入时考虑文化差异
- 对大量文本操作使用
StringBuilder
- 优先使用
string.IsNullOrEmpty()
和string.IsNullOrWhiteSpace()
进行检查 - 考虑使用
Memory<char>
或Span<char>
处理大文本
结语
C#提供了丰富而强大的字符串处理功能,从基本的操作到高级的模式匹配,能够满足各种文本处理需求。理解字符串的不可变性、掌握各种操作方法的特点和适用场景,对于编写高效、可靠的代码至关重要。
随着C#版本的更新,字符串处理也在不断进化,如插值字符串、Span<T>
支持等特性让字符串操作更加高效。希望本文介绍的各种方法和技巧能够帮助您在项目中更加得心应手地处理字符串相关任务。