学习目标
通过本章学习,您将掌握:
C# 9.0+ 新特性
- Record类型和模式匹配
- Init-only属性和顶级程序
- 目标类型new表达式
C# 10.0+ 新特性
- 全局using指令
- 文件范围命名空间
- 常量插值字符串
C# 11.0+ 新特性
- 原始字符串字面量
- 泛型特性
- 静态虚拟成员
C# 12.0+ 新特性
- 主构造函数
- 集合表达式
- 默认lambda参数
高级反射和元编程
- 源生成器
- 编译时代码生成
- 动态代码执行
内存管理高级技术
- Span
和Memory - 栈分配和unsafe代码
- 内存映射文件
- Span
高性能编程技术
- SIMD指令集
- 向量化计算
- 并行算法优化
22.1 C# 9.0+ 新特性
Record类型
using System;
using System.Collections.Generic;
using System.Linq;
// 基本Record类型
public record Person(string FirstName, string LastName, int Age)
{
// 计算属性
public string FullName => $"{FirstName} {LastName}";
// 自定义方法
public bool IsAdult() => Age >= 18;
// 验证
public Person
{
if (Age < 0) throw new ArgumentException("Age cannot be negative");
}
}
## 22.4 C# 12.0+ 新特性
### 主构造函数
```csharp
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
// 类的主构造函数
public class PersonService(ILogger<PersonService> logger, IPersonRepository repository)
{
private readonly List<Person> _cache = new();
public async Task<Person> GetPersonAsync(int id)
{
logger.LogInformation("Getting person with ID: {Id}", id);
var cached = _cache.FirstOrDefault(p => p.Id == id);
if (cached != null)
{
return cached;
}
var person = await repository.GetByIdAsync(id);
if (person != null)
{
_cache.Add(person);
}
return person;
}
public async Task<Person> CreatePersonAsync(CreatePersonRequest request)
{
logger.LogInformation("Creating new person: {Name}", request.FullName);
var person = new Person
{
FirstName = request.FirstName,
LastName = request.LastName,
Age = request.Age
};
var created = await repository.CreateAsync(person);
_cache.Add(created);
return created;
}
}
// 结构体的主构造函数
public readonly struct Vector3D(double x, double y, double z)
{
public double X { get; } = x;
public double Y { get; } = y;
public double Z { get; } = z;
public double Magnitude => Math.Sqrt(X * X + Y * Y + Z * Z);
public Vector3D Normalize()
{
var mag = Magnitude;
return mag == 0 ? new(0, 0, 0) : new(X / mag, Y / mag, Z / mag);
}
public static Vector3D operator +(Vector3D left, Vector3D right)
=> new(left.X + right.X, left.Y + right.Y, left.Z + right.Z);
public static Vector3D operator *(Vector3D vector, double scalar)
=> new(vector.X * scalar, vector.Y * scalar, vector.Z * scalar);
public override string ToString() => $"({X:F2}, {Y:F2}, {Z:F2})";
}
// 带验证的主构造函数
public class BankAccount(string accountNumber, string ownerName, decimal initialBalance)
{
public string AccountNumber { get; } = !string.IsNullOrWhiteSpace(accountNumber)
? accountNumber
: throw new ArgumentException("Account number cannot be empty", nameof(accountNumber));
public string OwnerName { get; } = !string.IsNullOrWhiteSpace(ownerName)
? ownerName
: throw new ArgumentException("Owner name cannot be empty", nameof(ownerName));
public decimal Balance { get; private set; } = initialBalance >= 0
? initialBalance
: throw new ArgumentException("Initial balance cannot be negative", nameof(initialBalance));
private readonly List<Transaction> _transactions = new();
public void Deposit(decimal amount)
{
if (amount <= 0)
throw new ArgumentException("Deposit amount must be positive", nameof(amount));
Balance += amount;
_transactions.Add(new Transaction(DateTime.UtcNow, "Deposit", amount, Balance));
}
public bool Withdraw(decimal amount)
{
if (amount <= 0)
throw new ArgumentException("Withdrawal amount must be positive", nameof(amount));
if (Balance < amount)
return false;
Balance -= amount;
_transactions.Add(new Transaction(DateTime.UtcNow, "Withdrawal", -amount, Balance));
return true;
}
public IReadOnlyList<Transaction> GetTransactionHistory() => _transactions.AsReadOnly();
}
public record Transaction(DateTime Timestamp, string Type, decimal Amount, decimal BalanceAfter);
// 依赖注入示例
public interface IPersonRepository
{
Task<Person> GetByIdAsync(int id);
Task<Person> CreateAsync(Person person);
Task<List<Person>> GetAllAsync();
}
public class CreatePersonRequest
{
[Required]
public string FirstName { get; set; }
[Required]
public string LastName { get; set; }
[Range(0, 150)]
public int Age { get; set; }
public string FullName => $"{FirstName} {LastName}";
}
// 扩展Person类
public class Person
{
public int Id { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
public int Age { get; set; }
public string FullName => $"{FirstName} {LastName}";
}
集合表达式
using System;
using System.Collections.Generic;
using System.Linq;
// 集合表达式示例
public class CollectionExpressions
{
public void DemonstrateCollectionExpressions()
{
// 数组集合表达式
int[] numbers = [1, 2, 3, 4, 5];
string[] names = ["Alice", "Bob", "Charlie"];
// List集合表达式
List<int> numberList = [10, 20, 30, 40, 50];
List<string> nameList = ["David", "Eve", "Frank"];
// 空集合
int[] emptyArray = [];
List<string> emptyList = [];
// 展开运算符
int[] moreNumbers = [..numbers, 6, 7, 8, ..numberList];
string[] allNames = [..names, "Grace", ..nameList, "Henry"];
// 条件集合表达式
bool includeExtra = true;
int[] conditionalNumbers = [1, 2, 3, ..(includeExtra ? [4, 5, 6] : [])];
// 嵌套集合
int[][] matrix = [
[1, 2, 3],
[4, 5, 6],
[7, 8, 9]
];
// 字典初始化(如果支持)
var keyValuePairs = [
new KeyValuePair<string, int>("one", 1),
new KeyValuePair<string, int>("two", 2),
new KeyValuePair<string, int>("three", 3)
];
Console.WriteLine($"Numbers: [{string.Join(", ", numbers)}]");
Console.WriteLine($"More numbers: [{string.Join(", ", moreNumbers)}]");
Console.WriteLine($"All names: [{string.Join(", ", allNames)}]");
Console.WriteLine($"Conditional: [{string.Join(", ", conditionalNumbers)}]");
}
// 方法参数中的集合表达式
public void ProcessNumbers(int[] numbers)
{
Console.WriteLine($"Processing {numbers.Length} numbers");
}
public void CallWithCollectionExpression()
{
ProcessNumbers([1, 2, 3, 4, 5]);
var baseNumbers = new[] { 10, 20, 30 };
ProcessNumbers([..baseNumbers, 40, 50]);
}
// 返回集合表达式
public int[] GetFibonacci(int count)
{
if (count <= 0) return [];
if (count == 1) return [1];
if (count == 2) return [1, 1];
var result = new List<int> { 1, 1 };
for (int i = 2; i < count; i++)
{
result.Add(result[i - 1] + result[i - 2]);
}
return [..result];
}
public string[] GetFilteredNames(string[] input, string filter)
{
return [..input.Where(name => name.Contains(filter, StringComparison.OrdinalIgnoreCase))];
}
}
// 自定义集合类型支持
public class CustomCollection<T> : IEnumerable<T>
{
private readonly List<T> _items = new();
public void Add(T item) => _items.Add(item);
public void AddRange(IEnumerable<T> items) => _items.AddRange(items);
public IEnumerator<T> GetEnumerator() => _items.GetEnumerator();
System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator() => GetEnumerator();
public int Count => _items.Count;
public T this[int index] => _items[index];
}
// 集合表达式与自定义类型
public class CustomCollectionExamples
{
public void DemonstrateCustomCollections()
{
// 如果CustomCollection支持集合表达式语法
var custom = new CustomCollection<int>();
custom.AddRange([1, 2, 3, 4, 5]);
var moreItems = new[] { 6, 7, 8 };
custom.AddRange(moreItems);
Console.WriteLine($"Custom collection has {custom.Count} items");
}
}
默认Lambda参数
using System;
using System.Collections.Generic;
using System.Linq;
// 默认Lambda参数示例
public class DefaultLambdaParameters
{
public void DemonstrateLambdaDefaults()
{
// 带默认参数的Lambda表达式
var greet = (string name = "World") => $"Hello, {name}!";
Console.WriteLine(greet()); // "Hello, World!"
Console.WriteLine(greet("Alice")); // "Hello, Alice!"
// 多个默认参数
var calculate = (int x, int y = 1, int z = 0) => x * y + z;
Console.WriteLine(calculate(5)); // 5 * 1 + 0 = 5
Console.WriteLine(calculate(5, 3)); // 5 * 3 + 0 = 15
Console.WriteLine(calculate(5, 3, 2)); // 5 * 3 + 2 = 17
// 异步Lambda的默认参数
var fetchData = async (string url = "https://api.example.com", int timeout = 5000) =>
{
await Task.Delay(100); // 模拟网络请求
return $"Data from {url} (timeout: {timeout}ms)";
};
// 使用默认参数
var result1 = await fetchData();
var result2 = await fetchData("https://custom.api.com");
var result3 = await fetchData(timeout: 10000);
Console.WriteLine(result1);
Console.WriteLine(result2);
Console.WriteLine(result3);
}
// 在LINQ中使用默认Lambda参数
public void DemonstrateLinqWithDefaults()
{
var numbers = new[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
// 带默认参数的过滤
var filter = (int value, int threshold = 5) => value > threshold;
var filtered = numbers.Where(x => filter(x)).ToArray();
Console.WriteLine($"Numbers > 5: [{string.Join(", ", filtered)}]");
// 带默认参数的转换
var transform = (int value, int multiplier = 2, int offset = 0) => value * multiplier + offset;
var transformed = numbers.Select(x => transform(x)).ToArray();
Console.WriteLine($"Transformed: [{string.Join(", ", transformed)}]");
// 自定义转换
var customTransformed = numbers.Select(x => transform(x, 3, 1)).ToArray();
Console.WriteLine($"Custom transformed: [{string.Join(", ", customTransformed)}]");
}
// 事件处理中的默认Lambda参数
public void DemonstrateEventHandling()
{
var eventHandler = (string message = "Default event", DateTime? timestamp = null) =>
{
var time = timestamp ?? DateTime.Now;
Console.WriteLine($"[{time:HH:mm:ss}] {message}");
};
// 不同的调用方式
eventHandler();
eventHandler("Custom message");
eventHandler(timestamp: DateTime.Now.AddMinutes(-5));
eventHandler("Historical event", DateTime.Now.AddHours(-1));
}
// 配置Lambda的默认参数
public void DemonstrateConfigurationLambdas()
{
// 配置构建器模式
var configureLogging = (bool enableConsole = true, bool enableFile = false, string logLevel = "Info") =>
{
var config = new Dictionary<string, object>
{
["Console"] = enableConsole,
["File"] = enableFile,
["Level"] = logLevel
};
return config;
};
// 不同的配置
var defaultConfig = configureLogging();
var fileConfig = configureLogging(enableFile: true);
var debugConfig = configureLogging(logLevel: "Debug");
var fullConfig = configureLogging(true, true, "Trace");
PrintConfig("Default", defaultConfig);
PrintConfig("File enabled", fileConfig);
PrintConfig("Debug level", debugConfig);
PrintConfig("Full config", fullConfig);
}
private void PrintConfig(string name, Dictionary<string, object> config)
{
Console.WriteLine($"{name}: {string.Join(", ", config.Select(kvp => $"{kvp.Key}={kvp.Value}"))}");
}
}
// 函数式编程中的默认参数
public static class FunctionalHelpers
{
public static Func<T, bool> CreatePredicate<T>(Func<T, bool> condition, bool defaultResult = false)
{
return item => condition?.Invoke(item) ?? defaultResult;
}
public static Func<T, TResult> CreateMapper<T, TResult>(Func<T, TResult> mapper, TResult defaultValue = default)
{
return item => mapper != null ? mapper(item) : defaultValue;
}
// 使用默认参数的高阶函数
public static IEnumerable<TResult> ProcessItems<T, TResult>(
IEnumerable<T> items,
Func<T, bool> filter = null,
Func<T, TResult> mapper = null,
TResult defaultValue = default)
{
var predicate = CreatePredicate(filter, true);
var transform = CreateMapper(mapper, defaultValue);
return items.Where(predicate).Select(transform);
}
}
22.5 高级反射和元编程
源生成器
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.CSharp;
using Microsoft.CodeAnalysis.CSharp.Syntax;
using Microsoft.CodeAnalysis.Text;
// 源生成器特性
[AttributeUsage(AttributeTargets.Class)]
public class AutoNotifyAttribute : Attribute
{
public string[] Properties { get; }
public AutoNotifyAttribute(params string[] properties)
{
Properties = properties;
}
}
// 序列化特性
[AttributeUsage(AttributeTargets.Class)]
public class AutoSerializableAttribute : Attribute
{
public bool IncludePrivateFields { get; set; }
public string[] ExcludeProperties { get; set; } = Array.Empty<string>();
}
// 源生成器实现
[Generator]
public class AutoNotifyGenerator : ISourceGenerator
{
public void Initialize(GeneratorInitializationContext context)
{
context.RegisterForSyntaxNotifications(() => new AutoNotifySyntaxReceiver());
}
public void Execute(GeneratorExecutionContext context)
{
if (context.SyntaxReceiver is not AutoNotifySyntaxReceiver receiver)
return;
foreach (var classDeclaration in receiver.CandidateClasses)
{
var model = context.Compilation.GetSemanticModel(classDeclaration.SyntaxTree);
var classSymbol = model.GetDeclaredSymbol(classDeclaration);
if (classSymbol == null)
continue;
var autoNotifyAttribute = classSymbol.GetAttributes()
.FirstOrDefault(attr => attr.AttributeClass?.Name == "AutoNotifyAttribute");
if (autoNotifyAttribute == null)
continue;
var source = GenerateNotifyPropertyChanged(classSymbol, autoNotifyAttribute);
context.AddSource($"{classSymbol.Name}.AutoNotify.g.cs", SourceText.From(source, Encoding.UTF8));
}
}
private string GenerateNotifyPropertyChanged(INamedTypeSymbol classSymbol, AttributeData attribute)
{
var namespaceName = classSymbol.ContainingNamespace.ToDisplayString();
var className = classSymbol.Name;
var properties = new List<string>();
// 从特性参数获取属性名
if (attribute.ConstructorArguments.Length > 0)
{
var propertiesArg = attribute.ConstructorArguments[0];
if (propertiesArg.Kind == TypedConstantKind.Array)
{
properties.AddRange(propertiesArg.Values.Select(v => v.Value?.ToString()).Where(v => v != null));
}
}
var sourceBuilder = new StringBuilder();
sourceBuilder.AppendLine("using System.ComponentModel;");
sourceBuilder.AppendLine("using System.Runtime.CompilerServices;");
sourceBuilder.AppendLine();
sourceBuilder.AppendLine($"namespace {namespaceName}");
sourceBuilder.AppendLine("{");
sourceBuilder.AppendLine($" public partial class {className} : INotifyPropertyChanged");
sourceBuilder.AppendLine(" {");
sourceBuilder.AppendLine(" public event PropertyChangedEventHandler PropertyChanged;");
sourceBuilder.AppendLine();
sourceBuilder.AppendLine(" protected virtual void OnPropertyChanged([CallerMemberName] string propertyName = null)");
sourceBuilder.AppendLine(" {");
sourceBuilder.AppendLine(" PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));");
sourceBuilder.AppendLine(" }");
sourceBuilder.AppendLine();
sourceBuilder.AppendLine(" protected bool SetProperty<T>(ref T field, T value, [CallerMemberName] string propertyName = null)");
sourceBuilder.AppendLine(" {");
sourceBuilder.AppendLine(" if (EqualityComparer<T>.Default.Equals(field, value))");
sourceBuilder.AppendLine(" return false;");
sourceBuilder.AppendLine();
sourceBuilder.AppendLine(" field = value;");
sourceBuilder.AppendLine(" OnPropertyChanged(propertyName);");
sourceBuilder.AppendLine(" return true;");
sourceBuilder.AppendLine(" }");
// 为每个指定的属性生成backing field和属性
foreach (var property in properties)
{
var fieldName = $"_{char.ToLower(property[0])}{property.Substring(1)}";
sourceBuilder.AppendLine();
sourceBuilder.AppendLine($" private object {fieldName};");
sourceBuilder.AppendLine($" public object {property}");
sourceBuilder.AppendLine(" {");
sourceBuilder.AppendLine($" get => {fieldName};");
sourceBuilder.AppendLine($" set => SetProperty(ref {fieldName}, value);");
sourceBuilder.AppendLine(" }");
}
sourceBuilder.AppendLine(" }");
sourceBuilder.AppendLine("}");
return sourceBuilder.ToString();
}
}
// 语法接收器
public class AutoNotifySyntaxReceiver : ISyntaxReceiver
{
public List<ClassDeclarationSyntax> CandidateClasses { get; } = new();
public void OnVisitSyntaxNode(SyntaxNode syntaxNode)
{
if (syntaxNode is ClassDeclarationSyntax classDeclaration &&
classDeclaration.AttributeLists.Count > 0)
{
CandidateClasses.Add(classDeclaration);
}
}
}
// 序列化源生成器
[Generator]
public class AutoSerializationGenerator : ISourceGenerator
{
public void Initialize(GeneratorInitializationContext context)
{
context.RegisterForSyntaxNotifications(() => new AutoSerializationSyntaxReceiver());
}
public void Execute(GeneratorExecutionContext context)
{
if (context.SyntaxReceiver is not AutoSerializationSyntaxReceiver receiver)
return;
foreach (var classDeclaration in receiver.CandidateClasses)
{
var model = context.Compilation.GetSemanticModel(classDeclaration.SyntaxTree);
var classSymbol = model.GetDeclaredSymbol(classDeclaration);
if (classSymbol == null)
continue;
var autoSerializableAttribute = classSymbol.GetAttributes()
.FirstOrDefault(attr => attr.AttributeClass?.Name == "AutoSerializableAttribute");
if (autoSerializableAttribute == null)
continue;
var source = GenerateSerializationMethods(classSymbol, autoSerializableAttribute);
context.AddSource($"{classSymbol.Name}.AutoSerialization.g.cs", SourceText.From(source, Encoding.UTF8));
}
}
private string GenerateSerializationMethods(INamedTypeSymbol classSymbol, AttributeData attribute)
{
var namespaceName = classSymbol.ContainingNamespace.ToDisplayString();
var className = classSymbol.Name;
// 获取配置
bool includePrivateFields = false;
var excludeProperties = new HashSet<string>();
foreach (var namedArg in attribute.NamedArguments)
{
switch (namedArg.Key)
{
case "IncludePrivateFields":
includePrivateFields = (bool)namedArg.Value.Value;
break;
case "ExcludeProperties":
if (namedArg.Value.Kind == TypedConstantKind.Array)
{
excludeProperties.UnionWith(namedArg.Value.Values.Select(v => v.Value?.ToString()).Where(v => v != null));
}
break;
}
}
var sourceBuilder = new StringBuilder();
sourceBuilder.AppendLine("using System;");
sourceBuilder.AppendLine("using System.Text.Json;");
sourceBuilder.AppendLine("using System.Collections.Generic;");
sourceBuilder.AppendLine();
sourceBuilder.AppendLine($"namespace {namespaceName}");
sourceBuilder.AppendLine("{");
sourceBuilder.AppendLine($" public partial class {className}");
sourceBuilder.AppendLine(" {");
// 生成ToJson方法
sourceBuilder.AppendLine(" public string ToJson()");
sourceBuilder.AppendLine(" {");
sourceBuilder.AppendLine(" var options = new JsonSerializerOptions");
sourceBuilder.AppendLine(" {");
sourceBuilder.AppendLine(" PropertyNamingPolicy = JsonNamingPolicy.CamelCase,");
sourceBuilder.AppendLine(" WriteIndented = true");
sourceBuilder.AppendLine(" };");
sourceBuilder.AppendLine(" return JsonSerializer.Serialize(this, options);");
sourceBuilder.AppendLine(" }");
sourceBuilder.AppendLine();
// 生成FromJson方法
sourceBuilder.AppendLine($" public static {className} FromJson(string json)");
sourceBuilder.AppendLine(" {");
sourceBuilder.AppendLine(" var options = new JsonSerializerOptions");
sourceBuilder.AppendLine(" {");
sourceBuilder.AppendLine(" PropertyNamingPolicy = JsonNamingPolicy.CamelCase");
sourceBuilder.AppendLine(" };");
sourceBuilder.AppendLine($" return JsonSerializer.Deserialize<{className}>(json, options);");
sourceBuilder.AppendLine(" }");
sourceBuilder.AppendLine();
// 生成ToDictionary方法
sourceBuilder.AppendLine(" public Dictionary<string, object> ToDictionary()");
sourceBuilder.AppendLine(" {");
sourceBuilder.AppendLine(" var result = new Dictionary<string, object>();");
// 添加属性
var properties = classSymbol.GetMembers().OfType<IPropertySymbol>()
.Where(p => p.DeclaredAccessibility == Accessibility.Public &&
!excludeProperties.Contains(p.Name));
foreach (var property in properties)
{
sourceBuilder.AppendLine($" result[\"{property.Name}\"] = {property.Name};");
}
sourceBuilder.AppendLine(" return result;");
sourceBuilder.AppendLine(" }");
sourceBuilder.AppendLine(" }");
sourceBuilder.AppendLine("}");
return sourceBuilder.ToString();
}
}
public class AutoSerializationSyntaxReceiver : ISyntaxReceiver
{
public List<ClassDeclarationSyntax> CandidateClasses { get; } = new();
public void OnVisitSyntaxNode(SyntaxNode syntaxNode)
{
if (syntaxNode is ClassDeclarationSyntax classDeclaration &&
classDeclaration.AttributeLists.Count > 0)
{
CandidateClasses.Add(classDeclaration);
}
}
}
// 使用源生成器的示例类
[AutoNotify("Name", "Age", "Email")]
[AutoSerializable(IncludePrivateFields = false, ExcludeProperties = new[] { "InternalId" })]
public partial class GeneratedPerson
{
public int InternalId { get; set; }
public DateTime CreatedAt { get; set; } = DateTime.UtcNow;
// 源生成器将为Name、Age、Email生成属性和通知逻辑
// 源生成器将生成序列化方法
}
// 使用示例
public class SourceGeneratorExamples
{
public void DemonstrateSourceGenerators()
{
var person = new GeneratedPerson
{
InternalId = 123,
CreatedAt = DateTime.Now
};
// 使用生成的属性(带通知)
person.PropertyChanged += (sender, e) =>
Console.WriteLine($"Property {e.PropertyName} changed");
person.Name = "John Doe";
person.Age = 30;
person.Email = "john@example.com";
// 使用生成的序列化方法
var json = person.ToJson();
Console.WriteLine($"JSON: {json}");
var dictionary = person.ToDictionary();
Console.WriteLine($"Dictionary: {string.Join(", ", dictionary.Select(kvp => $"{kvp.Key}={kvp.Value}"))}");
// 反序列化
var restored = GeneratedPerson.FromJson(json);
Console.WriteLine($"Restored: {restored.Name}, {restored.Age}, {restored.Email}");
}
}
高级反射技术
using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Reflection.Emit;
using System.Runtime.CompilerServices;
using System.Linq.Expressions;
// 高性能反射缓存
public static class ReflectionCache
{
private static readonly ConcurrentDictionary<string, PropertyInfo> _propertyCache = new();
private static readonly ConcurrentDictionary<string, MethodInfo> _methodCache = new();
private static readonly ConcurrentDictionary<Type, Func<object>> _constructorCache = new();
private static readonly ConcurrentDictionary<PropertyInfo, Func<object, object>> _getterCache = new();
private static readonly ConcurrentDictionary<PropertyInfo, Action<object, object>> _setterCache = new();
public static PropertyInfo GetProperty(Type type, string propertyName)
{
var key = $"{type.FullName}.{propertyName}";
return _propertyCache.GetOrAdd(key, _ => type.GetProperty(propertyName));
}
public static MethodInfo GetMethod(Type type, string methodName, Type[] parameterTypes = null)
{
var key = $"{type.FullName}.{methodName}({string.Join(",", parameterTypes?.Select(t => t.Name) ?? Array.Empty<string>())})";
return _methodCache.GetOrAdd(key, _ =>
parameterTypes == null ? type.GetMethod(methodName) : type.GetMethod(methodName, parameterTypes));
}
public static Func<object> GetConstructor(Type type)
{
return _constructorCache.GetOrAdd(type, t =>
{
var constructor = t.GetConstructor(Type.EmptyTypes);
if (constructor == null)
throw new InvalidOperationException($"Type {t.Name} does not have a parameterless constructor");
var lambda = Expression.Lambda<Func<object>>(Expression.New(constructor));
return lambda.Compile();
});
}
public static Func<object, object> GetPropertyGetter(PropertyInfo property)
{
return _getterCache.GetOrAdd(property, prop =>
{
var instance = Expression.Parameter(typeof(object), "instance");
var convert = Expression.Convert(instance, prop.DeclaringType);
var propertyAccess = Expression.Property(convert, prop);
var convertResult = Expression.Convert(propertyAccess, typeof(object));
var lambda = Expression.Lambda<Func<object, object>>(convertResult, instance);
return lambda.Compile();
});
}
public static Action<object, object> GetPropertySetter(PropertyInfo property)
{
return _setterCache.GetOrAdd(property, prop =>
{
var instance = Expression.Parameter(typeof(object), "instance");
var value = Expression.Parameter(typeof(object), "value");
var convert = Expression.Convert(instance, prop.DeclaringType);
var convertValue = Expression.Convert(value, prop.PropertyType);
var propertyAccess = Expression.Property(convert, prop);
var assign = Expression.Assign(propertyAccess, convertValue);
var lambda = Expression.Lambda<Action<object, object>>(assign, instance, value);
return lambda.Compile();
});
}
}
// 动态类型构建器
public class DynamicTypeBuilder
{
private readonly AssemblyBuilder _assemblyBuilder;
private readonly ModuleBuilder _moduleBuilder;
public DynamicTypeBuilder(string assemblyName)
{
var assemblyBuilderName = new AssemblyName(assemblyName);
_assemblyBuilder = AssemblyBuilder.DefineDynamicAssembly(assemblyBuilderName, AssemblyBuilderAccess.Run);
_moduleBuilder = _assemblyBuilder.DefineDynamicModule("MainModule");
}
public Type CreateType(string typeName, Dictionary<string, Type> properties)
{
var typeBuilder = _moduleBuilder.DefineType(typeName,
TypeAttributes.Public | TypeAttributes.Class | TypeAttributes.AutoClass | TypeAttributes.AnsiClass | TypeAttributes.BeforeFieldInit | TypeAttributes.AutoLayout,
null);
// 添加属性
foreach (var property in properties)
{
AddProperty(typeBuilder, property.Key, property.Value);
}
// 添加ToString重写
AddToStringMethod(typeBuilder, properties.Keys);
return typeBuilder.CreateType();
}
private void AddProperty(TypeBuilder typeBuilder, string propertyName, Type propertyType)
{
var fieldBuilder = typeBuilder.DefineField($"_{propertyName.ToLower()}", propertyType, FieldAttributes.Private);
var propertyBuilder = typeBuilder.DefineProperty(propertyName, PropertyAttributes.HasDefault, propertyType, null);
// Getter
var getMethodBuilder = typeBuilder.DefineMethod($"get_{propertyName}",
MethodAttributes.Public | MethodAttributes.SpecialName | MethodAttributes.HideBySig,
propertyType, Type.EmptyTypes);
var getIL = getMethodBuilder.GetILGenerator();
getIL.Emit(OpCodes.Ldarg_0);
getIL.Emit(OpCodes.Ldfld, fieldBuilder);
getIL.Emit(OpCodes.Ret);
// Setter
var setMethodBuilder = typeBuilder.DefineMethod($"set_{propertyName}",
MethodAttributes.Public | MethodAttributes.SpecialName | MethodAttributes.HideBySig,
null, new[] { propertyType });
var setIL = setMethodBuilder.GetILGenerator();
setIL.Emit(OpCodes.Ldarg_0);
setIL.Emit(OpCodes.Ldarg_1);
setIL.Emit(OpCodes.Stfld, fieldBuilder);
setIL.Emit(OpCodes.Ret);
propertyBuilder.SetGetMethod(getMethodBuilder);
propertyBuilder.SetSetMethod(setMethodBuilder);
}
private void AddToStringMethod(TypeBuilder typeBuilder, IEnumerable<string> propertyNames)
{
var toStringMethod = typeBuilder.DefineMethod("ToString",
MethodAttributes.Public | MethodAttributes.ReuseSlot | MethodAttributes.Virtual | MethodAttributes.HideBySig,
typeof(string), Type.EmptyTypes);
var il = toStringMethod.GetILGenerator();
// 构建字符串格式
var format = string.Join(", ", propertyNames.Select(name => $"{name}: {{{propertyNames.ToList().IndexOf(name)}}}"));
il.Emit(OpCodes.Ldstr, format);
il.Emit(OpCodes.Ldc_I4, propertyNames.Count());
il.Emit(OpCodes.Newarr, typeof(object));
int index = 0;
foreach (var propertyName in propertyNames)
{
il.Emit(OpCodes.Dup);
il.Emit(OpCodes.Ldc_I4, index);
il.Emit(OpCodes.Ldarg_0);
il.Emit(OpCodes.Call, typeBuilder.GetMethod($"get_{propertyName}"));
if (typeBuilder.GetProperty(propertyName).PropertyType.IsValueType)
{
il.Emit(OpCodes.Box, typeBuilder.GetProperty(propertyName).PropertyType);
}
il.Emit(OpCodes.Stelem_Ref);
index++;
}
il.Emit(OpCodes.Call, typeof(string).GetMethod("Format", new[] { typeof(string), typeof(object[]) }));
il.Emit(OpCodes.Ret);
}
}
// 对象映射器
public static class ObjectMapper
{
private static readonly ConcurrentDictionary<(Type, Type), Func<object, object>> _mapperCache = new();
public static TTarget Map<TSource, TTarget>(TSource source) where TTarget : new()
{
return (TTarget)Map(source, typeof(TSource), typeof(TTarget));
}
public static object Map(object source, Type sourceType, Type targetType)
{
if (source == null) return null;
var mapper = _mapperCache.GetOrAdd((sourceType, targetType), key => CreateMapper(key.Item1, key.Item2));
return mapper(source);
}
private static Func<object, object> CreateMapper(Type sourceType, Type targetType)
{
var sourceParam = Expression.Parameter(typeof(object), "source");
var sourceConverted = Expression.Convert(sourceParam, sourceType);
var targetConstructor = targetType.GetConstructor(Type.EmptyTypes);
if (targetConstructor == null)
throw new InvalidOperationException($"Target type {targetType.Name} must have a parameterless constructor");
var targetInstance = Expression.Variable(targetType, "target");
var createTarget = Expression.Assign(targetInstance, Expression.New(targetConstructor));
var assignments = new List<Expression> { createTarget };
var sourceProperties = sourceType.GetProperties(BindingFlags.Public | BindingFlags.Instance)
.Where(p => p.CanRead)
.ToDictionary(p => p.Name, p => p);
var targetProperties = targetType.GetProperties(BindingFlags.Public | BindingFlags.Instance)
.Where(p => p.CanWrite);
foreach (var targetProp in targetProperties)
{
if (sourceProperties.TryGetValue(targetProp.Name, out var sourceProp) &&
IsAssignable(sourceProp.PropertyType, targetProp.PropertyType))
{
var sourceValue = Expression.Property(sourceConverted, sourceProp);
var targetProperty = Expression.Property(targetInstance, targetProp);
Expression assignValue = sourceValue;
if (sourceProp.PropertyType != targetProp.PropertyType)
{
assignValue = Expression.Convert(sourceValue, targetProp.PropertyType);
}
assignments.Add(Expression.Assign(targetProperty, assignValue));
}
}
assignments.Add(Expression.Convert(targetInstance, typeof(object)));
var block = Expression.Block(new[] { targetInstance }, assignments);
var lambda = Expression.Lambda<Func<object, object>>(block, sourceParam);
return lambda.Compile();
}
private static bool IsAssignable(Type sourceType, Type targetType)
{
return targetType.IsAssignableFrom(sourceType) ||
(sourceType.IsValueType && targetType.IsValueType &&
Nullable.GetUnderlyingType(targetType) == sourceType) ||
(Nullable.GetUnderlyingType(sourceType) == targetType);
}
}
// 表达式树构建器
public static class ExpressionBuilder
{
public static Expression<Func<T, bool>> BuildPredicate<T>(string propertyName, object value, ComparisonOperator op)
{
var parameter = Expression.Parameter(typeof(T), "x");
var property = Expression.Property(parameter, propertyName);
var constant = Expression.Constant(value, property.Type);
Expression comparison = op switch
{
ComparisonOperator.Equal => Expression.Equal(property, constant),
ComparisonOperator.NotEqual => Expression.NotEqual(property, constant),
ComparisonOperator.GreaterThan => Expression.GreaterThan(property, constant),
ComparisonOperator.GreaterThanOrEqual => Expression.GreaterThanOrEqual(property, constant),
ComparisonOperator.LessThan => Expression.LessThan(property, constant),
ComparisonOperator.LessThanOrEqual => Expression.LessThanOrEqual(property, constant),
ComparisonOperator.Contains => Expression.Call(property, "Contains", null, constant),
_ => throw new ArgumentException($"Unsupported operator: {op}")
};
return Expression.Lambda<Func<T, bool>>(comparison, parameter);
}
public static Expression<Func<T, object>> BuildSelector<T>(string propertyName)
{
var parameter = Expression.Parameter(typeof(T), "x");
var property = Expression.Property(parameter, propertyName);
var converted = Expression.Convert(property, typeof(object));
return Expression.Lambda<Func<T, object>>(converted, parameter);
}
public static Expression<Func<T, bool>> CombinePredicates<T>(
Expression<Func<T, bool>> left,
Expression<Func<T, bool>> right,
LogicalOperator op)
{
var parameter = Expression.Parameter(typeof(T), "x");
var leftBody = ReplaceParameter(left.Body, left.Parameters[0], parameter);
var rightBody = ReplaceParameter(right.Body, right.Parameters[0], parameter);
Expression combined = op switch
{
LogicalOperator.And => Expression.AndAlso(leftBody, rightBody),
LogicalOperator.Or => Expression.OrElse(leftBody, rightBody),
_ => throw new ArgumentException($"Unsupported logical operator: {op}")
};
return Expression.Lambda<Func<T, bool>>(combined, parameter);
}
private static Expression ReplaceParameter(Expression expression, ParameterExpression oldParameter, ParameterExpression newParameter)
{
return new ParameterReplacer(oldParameter, newParameter).Visit(expression);
}
private class ParameterReplacer : ExpressionVisitor
{
private readonly ParameterExpression _oldParameter;
private readonly ParameterExpression _newParameter;
public ParameterReplacer(ParameterExpression oldParameter, ParameterExpression newParameter)
{
_oldParameter = oldParameter;
_newParameter = newParameter;
}
protected override Expression VisitParameter(ParameterExpression node)
{
return node == _oldParameter ? _newParameter : base.VisitParameter(node);
}
}
}
public enum ComparisonOperator
{
Equal,
NotEqual,
GreaterThan,
GreaterThanOrEqual,
LessThan,
LessThanOrEqual,
Contains
}
public enum LogicalOperator
{
And,
Or
}
// 使用示例
public class AdvancedReflectionExamples
{
public void DemonstrateReflectionCache()
{
var personType = typeof(Person);
// 缓存的属性访问
var nameProperty = ReflectionCache.GetProperty(personType, "FirstName");
var getter = ReflectionCache.GetPropertyGetter(nameProperty);
var setter = ReflectionCache.GetPropertySetter(nameProperty);
var person = new Person { FirstName = "John", LastName = "Doe", Age = 30 };
// 高性能属性访问
var name = getter(person);
Console.WriteLine($"Name: {name}");
setter(person, "Jane");
Console.WriteLine($"Updated name: {person.FirstName}");
}
public void DemonstrateDynamicTypeBuilder()
{
var builder = new DynamicTypeBuilder("DynamicAssembly");
var properties = new Dictionary<string, Type>
{
["Id"] = typeof(int),
["Name"] = typeof(string),
["CreatedAt"] = typeof(DateTime)
};
var dynamicType = builder.CreateType("DynamicEntity", properties);
// 创建实例
var constructor = ReflectionCache.GetConstructor(dynamicType);
var instance = constructor();
// 设置属性
var idSetter = ReflectionCache.GetPropertySetter(dynamicType.GetProperty("Id"));
var nameSetter = ReflectionCache.GetPropertySetter(dynamicType.GetProperty("Name"));
var dateSetter = ReflectionCache.GetPropertySetter(dynamicType.GetProperty("CreatedAt"));
idSetter(instance, 1);
nameSetter(instance, "Dynamic Entity");
dateSetter(instance, DateTime.Now);
Console.WriteLine($"Dynamic instance: {instance}");
}
public void DemonstrateObjectMapper()
{
var source = new Person { FirstName = "John", LastName = "Doe", Age = 30 };
// 映射到不同类型
var target = ObjectMapper.Map<Person, PersonDto>(source);
Console.WriteLine($"Mapped: {target.FirstName} {target.LastName}, Age: {target.Age}");
}
public void DemonstrateExpressionBuilder()
{
var people = new List<Person>
{
new() { FirstName = "John", LastName = "Doe", Age = 30 },
new() { FirstName = "Jane", LastName = "Smith", Age = 25 },
new() { FirstName = "Bob", LastName = "Johnson", Age = 35 }
};
// 动态构建查询条件
var agePredicate = ExpressionBuilder.BuildPredicate<Person>("Age", 30, ComparisonOperator.GreaterThan);
var namePredicate = ExpressionBuilder.BuildPredicate<Person>("FirstName", "J", ComparisonOperator.Contains);
var combinedPredicate = ExpressionBuilder.CombinePredicates(agePredicate, namePredicate, LogicalOperator.And);
var filtered = people.Where(combinedPredicate.Compile()).ToList();
Console.WriteLine($"Filtered results: {filtered.Count}");
foreach (var person in filtered)
{
Console.WriteLine($" {person.FirstName} {person.LastName}, Age: {person.Age}");
}
}
}
public class PersonDto
{
public string FirstName { get; set; }
public string LastName { get; set; }
public int Age { get; set; }
}
22.6 内存管理高级技术
Span 和 Memory
using System;
using System.Buffers;
using System.Runtime.InteropServices;
using System.Text;
// 高性能内存操作
public static class HighPerformanceMemoryOperations
{
// Span<T> 基本操作
public static void DemonstrateSpanOperations()
{
// 从数组创建Span
var array = new int[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
Span<int> span = array;
// 切片操作(零拷贝)
Span<int> slice = span.Slice(2, 5); // 从索引2开始,取5个元素
Console.WriteLine($"Original: [{string.Join(", ", array)}]");
Console.WriteLine($"Slice: [{string.Join(", ", slice.ToArray())}]");
// 修改slice会影响原数组
slice[0] = 100;
Console.WriteLine($"After modification: [{string.Join(", ", array)}]");
// 栈上分配(小数组)
Span<int> stackSpan = stackalloc int[10];
for (int i = 0; i < stackSpan.Length; i++)
{
stackSpan[i] = i * i;
}
Console.WriteLine($"Stack span: [{string.Join(", ", stackSpan.ToArray())}]");
}
// Memory<T> 异步操作
public static async Task DemonstrateMemoryOperations()
{
var buffer = new byte[1024];
Memory<byte> memory = buffer;
// 异步写入
await WriteToMemoryAsync(memory.Slice(0, 100));
// 异步读取
var result = await ReadFromMemoryAsync(memory.Slice(0, 100));
Console.WriteLine($"Read {result} bytes");
}
private static async Task WriteToMemoryAsync(Memory<byte> memory)
{
var data = Encoding.UTF8.GetBytes("Hello, Memory<T>!");
data.CopyTo(memory.Span);
await Task.Delay(10); // 模拟异步操作
}
private static async Task<int> ReadFromMemoryAsync(Memory<byte> memory)
{
await Task.Delay(10); // 模拟异步操作
return memory.Length;
}
// 字符串操作优化
public static void OptimizedStringOperations()
{
var text = "Hello, World! This is a test string for demonstration.";
ReadOnlySpan<char> span = text.AsSpan();
// 查找子字符串(无分配)
var index = span.IndexOf("World");
if (index >= 0)
{
var worldSpan = span.Slice(index, 5);
Console.WriteLine($"Found: {worldSpan.ToString()}");
}
// 分割字符串(无分配)
var parts = new List<ReadOnlySpan<char>>();
var remaining = span;
while (true)
{
var spaceIndex = remaining.IndexOf(' ');
if (spaceIndex == -1)
{
if (!remaining.IsEmpty)
parts.Add(remaining);
break;
}
parts.Add(remaining.Slice(0, spaceIndex));
remaining = remaining.Slice(spaceIndex + 1);
}
Console.WriteLine($"Split into {parts.Count} parts:");
foreach (var part in parts)
{
Console.WriteLine($" '{part.ToString()}'");
}
}
// 数值解析优化
public static void OptimizedNumberParsing()
{
var numberStrings = new[] { "123", "456", "789", "101112" };
foreach (var numStr in numberStrings)
{
ReadOnlySpan<char> span = numStr.AsSpan();
if (int.TryParse(span, out var number))
{
Console.WriteLine($"Parsed: {number}");
}
}
// 自定义数值解析
var customNumber = ParseCustomNumber("12345".AsSpan());
Console.WriteLine($"Custom parsed: {customNumber}");
}
private static int ParseCustomNumber(ReadOnlySpan<char> span)
{
int result = 0;
foreach (var c in span)
{
if (c >= '0' && c <= '9')
{
result = result * 10 + (c - '0');
}
}
return result;
}
}
// ArrayPool 使用
public class ArrayPoolExample
{
private static readonly ArrayPool<byte> _bytePool = ArrayPool<byte>.Shared;
private static readonly ArrayPool<char> _charPool = ArrayPool<char>.Shared;
public async Task ProcessLargeDataAsync()
{
// 租用数组而不是分配
var buffer = _bytePool.Rent(4096);
try
{
// 使用buffer进行操作
await SimulateDataProcessing(buffer.AsMemory(0, 1024));
}
finally
{
// 归还数组到池中
_bytePool.Return(buffer);
}
}
public string BuildLargeString(IEnumerable<string> parts)
{
var estimatedLength = parts.Sum(p => p.Length) + parts.Count() * 2;
var buffer = _charPool.Rent(estimatedLength);
try
{
var span = buffer.AsSpan();
var position = 0;
foreach (var part in parts)
{
part.AsSpan().CopyTo(span.Slice(position));
position += part.Length;
if (position < span.Length - 2)
{
span[position++] = ',';
span[position++] = ' ';
}
}
return new string(span.Slice(0, position));
}
finally
{
_charPool.Return(buffer);
}
}
private async Task SimulateDataProcessing(Memory<byte> buffer)
{
// 模拟数据处理
var random = new Random();
random.NextBytes(buffer.Span);
await Task.Delay(10);
}
}
// 内存映射文件
public class MemoryMappedFileExample
{
public unsafe void DemonstrateMemoryMappedFile()
{
var fileName = "test_data.bin";
var fileSize = 1024 * 1024; // 1MB
// 创建测试文件
using (var fs = File.Create(fileName))
{
fs.SetLength(fileSize);
}
try
{
using var mmf = MemoryMappedFile.CreateFromFile(fileName, FileMode.Open, "test", fileSize);
using var accessor = mmf.CreateViewAccessor(0, fileSize);
// 写入数据
for (int i = 0; i < 1000; i++)
{
accessor.Write(i * 4, i);
}
// 读取数据
var sum = 0;
for (int i = 0; i < 1000; i++)
{
sum += accessor.ReadInt32(i * 4);
}
Console.WriteLine($"Sum of first 1000 integers: {sum}");
// 使用指针直接访问
byte* ptr = null;
accessor.SafeMemoryMappedViewHandle.AcquirePointer(ref ptr);
try
{
var intPtr = (int*)ptr;
var directSum = 0;
for (int i = 0; i < 1000; i++)
{
directSum += intPtr[i];
}
Console.WriteLine($"Direct pointer sum: {directSum}");
}
finally
{
accessor.SafeMemoryMappedViewHandle.ReleasePointer();
}
}
finally
{
File.Delete(fileName);
}
}
}
// 非托管内存管理
public unsafe class UnmanagedMemoryExample
{
public void DemonstrateUnmanagedMemory()
{
var size = 1024;
// 分配非托管内存
var ptr = (byte*)Marshal.AllocHGlobal(size);
try
{
// 创建Span指向非托管内存
var span = new Span<byte>(ptr, size);
// 填充数据
for (int i = 0; i < size; i++)
{
span[i] = (byte)(i % 256);
}
// 计算校验和
var checksum = 0;
foreach (var b in span)
{
checksum += b;
}
Console.WriteLine($"Checksum: {checksum}");
// 使用NativeMemory(.NET 6+)
DemonstrateNativeMemory();
}
finally
{
Marshal.FreeHGlobal((IntPtr)ptr);
}
}
private void DemonstrateNativeMemory()
{
var size = (nuint)1024;
// 分配对齐的内存
var ptr = NativeMemory.AlignedAlloc(size, 64); // 64字节对齐
try
{
var span = new Span<byte>(ptr, (int)size);
// 零初始化
span.Clear();
// 设置一些值
for (int i = 0; i < 100; i++)
{
span[i] = (byte)i;
}
Console.WriteLine($"First 10 bytes: [{string.Join(", ", span.Slice(0, 10).ToArray())}]");
}
finally
{
NativeMemory.AlignedFree(ptr);
}
}
}
// 内存性能分析器
public class MemoryPerformanceAnalyzer
{
public void CompareMemoryOperations()
{
const int iterations = 1000000;
const int arraySize = 1000;
// 传统数组操作
var sw = Stopwatch.StartNew();
for (int i = 0; i < iterations; i++)
{
var array = new int[arraySize];
for (int j = 0; j < arraySize; j++)
{
array[j] = j;
}
}
sw.Stop();
Console.WriteLine($"Traditional array: {sw.ElapsedMilliseconds}ms");
// ArrayPool操作
var pool = ArrayPool<int>.Shared;
sw.Restart();
for (int i = 0; i < iterations; i++)
{
var array = pool.Rent(arraySize);
try
{
var span = array.AsSpan(0, arraySize);
for (int j = 0; j < arraySize; j++)
{
span[j] = j;
}
}
finally
{
pool.Return(array);
}
}
sw.Stop();
Console.WriteLine($"ArrayPool: {sw.ElapsedMilliseconds}ms");
// 栈分配(小数组)
sw.Restart();
for (int i = 0; i < iterations; i++)
{
Span<int> span = stackalloc int[100]; // 只能用于小数组
for (int j = 0; j < 100; j++)
{
span[j] = j;
}
}
sw.Stop();
Console.WriteLine($"Stack allocation: {sw.ElapsedMilliseconds}ms");
}
}
// 继承Record public record Employee(string FirstName, string LastName, int Age, string Department, decimal Salary) : Person(FirstName, LastName, Age);
## 22.7 高性能编程技术
### SIMD(单指令多数据)编程
```csharp
using System;
using System.Numerics;
using System.Runtime.Intrinsics;
using System.Runtime.Intrinsics.X86;
using System.Diagnostics;
// SIMD向量化操作
public static class SIMDOperations
{
// 向量化数组求和
public static float VectorSum(float[] array)
{
if (!Vector.IsHardwareAccelerated)
{
return array.Sum(); // 回退到标准实现
}
var vectorSize = Vector<float>.Count;
var sum = Vector<float>.Zero;
int i = 0;
for (; i <= array.Length - vectorSize; i += vectorSize)
{
var vector = new Vector<float>(array, i);
sum = Vector.Add(sum, vector);
}
// 处理剩余元素
float scalarSum = 0;
for (; i < array.Length; i++)
{
scalarSum += array[i];
}
// 将向量求和转换为标量
float vectorSum = 0;
for (int j = 0; j < vectorSize; j++)
{
vectorSum += sum[j];
}
return vectorSum + scalarSum;
}
// 向量化数组乘法
public static void VectorMultiply(float[] a, float[] b, float[] result)
{
if (a.Length != b.Length || a.Length != result.Length)
throw new ArgumentException("Arrays must have the same length");
if (!Vector.IsHardwareAccelerated)
{
for (int i = 0; i < a.Length; i++)
{
result[i] = a[i] * b[i];
}
return;
}
var vectorSize = Vector<float>.Count;
int i = 0;
for (; i <= a.Length - vectorSize; i += vectorSize)
{
var vectorA = new Vector<float>(a, i);
var vectorB = new Vector<float>(b, i);
var vectorResult = Vector.Multiply(vectorA, vectorB);
vectorResult.CopyTo(result, i);
}
// 处理剩余元素
for (; i < a.Length; i++)
{
result[i] = a[i] * b[i];
}
}
// 向量化矩阵乘法
public static void VectorMatrixMultiply(float[,] a, float[,] b, float[,] result)
{
int rows = a.GetLength(0);
int cols = b.GetLength(1);
int inner = a.GetLength(1);
if (inner != b.GetLength(0) || result.GetLength(0) != rows || result.GetLength(1) != cols)
throw new ArgumentException("Matrix dimensions are incompatible");
for (int i = 0; i < rows; i++)
{
for (int j = 0; j < cols; j++)
{
var sum = Vector<float>.Zero;
int k = 0;
if (Vector.IsHardwareAccelerated)
{
var vectorSize = Vector<float>.Count;
for (; k <= inner - vectorSize; k += vectorSize)
{
var vectorA = LoadVector(a, i, k, vectorSize);
var vectorB = LoadVector(b, k, j, vectorSize, true);
sum = Vector.Add(sum, Vector.Multiply(vectorA, vectorB));
}
}
// 处理剩余元素和向量求和
float scalarSum = 0;
for (; k < inner; k++)
{
scalarSum += a[i, k] * b[k, j];
}
// 将向量求和转换为标量
for (int v = 0; v < Vector<float>.Count; v++)
{
scalarSum += sum[v];
}
result[i, j] = scalarSum;
}
}
}
private static Vector<float> LoadVector(float[,] matrix, int row, int startCol, int count, bool transpose = false)
{
var values = new float[count];
for (int i = 0; i < count; i++)
{
values[i] = transpose ? matrix[startCol + i, row] : matrix[row, startCol + i];
}
return new Vector<float>(values);
}
// AVX2 特定优化(需要支持AVX2的CPU)
public static unsafe void AVX2Sum(float* data, int length, out float result)
{
result = 0;
if (!Avx2.IsSupported)
{
for (int i = 0; i < length; i++)
{
result += data[i];
}
return;
}
var sum = Vector256<float>.Zero;
int i = 0;
for (; i <= length - 8; i += 8)
{
var vector = Avx.LoadVector256(data + i);
sum = Avx.Add(sum, vector);
}
// 水平求和
var temp = Avx.HorizontalAdd(sum, sum);
temp = Avx.HorizontalAdd(temp, temp);
result = temp.GetElement(0) + temp.GetElement(4);
// 处理剩余元素
for (; i < length; i++)
{
result += data[i];
}
}
}
// 高性能数据结构
public struct HighPerformanceList<T> where T : unmanaged
{
private T[] _items;
private int _count;
public HighPerformanceList(int capacity)
{
_items = new T[capacity];
_count = 0;
}
public int Count => _count;
public int Capacity => _items.Length;
public ref T this[int index]
{
get
{
if (index >= _count)
throw new IndexOutOfRangeException();
return ref _items[index];
}
}
public void Add(T item)
{
if (_count >= _items.Length)
{
Resize();
}
_items[_count++] = item;
}
public Span<T> AsSpan() => _items.AsSpan(0, _count);
public ReadOnlySpan<T> AsReadOnlySpan() => _items.AsSpan(0, _count);
private void Resize()
{
var newCapacity = _items.Length * 2;
var newItems = new T[newCapacity];
_items.AsSpan(0, _count).CopyTo(newItems);
_items = newItems;
}
public void Clear() => _count = 0;
public bool Remove(T item)
{
var index = IndexOf(item);
if (index >= 0)
{
RemoveAt(index);
return true;
}
return false;
}
public void RemoveAt(int index)
{
if (index >= _count)
throw new IndexOutOfRangeException();
if (index < _count - 1)
{
_items.AsSpan(index + 1, _count - index - 1).CopyTo(_items.AsSpan(index));
}
_count--;
}
public int IndexOf(T item)
{
for (int i = 0; i < _count; i++)
{
if (_items[i].Equals(item))
return i;
}
return -1;
}
}
// 无锁数据结构
public class LockFreeQueue<T> where T : class
{
private class Node
{
public volatile T Data;
public volatile Node Next;
}
private volatile Node _head;
private volatile Node _tail;
public LockFreeQueue()
{
var dummy = new Node();
_head = _tail = dummy;
}
public void Enqueue(T item)
{
var newNode = new Node { Data = item };
while (true)
{
var tail = _tail;
var next = tail.Next;
if (tail == _tail) // 确保tail没有被其他线程修改
{
if (next == null)
{
// 尝试链接新节点
if (Interlocked.CompareExchange(ref tail.Next, newNode, null) == null)
{
// 成功链接,尝试移动tail
Interlocked.CompareExchange(ref _tail, newNode, tail);
break;
}
}
else
{
// 帮助其他线程移动tail
Interlocked.CompareExchange(ref _tail, next, tail);
}
}
}
}
public bool TryDequeue(out T result)
{
result = null;
while (true)
{
var head = _head;
var tail = _tail;
var next = head.Next;
if (head == _head) // 确保head没有被其他线程修改
{
if (head == tail)
{
if (next == null)
{
return false; // 队列为空
}
// 帮助其他线程移动tail
Interlocked.CompareExchange(ref _tail, next, tail);
}
else
{
if (next != null)
{
result = next.Data;
// 尝试移动head
if (Interlocked.CompareExchange(ref _head, next, head) == head)
{
return true;
}
}
}
}
}
}
}
// 高性能字符串构建器
public ref struct HighPerformanceStringBuilder
{
private Span<char> _buffer;
private int _position;
public HighPerformanceStringBuilder(Span<char> buffer)
{
_buffer = buffer;
_position = 0;
}
public void Append(ReadOnlySpan<char> value)
{
if (_position + value.Length > _buffer.Length)
throw new InvalidOperationException("Buffer overflow");
value.CopyTo(_buffer.Slice(_position));
_position += value.Length;
}
public void Append(char value)
{
if (_position >= _buffer.Length)
throw new InvalidOperationException("Buffer overflow");
_buffer[_position++] = value;
}
public void Append(int value)
{
Span<char> temp = stackalloc char[11]; // int.MaxValue has 10 digits
if (value.TryFormat(temp, out var charsWritten))
{
Append(temp.Slice(0, charsWritten));
}
}
public void AppendLine(ReadOnlySpan<char> value)
{
Append(value);
Append('\n');
}
public ReadOnlySpan<char> AsSpan() => _buffer.Slice(0, _position);
public override string ToString() => new string(_buffer.Slice(0, _position));
public void Clear() => _position = 0;
public int Length => _position;
public int Capacity => _buffer.Length;
}
// 性能基准测试
public class PerformanceBenchmarks
{
public void BenchmarkSIMDOperations()
{
const int arraySize = 1000000;
var array1 = new float[arraySize];
var array2 = new float[arraySize];
var result = new float[arraySize];
var random = new Random(42);
for (int i = 0; i < arraySize; i++)
{
array1[i] = (float)random.NextDouble();
array2[i] = (float)random.NextDouble();
}
// 标准实现
var sw = Stopwatch.StartNew();
for (int i = 0; i < arraySize; i++)
{
result[i] = array1[i] * array2[i];
}
sw.Stop();
Console.WriteLine($"Standard multiplication: {sw.ElapsedMilliseconds}ms");
// SIMD实现
sw.Restart();
SIMDOperations.VectorMultiply(array1, array2, result);
sw.Stop();
Console.WriteLine($"SIMD multiplication: {sw.ElapsedMilliseconds}ms");
// 求和基准测试
sw.Restart();
var standardSum = array1.Sum();
sw.Stop();
Console.WriteLine($"Standard sum: {sw.ElapsedMilliseconds}ms, Result: {standardSum}");
sw.Restart();
var simdSum = SIMDOperations.VectorSum(array1);
sw.Stop();
Console.WriteLine($"SIMD sum: {sw.ElapsedMilliseconds}ms, Result: {simdSum}");
}
public void BenchmarkDataStructures()
{
const int operations = 1000000;
// List<T> vs HighPerformanceList<T>
var list = new List<int>(operations);
var hpList = new HighPerformanceList<int>(operations);
var sw = Stopwatch.StartNew();
for (int i = 0; i < operations; i++)
{
list.Add(i);
}
sw.Stop();
Console.WriteLine($"List<T> add: {sw.ElapsedMilliseconds}ms");
sw.Restart();
for (int i = 0; i < operations; i++)
{
hpList.Add(i);
}
sw.Stop();
Console.WriteLine($"HighPerformanceList<T> add: {sw.ElapsedMilliseconds}ms");
// 访问性能
sw.Restart();
var sum1 = 0;
for (int i = 0; i < list.Count; i++)
{
sum1 += list[i];
}
sw.Stop();
Console.WriteLine($"List<T> access: {sw.ElapsedMilliseconds}ms, Sum: {sum1}");
sw.Restart();
var sum2 = 0;
for (int i = 0; i < hpList.Count; i++)
{
sum2 += hpList[i];
}
sw.Stop();
Console.WriteLine($"HighPerformanceList<T> access: {sw.ElapsedMilliseconds}ms, Sum: {sum2}");
}
public void BenchmarkStringBuilding()
{
const int iterations = 100000;
// StringBuilder
var sw = Stopwatch.StartNew();
var sb = new StringBuilder();
for (int i = 0; i < iterations; i++)
{
sb.Append("Item ");
sb.Append(i);
sb.AppendLine();
}
var result1 = sb.ToString();
sw.Stop();
Console.WriteLine($"StringBuilder: {sw.ElapsedMilliseconds}ms, Length: {result1.Length}");
// HighPerformanceStringBuilder
sw.Restart();
Span<char> buffer = new char[iterations * 20]; // 估算缓冲区大小
var hpsb = new HighPerformanceStringBuilder(buffer);
for (int i = 0; i < iterations; i++)
{
hpsb.Append("Item ");
hpsb.Append(i);
hpsb.Append('\n');
}
var result2 = hpsb.ToString();
sw.Stop();
Console.WriteLine($"HighPerformanceStringBuilder: {sw.ElapsedMilliseconds}ms, Length: {result2.Length}");
}
}
22.8 实践练习
练习1:高级特性综合应用
// 综合应用:构建一个高性能的数据处理管道
public class DataProcessingPipeline<T> where T : unmanaged
{
private readonly ArrayPool<T> _arrayPool;
private readonly LockFreeQueue<ProcessingTask<T>> _taskQueue;
private readonly CancellationTokenSource _cancellationTokenSource;
private readonly Task[] _workers;
public DataProcessingPipeline(int workerCount = Environment.ProcessorCount)
{
_arrayPool = ArrayPool<T>.Shared;
_taskQueue = new LockFreeQueue<ProcessingTask<T>>();
_cancellationTokenSource = new CancellationTokenSource();
_workers = new Task[workerCount];
for (int i = 0; i < workerCount; i++)
{
_workers[i] = Task.Run(WorkerLoop);
}
}
public async Task<ProcessingResult<TResult>> ProcessAsync<TResult>(
ReadOnlyMemory<T> data,
Func<ReadOnlySpan<T>, TResult> processor,
CancellationToken cancellationToken = default) where TResult : class
{
var tcs = new TaskCompletionSource<TResult>();
var task = new ProcessingTask<T>
{
Data = data,
Processor = span => processor(span),
CompletionSource = tcs
};
_taskQueue.Enqueue(task);
try
{
var result = await tcs.Task.ConfigureAwait(false);
return new ProcessingResult<TResult>
{
Success = true,
Result = result,
ProcessedAt = DateTime.UtcNow
};
}
catch (Exception ex)
{
return new ProcessingResult<TResult>
{
Success = false,
Error = ex,
ProcessedAt = DateTime.UtcNow
};
}
}
private async Task WorkerLoop()
{
while (!_cancellationTokenSource.Token.IsCancellationRequested)
{
if (_taskQueue.TryDequeue(out var task))
{
try
{
var result = task.Processor(task.Data.Span);
task.CompletionSource.SetResult(result);
}
catch (Exception ex)
{
task.CompletionSource.SetException(ex);
}
}
else
{
await Task.Delay(1, _cancellationTokenSource.Token);
}
}
}
public void Dispose()
{
_cancellationTokenSource.Cancel();
Task.WaitAll(_workers, TimeSpan.FromSeconds(5));
_cancellationTokenSource.Dispose();
}
}
public class ProcessingTask<T>
{
public ReadOnlyMemory<T> Data { get; set; }
public Func<ReadOnlySpan<T>, object> Processor { get; set; }
public TaskCompletionSource<object> CompletionSource { get; set; }
}
public record ProcessingResult<T>
{
public bool Success { get; init; }
public T Result { get; init; }
public Exception Error { get; init; }
public DateTime ProcessedAt { get; init; }
}
// 使用示例
public class DataProcessingExample
{
public async Task DemonstrateDataProcessing()
{
using var pipeline = new DataProcessingPipeline<float>();
// 生成测试数据
var data = new float[1000000];
var random = new Random(42);
for (int i = 0; i < data.Length; i++)
{
data[i] = (float)random.NextDouble() * 100;
}
// 并行处理:计算统计信息
var tasks = new List<Task<ProcessingResult<Statistics>>>();
const int chunkSize = 10000;
for (int i = 0; i < data.Length; i += chunkSize)
{
var chunk = data.AsMemory(i, Math.Min(chunkSize, data.Length - i));
var task = pipeline.ProcessAsync(chunk, CalculateStatistics);
tasks.Add(task);
}
var results = await Task.WhenAll(tasks);
// 合并结果
var totalStats = MergeStatistics(results.Where(r => r.Success).Select(r => r.Result));
Console.WriteLine($"Processed {data.Length} elements");
Console.WriteLine($"Mean: {totalStats.Mean:F2}");
Console.WriteLine($"Min: {totalStats.Min:F2}");
Console.WriteLine($"Max: {totalStats.Max:F2}");
Console.WriteLine($"StdDev: {totalStats.StandardDeviation:F2}");
}
private Statistics CalculateStatistics(ReadOnlySpan<float> data)
{
if (data.IsEmpty)
return new Statistics();
var sum = 0.0;
var min = float.MaxValue;
var max = float.MinValue;
// 使用SIMD优化的求和
if (Vector.IsHardwareAccelerated && data.Length >= Vector<float>.Count)
{
var vectorSum = Vector<float>.Zero;
var vectorMin = new Vector<float>(float.MaxValue);
var vectorMax = new Vector<float>(float.MinValue);
int i = 0;
var vectorSize = Vector<float>.Count;
for (; i <= data.Length - vectorSize; i += vectorSize)
{
var vector = new Vector<float>(data.Slice(i, vectorSize));
vectorSum = Vector.Add(vectorSum, vector);
vectorMin = Vector.Min(vectorMin, vector);
vectorMax = Vector.Max(vectorMax, vector);
}
// 提取向量结果
for (int j = 0; j < vectorSize; j++)
{
sum += vectorSum[j];
min = Math.Min(min, vectorMin[j]);
max = Math.Max(max, vectorMax[j]);
}
// 处理剩余元素
for (; i < data.Length; i++)
{
var value = data[i];
sum += value;
min = Math.Min(min, value);
max = Math.Max(max, value);
}
}
else
{
// 标准实现
foreach (var value in data)
{
sum += value;
min = Math.Min(min, value);
max = Math.Max(max, value);
}
}
var mean = sum / data.Length;
// 计算标准差
var sumSquaredDiffs = 0.0;
foreach (var value in data)
{
var diff = value - mean;
sumSquaredDiffs += diff * diff;
}
var variance = sumSquaredDiffs / data.Length;
var standardDeviation = Math.Sqrt(variance);
return new Statistics
{
Count = data.Length,
Sum = sum,
Mean = mean,
Min = min,
Max = max,
StandardDeviation = standardDeviation
};
}
private Statistics MergeStatistics(IEnumerable<Statistics> stats)
{
var statsList = stats.ToList();
if (!statsList.Any())
return new Statistics();
var totalCount = statsList.Sum(s => s.Count);
var totalSum = statsList.Sum(s => s.Sum);
var overallMean = totalSum / totalCount;
var overallMin = statsList.Min(s => s.Min);
var overallMax = statsList.Max(s => s.Max);
// 计算合并后的标准差(简化版本)
var weightedVarianceSum = 0.0;
foreach (var stat in statsList)
{
var variance = stat.StandardDeviation * stat.StandardDeviation;
weightedVarianceSum += variance * stat.Count;
}
var overallVariance = weightedVarianceSum / totalCount;
var overallStandardDeviation = Math.Sqrt(overallVariance);
return new Statistics
{
Count = totalCount,
Sum = totalSum,
Mean = overallMean,
Min = overallMin,
Max = overallMax,
StandardDeviation = overallStandardDeviation
};
}
}
public record Statistics
{
public int Count { get; init; }
public double Sum { get; init; }
public double Mean { get; init; }
public float Min { get; init; } = float.MaxValue;
public float Max { get; init; } = float.MinValue;
public double StandardDeviation { get; init; }
}
练习2:现代C#特性应用
// 使用最新C#特性构建配置管理系统
public record DatabaseConfig(
string ConnectionString,
int MaxConnections = 100,
TimeSpan CommandTimeout = default
)
{
public TimeSpan CommandTimeout { get; init; } = CommandTimeout == default ? TimeSpan.FromSeconds(30) : CommandTimeout;
}
public record CacheConfig(
string RedisConnectionString,
TimeSpan DefaultExpiration = default,
int MaxMemoryMB = 512
)
{
public TimeSpan DefaultExpiration { get; init; } = DefaultExpiration == default ? TimeSpan.FromMinutes(30) : DefaultExpiration;
}
public record LoggingConfig(
string LogLevel = "Information",
string OutputTemplate = "{Timestamp:yyyy-MM-dd HH:mm:ss} [{Level:u3}] {Message:lj}{NewLine}{Exception}",
bool EnableConsoleLogging = true,
bool EnableFileLogging = false,
string LogFilePath = "logs/app.log"
);
// 主配置类使用主构造函数
public class ApplicationConfig(
DatabaseConfig database,
CacheConfig cache,
LoggingConfig logging)
{
public DatabaseConfig Database { get; } = database;
public CacheConfig Cache { get; } = cache;
public LoggingConfig Logging { get; } = logging;
// 使用集合表达式和模式匹配
public string[] GetValidationErrors()
{
List<string> errors = [];
// 数据库配置验证
if (string.IsNullOrWhiteSpace(Database.ConnectionString))
errors.Add("Database connection string is required");
if (Database.MaxConnections is <= 0 or > 1000)
errors.Add("Database max connections must be between 1 and 1000");
// 缓存配置验证
if (string.IsNullOrWhiteSpace(Cache.RedisConnectionString))
errors.Add("Redis connection string is required");
if (Cache.MaxMemoryMB <= 0)
errors.Add("Cache max memory must be positive");
// 日志配置验证
var validLogLevels = new[] { "Trace", "Debug", "Information", "Warning", "Error", "Critical" };
if (!validLogLevels.Contains(Logging.LogLevel))
errors.Add($"Invalid log level. Valid values: {string.Join(", ", validLogLevels)}");
return [.. errors];
}
// 使用原始字符串字面量生成配置摘要
public string GenerateConfigSummary() => $"""
Application Configuration Summary
================================
Database:
Connection: {MaskConnectionString(Database.ConnectionString)}
Max Connections: {Database.MaxConnections}
Command Timeout: {Database.CommandTimeout.TotalSeconds}s
Cache:
Redis: {MaskConnectionString(Cache.RedisConnectionString)}
Default Expiration: {Cache.DefaultExpiration.TotalMinutes}m
Max Memory: {Cache.MaxMemoryMB}MB
Logging:
Level: {Logging.LogLevel}
Console: {Logging.EnableConsoleLogging}
File: {Logging.EnableFileLogging}
{(Logging.EnableFileLogging ? $"File Path: {Logging.LogFilePath}" : "")}
""";
private static string MaskConnectionString(string connectionString)
{
if (string.IsNullOrWhiteSpace(connectionString))
return "[Not Set]";
// 简单的连接字符串掩码
var parts = connectionString.Split(';');
var maskedParts = parts.Select(part =>
{
if (part.Contains("password", StringComparison.OrdinalIgnoreCase) ||
part.Contains("pwd", StringComparison.OrdinalIgnoreCase))
{
var equalIndex = part.IndexOf('=');
return equalIndex >= 0 ? $"{part[..(equalIndex + 1)]}****" : part;
}
return part;
});
return string.Join(";", maskedParts);
}
}
// 配置构建器使用流畅API和默认Lambda参数
public class ConfigurationBuilder
{
private DatabaseConfig _database = new("");
private CacheConfig _cache = new("");
private LoggingConfig _logging = new();
public ConfigurationBuilder WithDatabase(Action<DatabaseConfigBuilder> configure = null)
{
var builder = new DatabaseConfigBuilder();
configure?.Invoke(builder);
_database = builder.Build();
return this;
}
public ConfigurationBuilder WithCache(Action<CacheConfigBuilder> configure = null)
{
var builder = new CacheConfigBuilder();
configure?.Invoke(builder);
_cache = builder.Build();
return this;
}
public ConfigurationBuilder WithLogging(Action<LoggingConfigBuilder> configure = null)
{
var builder = new LoggingConfigBuilder();
configure?.Invoke(builder);
_logging = builder.Build();
return this;
}
public ApplicationConfig Build() => new(_database, _cache, _logging);
}
public class DatabaseConfigBuilder
{
private string _connectionString = "";
private int _maxConnections = 100;
private TimeSpan _commandTimeout = TimeSpan.FromSeconds(30);
public DatabaseConfigBuilder ConnectionString(string value)
{
_connectionString = value;
return this;
}
public DatabaseConfigBuilder MaxConnections(int value)
{
_maxConnections = value;
return this;
}
public DatabaseConfigBuilder CommandTimeout(TimeSpan value)
{
_commandTimeout = value;
return this;
}
public DatabaseConfig Build() => new(_connectionString, _maxConnections, _commandTimeout);
}
public class CacheConfigBuilder
{
private string _connectionString = "";
private TimeSpan _defaultExpiration = TimeSpan.FromMinutes(30);
private int _maxMemoryMB = 512;
public CacheConfigBuilder ConnectionString(string value)
{
_connectionString = value;
return this;
}
public CacheConfigBuilder DefaultExpiration(TimeSpan value)
{
_defaultExpiration = value;
return this;
}
public CacheConfigBuilder MaxMemoryMB(int value)
{
_maxMemoryMB = value;
return this;
}
public CacheConfig Build() => new(_connectionString, _defaultExpiration, _maxMemoryMB);
}
public class LoggingConfigBuilder
{
private string _logLevel = "Information";
private string _outputTemplate = "{Timestamp:yyyy-MM-dd HH:mm:ss} [{Level:u3}] {Message:lj}{NewLine}{Exception}";
private bool _enableConsoleLogging = true;
private bool _enableFileLogging = false;
private string _logFilePath = "logs/app.log";
public LoggingConfigBuilder LogLevel(string value)
{
_logLevel = value;
return this;
}
public LoggingConfigBuilder OutputTemplate(string value)
{
_outputTemplate = value;
return this;
}
public LoggingConfigBuilder EnableConsole(bool value = true)
{
_enableConsoleLogging = value;
return this;
}
public LoggingConfigBuilder EnableFile(bool value = true, string filePath = "logs/app.log")
{
_enableFileLogging = value;
_logFilePath = filePath;
return this;
}
public LoggingConfig Build() => new(_logLevel, _outputTemplate, _enableConsoleLogging, _enableFileLogging, _logFilePath);
}
// 使用示例
public class ModernCSharpExample
{
public void DemonstrateModernFeatures()
{
// 使用流畅API和默认Lambda参数构建配置
var config = new ConfigurationBuilder()
.WithDatabase(db => db
.ConnectionString("Server=localhost;Database=MyApp;Trusted_Connection=true;")
.MaxConnections(200)
.CommandTimeout(TimeSpan.FromSeconds(45)))
.WithCache(cache => cache
.ConnectionString("localhost:6379")
.DefaultExpiration(TimeSpan.FromHours(1))
.MaxMemoryMB(1024))
.WithLogging(log => log
.LogLevel("Debug")
.EnableConsole()
.EnableFile(true, "logs/myapp.log"))
.Build();
// 验证配置
var errors = config.GetValidationErrors();
if (errors.Length > 0)
{
Console.WriteLine("Configuration errors:");
foreach (var error in errors)
{
Console.WriteLine($" - {error}");
}
return;
}
// 显示配置摘要
Console.WriteLine(config.GenerateConfigSummary());
// 使用模式匹配处理不同配置场景
var recommendation = config switch
{
{ Database.MaxConnections: > 500 } => "Consider connection pooling optimization",
{ Cache.MaxMemoryMB: > 2048 } => "High memory cache configuration detected",
{ Logging.LogLevel: "Debug" or "Trace" } => "Verbose logging enabled - consider for production",
_ => "Configuration looks good"
};
Console.WriteLine($"\nRecommendation: {recommendation}");
}
}
22.9 本章总结
本章深入探讨了C#的高级特性和最新功能,涵盖了从C# 9.0到C# 12.0的重要更新。
核心概念
现代语言特性
- Record类型:不可变数据建模
- 模式匹配:强大的条件逻辑
- Init-only属性:对象初始化控制
- 主构造函数:简化类定义
- 集合表达式:简洁的集合创建
高级反射和元编程
- 源生成器:编译时代码生成
- 表达式树:动态代码构建
- 高性能反射缓存
- 动态类型构建
内存管理高级技术
- Span
和Memory :零拷贝操作 - ArrayPool:内存池化
- 非托管内存管理
- 内存映射文件
- Span
高性能编程技术
- SIMD向量化操作
- 无锁数据结构
- 高性能字符串处理
- 性能基准测试
高级技术
源生成器应用
- 自动属性通知
- 序列化代码生成
- 编译时验证
内存优化策略
- 栈分配优化
- 缓冲区重用
- 内存对齐
并发编程优化
- 无锁算法
- 内存屏障
- 原子操作
实际应用
企业级开发
- 配置管理系统
- 数据处理管道
- 高性能服务
性能关键场景
- 实时数据处理
- 大规模计算
- 内存受限环境
现代化改造
- 遗留代码升级
- 性能优化
- 可维护性提升
重要技能
语言特性掌握
- 新语法理解
- 适用场景判断
- 最佳实践应用
性能优化能力
- 瓶颈识别
- 优化策略选择
- 效果验证
架构设计思维
- 可扩展性考虑
- 可维护性平衡
- 技术选型决策
通过掌握这些高级特性和技术,你将能够构建更高效、更现代、更可维护的C#应用程序。下一章我们将探讨C#在云原生和微服务架构中的应用。Age) { public decimal AnnualSalary => Salary * 12; }
// 可变Record public record MutablePerson { public string FirstName { get; set; } public string LastName { get; set; } public int Age { get; set; } }
// Record结构体 public readonly record struct Point(double X, double Y) { public double DistanceFromOrigin => Math.Sqrt(X * X + Y * Y);
public Point MoveBy(double deltaX, double deltaY) => new(X + deltaX, Y + deltaY);
}
// Record使用示例 public class RecordExamples { public void DemonstrateRecords() { // 创建Record实例 var person = new Person(“John”, “Doe”, 30); var employee = new Employee(“Jane”, “Smith”, 25, “IT”, 5000);
// Record相等性比较
var person2 = new Person("John", "Doe", 30);
Console.WriteLine($"Records equal: {person == person2}"); // True
// With表达式(非破坏性变更)
var olderPerson = person with { Age = 31 };
Console.WriteLine($"Original: {person}");
Console.WriteLine($"Modified: {olderPerson}");
// 解构
var (firstName, lastName, age) = person;
Console.WriteLine($"Deconstructed: {firstName} {lastName}, {age}");
// ToString自动实现
Console.WriteLine($"Person: {person}");
Console.WriteLine($"Employee: {employee}");
}
public void DemonstrateRecordCollections()
{
var people = new List<Person>
{
new("Alice", "Johnson", 28),
new("Bob", "Wilson", 35),
new("Charlie", "Brown", 22)
};
// 使用Record进行查询
var adults = people.Where(p => p.IsAdult()).ToList();
var names = people.Select(p => p.FullName).ToList();
// 分组
var ageGroups = people.GroupBy(p => p.Age / 10 * 10)
.ToDictionary(g => $"{g.Key}s", g => g.ToList());
foreach (var group in ageGroups)
{
Console.WriteLine($"{group.Key}: {string.Join(", ", group.Value.Select(p => p.FullName))}");
}
}
}
### 模式匹配增强
```csharp
using System;
using System.Collections.Generic;
// 模式匹配示例
public class PatternMatchingExamples
{
// 关系模式
public string ClassifyAge(int age) => age switch
{
< 13 => "Child",
>= 13 and < 20 => "Teenager",
>= 20 and < 65 => "Adult",
>= 65 => "Senior",
_ => "Unknown"
};
// 逻辑模式
public bool IsWeekend(DayOfWeek day) => day is DayOfWeek.Saturday or DayOfWeek.Sunday;
// 属性模式
public decimal CalculateDiscount(Person person) => person switch
{
{ Age: < 18 } => 0.2m,
{ Age: >= 65 } => 0.15m,
{ FirstName: "VIP" } => 0.3m,
_ => 0.0m
};
// 元组模式
public string GetQuadrant(double x, double y) => (x, y) switch
{
(> 0, > 0) => "First",
(< 0, > 0) => "Second",
(< 0, < 0) => "Third",
(> 0, < 0) => "Fourth",
(0, 0) => "Origin",
(0, _) => "X-axis",
(_, 0) => "Y-axis"
};
// 位置模式
public string AnalyzePoint(Point point) => point switch
{
(0, 0) => "Origin",
(var x, 0) => $"On X-axis at {x}",
(0, var y) => $"On Y-axis at {y}",
(var x, var y) when x == y => $"On diagonal at ({x}, {y})",
(var x, var y) => $"Point at ({x}, {y})"
};
// 类型模式
public string ProcessValue(object value) => value switch
{
int i when i > 0 => $"Positive integer: {i}",
int i when i < 0 => $"Negative integer: {i}",
int => "Zero",
string s when !string.IsNullOrEmpty(s) => $"Non-empty string: {s}",
string => "Empty or null string",
Person p => $"Person: {p.FullName}",
IEnumerable<int> numbers => $"Number collection with {numbers.Count()} items",
null => "Null value",
_ => $"Unknown type: {value.GetType().Name}"
};
// 嵌套模式
public string AnalyzeEmployee(Employee employee) => employee switch
{
{ Department: "IT", Salary: > 6000 } => "Senior IT Professional",
{ Department: "IT", Age: < 25 } => "Junior IT Professional",
{ Department: "HR", Age: > 40 } => "Senior HR Professional",
{ Salary: > 8000 } => "High Earner",
{ Age: < 25 } => "Young Professional",
_ => "Regular Employee"
};
}
Init-only属性和顶级程序
using System;
using System.Collections.Generic;
// Init-only属性
public class ImmutablePerson
{
public string FirstName { get; init; }
public string LastName { get; init; }
public int Age { get; init; }
public List<string> Hobbies { get; init; } = new();
// 只能在构造时设置
public string FullName { get; init; }
public ImmutablePerson()
{
FullName = $"{FirstName} {LastName}";
}
}
// 目标类型new表达式
public class TargetTypedNewExamples
{
public void DemonstrateTargetTypedNew()
{
// 字典初始化
Dictionary<string, List<int>> data = new()
{
["numbers"] = new() { 1, 2, 3, 4, 5 },
["primes"] = new() { 2, 3, 5, 7, 11 }
};
// 数组初始化
int[] numbers = new[] { 1, 2, 3, 4, 5 };
// 对象初始化
ImmutablePerson person = new()
{
FirstName = "John",
LastName = "Doe",
Age = 30,
Hobbies = new() { "Reading", "Gaming", "Cooking" }
};
// 方法参数
ProcessPerson(new() { FirstName = "Jane", LastName = "Smith", Age = 25 });
}
private void ProcessPerson(ImmutablePerson person)
{
Console.WriteLine($"Processing: {person.FullName}");
}
}
// 顶级程序示例(通常在Program.cs中)
/*
using System;
using System.Threading.Tasks;
// 顶级语句
Console.WriteLine("Hello, World!");
var person = new Person("John", "Doe", 30);
Console.WriteLine($"Created person: {person}");
await ProcessDataAsync();
Console.WriteLine("Program completed.");
// 本地函数
async Task ProcessDataAsync()
{
await Task.Delay(1000);
Console.WriteLine("Data processed.");
}
// 本地类
class LocalHelper
{
public static void Help()
{
Console.WriteLine("Helper method called.");
}
}
*/
22.2 C# 10.0+ 新特性
全局using指令和文件范围命名空间
// GlobalUsings.cs - 全局using指令
global using System;
global using System.Collections.Generic;
global using System.Linq;
global using System.Threading.Tasks;
global using System.Text.Json;
global using Microsoft.Extensions.Logging;
// 文件范围命名空间
namespace AdvancedFeatures.CSharp10;
// 常量插值字符串
public class InterpolatedStringConstants
{
private const string Greeting = "Hello";
private const string Target = "World";
// C# 10.0+ 支持常量插值字符串
private const string Message = $"{Greeting}, {Target}!";
public void DisplayMessage()
{
Console.WriteLine(Message);
}
}
// 结构体改进
public struct ImprovedStruct
{
public int Value { get; set; }
// 无参构造函数
public ImprovedStruct()
{
Value = 42;
}
public ImprovedStruct(int value)
{
Value = value;
}
}
// 扩展属性模式
public class ExtendedPropertyPatterns
{
public string AnalyzePerson(Person person) => person switch
{
{ FirstName.Length: > 10 } => "Long first name",
{ LastName.Length: < 3 } => "Short last name",
{ FullName.Length: > 20 } => "Long full name",
_ => "Regular name"
};
public bool IsValidEmail(string email) => email switch
{
{ Length: > 5 } and var e when e.Contains('@') && e.Contains('.') => true,
_ => false
};
}
// Lambda改进
public class LambdaImprovements
{
public void DemonstrateLambdaImprovements()
{
// 自然类型推断
var parse = (string s) => int.Parse(s);
var choose = object (bool b) => b ? 1 : "two";
// Lambda特性
var lambda = [Obsolete("Use new method")] (int x) => x * 2;
// 返回类型推断
var func = () => new { Name = "Test", Value = 42 };
}
}
CallerArgumentExpression特性
using System;
using System.Runtime.CompilerServices;
// CallerArgumentExpression示例
public static class ValidationHelper
{
public static void ValidateNotNull<T>(T value, [CallerArgumentExpression("value")] string? paramName = null)
where T : class
{
if (value is null)
{
throw new ArgumentNullException(paramName);
}
}
public static void ValidateRange(int value, int min, int max,
[CallerArgumentExpression("value")] string? paramName = null)
{
if (value < min || value > max)
{
throw new ArgumentOutOfRangeException(paramName,
$"Value {value} is not in range [{min}, {max}]");
}
}
public static void Assert(bool condition,
[CallerArgumentExpression("condition")] string? expression = null,
[CallerMemberName] string? memberName = null,
[CallerFilePath] string? filePath = null,
[CallerLineNumber] int lineNumber = 0)
{
if (!condition)
{
var fileName = System.IO.Path.GetFileName(filePath);
throw new InvalidOperationException(
$"Assertion failed: {expression} in {memberName} at {fileName}:{lineNumber}");
}
}
}
// 使用示例
public class ValidationExamples
{
public void ProcessData(string data, int count)
{
// 自动捕获参数表达式
ValidationHelper.ValidateNotNull(data); // 异常消息将包含"data"
ValidationHelper.ValidateRange(count, 1, 100); // 异常消息将包含"count"
var result = CalculateValue(count);
ValidationHelper.Assert(result > 0); // 异常消息将包含"result > 0"
}
private int CalculateValue(int input)
{
return input * 2;
}
}
22.3 C# 11.0+ 新特性
原始字符串字面量
using System;
using System.Text.Json;
// 原始字符串字面量示例
public class RawStringLiterals
{
public void DemonstrateRawStrings()
{
// 基本原始字符串
string basicRaw = """
This is a raw string literal.
It can contain "quotes" and 'apostrophes' without escaping.
Even backslashes \ are treated literally.
""";
// JSON示例
string jsonData = """
{
"name": "John Doe",
"age": 30,
"address": {
"street": "123 Main St",
"city": "Anytown"
},
"hobbies": ["reading", "gaming", "cooking"]
}
""";
// SQL查询示例
string sqlQuery = """
SELECT p.FirstName, p.LastName, e.Department, e.Salary
FROM Persons p
INNER JOIN Employees e ON p.Id = e.PersonId
WHERE e.Salary > 50000
AND e.Department IN ('IT', 'Engineering')
ORDER BY e.Salary DESC
""";
// HTML模板示例
string htmlTemplate = """
<!DOCTYPE html>
<html>
<head>
<title>{{title}}</title>
<style>
body { font-family: Arial, sans-serif; }
.container { max-width: 800px; margin: 0 auto; }
</style>
</head>
<body>
<div class="container">
<h1>{{heading}}</h1>
<p>{{content}}</p>
</div>
</body>
</html>
""";
// 正则表达式示例
string regexPattern = """
^(?<protocol>https?)://
(?<domain>[a-zA-Z0-9.-]+)
(?<port>:[0-9]+)?
(?<path>/[^?#]*)?
(?<query>\?[^#]*)?
(?<fragment>#.*)?$
""";
Console.WriteLine("Raw string examples created successfully.");
}
// 插值原始字符串
public void DemonstrateInterpolatedRawStrings()
{
string name = "Alice";
int age = 25;
string department = "Engineering";
// 插值原始字符串
string report = $"""
Employee Report
===============
Name: {name}
Age: {age}
Department: {department}
Performance Metrics:
- Projects Completed: {CalculateProjects(age)}
- Efficiency Rating: {CalculateEfficiency(age):F2}%
""";
Console.WriteLine(report);
}
private int CalculateProjects(int age) => age - 20;
private double CalculateEfficiency(int age) => Math.Min(95.0, age * 3.5);
}
泛型特性
using System;
using System.Reflection;
// 泛型特性定义
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method | AttributeTargets.Property)]
public class GenericAttribute<T> : Attribute
{
public T Value { get; }
public Type ValueType => typeof(T);
public GenericAttribute(T value)
{
Value = value;
}
public override string ToString()
{
return $"GenericAttribute<{typeof(T).Name}>: {Value}";
}
}
// 验证特性
[AttributeUsage(AttributeTargets.Property)]
public class RangeAttribute<T> : Attribute where T : IComparable<T>
{
public T Min { get; }
public T Max { get; }
public RangeAttribute(T min, T max)
{
Min = min;
Max = max;
}
public bool IsValid(T value)
{
return value.CompareTo(Min) >= 0 && value.CompareTo(Max) <= 0;
}
}
// 缓存特性
[AttributeUsage(AttributeTargets.Method)]
public class CacheAttribute<TKey> : Attribute
{
public TimeSpan Duration { get; }
public TKey CacheKey { get; }
public CacheAttribute(TKey cacheKey, int durationMinutes = 5)
{
CacheKey = cacheKey;
Duration = TimeSpan.FromMinutes(durationMinutes);
}
}
// 使用泛型特性的示例类
[GenericAttribute<string>("This is a test class")]
[GenericAttribute<int>(42)]
public class GenericAttributeExample
{
[RangeAttribute<int>(1, 100)]
public int Score { get; set; }
[RangeAttribute<double>(0.0, 1.0)]
public double Percentage { get; set; }
[RangeAttribute<DateTime>("2020-01-01", "2030-12-31")]
public DateTime EventDate { get; set; }
[GenericAttribute<bool>(true)]
[CacheAttribute<string>("user_data", 10)]
public string GetUserData(int userId)
{
return $"User data for {userId}";
}
[CacheAttribute<int>(12345, 30)]
public async Task<string> GetAsyncData()
{
await Task.Delay(100);
return "Async data";
}
}
// 特性反射工具
public static class GenericAttributeHelper
{
public static void AnalyzeType<T>()
{
var type = typeof(T);
Console.WriteLine($"Analyzing type: {type.Name}");
// 分析类级别特性
var classAttributes = type.GetCustomAttributes(typeof(Attribute), false);
foreach (var attr in classAttributes)
{
Console.WriteLine($" Class attribute: {attr}");
}
// 分析属性特性
var properties = type.GetProperties();
foreach (var prop in properties)
{
var propAttributes = prop.GetCustomAttributes(typeof(Attribute), false);
if (propAttributes.Length > 0)
{
Console.WriteLine($" Property {prop.Name}:");
foreach (var attr in propAttributes)
{
Console.WriteLine($" {attr}");
}
}
}
// 分析方法特性
var methods = type.GetMethods(BindingFlags.Public | BindingFlags.Instance | BindingFlags.DeclaredOnly);
foreach (var method in methods)
{
var methodAttributes = method.GetCustomAttributes(typeof(Attribute), false);
if (methodAttributes.Length > 0)
{
Console.WriteLine($" Method {method.Name}:");
foreach (var attr in methodAttributes)
{
Console.WriteLine($" {attr}");
}
}
}
}
public static bool ValidateProperty<T>(T obj, string propertyName)
{
var type = typeof(T);
var property = type.GetProperty(propertyName);
if (property == null)
return false;
var value = property.GetValue(obj);
var rangeAttributes = property.GetCustomAttributes(typeof(RangeAttribute<>), false);
foreach (var attr in rangeAttributes)
{
var rangeAttr = attr as dynamic;
if (rangeAttr != null && !rangeAttr.IsValid(value))
{
return false;
}
}
return true;
}
}
静态虚拟成员
using System;
using System.Numerics;
// 静态虚拟成员接口
public interface ICalculatable<TSelf> where TSelf : ICalculatable<TSelf>
{
static abstract TSelf Zero { get; }
static abstract TSelf One { get; }
static abstract TSelf Add(TSelf left, TSelf right);
static abstract TSelf Multiply(TSelf left, TSelf right);
static abstract TSelf Parse(string value);
static abstract bool TryParse(string value, out TSelf result);
// 实例方法
TSelf Increment();
string ToDisplayString();
}
// 数学运算接口
public interface IMathOperations<TSelf> where TSelf : IMathOperations<TSelf>
{
static abstract TSelf Abs(TSelf value);
static abstract TSelf Max(TSelf left, TSelf right);
static abstract TSelf Min(TSelf left, TSelf right);
static abstract double ToDouble(TSelf value);
}
// 自定义数值类型
public readonly struct CustomNumber : ICalculatable<CustomNumber>, IMathOperations<CustomNumber>
{
private readonly double _value;
public CustomNumber(double value)
{
_value = value;
}
// 静态虚拟属性实现
public static CustomNumber Zero => new(0);
public static CustomNumber One => new(1);
// 静态虚拟方法实现
public static CustomNumber Add(CustomNumber left, CustomNumber right)
=> new(left._value + right._value);
public static CustomNumber Multiply(CustomNumber left, CustomNumber right)
=> new(left._value * right._value);
public static CustomNumber Parse(string value)
=> new(double.Parse(value));
public static bool TryParse(string value, out CustomNumber result)
{
if (double.TryParse(value, out var doubleValue))
{
result = new(doubleValue);
return true;
}
result = Zero;
return false;
}
public static CustomNumber Abs(CustomNumber value)
=> new(Math.Abs(value._value));
public static CustomNumber Max(CustomNumber left, CustomNumber right)
=> new(Math.Max(left._value, right._value));
public static CustomNumber Min(CustomNumber left, CustomNumber right)
=> new(Math.Min(left._value, right._value));
public static double ToDouble(CustomNumber value)
=> value._value;
// 实例方法实现
public CustomNumber Increment() => new(_value + 1);
public string ToDisplayString() => _value.ToString("F2");
// 运算符重载
public static CustomNumber operator +(CustomNumber left, CustomNumber right)
=> Add(left, right);
public static CustomNumber operator *(CustomNumber left, CustomNumber right)
=> Multiply(left, right);
public override string ToString() => ToDisplayString();
}
// 泛型数学工具类
public static class GenericMath<T> where T : ICalculatable<T>, IMathOperations<T>
{
public static T Sum(params T[] values)
{
var result = T.Zero;
foreach (var value in values)
{
result = T.Add(result, value);
}
return result;
}
public static T Product(params T[] values)
{
var result = T.One;
foreach (var value in values)
{
result = T.Multiply(result, value);
}
return result;
}
public static T Average(params T[] values)
{
if (values.Length == 0)
return T.Zero;
var sum = Sum(values);
var count = new CustomNumber(values.Length);
// 这里需要更复杂的除法实现
var average = T.ToDouble(sum) / values.Length;
return T.Parse(average.ToString());
}
public static T Clamp(T value, T min, T max)
{
return T.Max(min, T.Min(max, value));
}
public static T[] Sort(T[] values)
{
var sorted = new T[values.Length];
Array.Copy(values, sorted, values.Length);
Array.Sort(sorted, (x, y) => T.ToDouble(x).CompareTo(T.ToDouble(y)));
return sorted;
}
}
// 使用示例
public class StaticVirtualMembersExample
{
public void DemonstrateStaticVirtualMembers()
{
// 创建自定义数值
var num1 = new CustomNumber(10.5);
var num2 = new CustomNumber(20.3);
var num3 = new CustomNumber(15.7);
// 使用静态方法
var sum = CustomNumber.Add(num1, num2);
var product = CustomNumber.Multiply(num1, num2);
Console.WriteLine($"Sum: {sum}");
Console.WriteLine($"Product: {product}");
// 使用泛型数学工具
var numbers = new[] { num1, num2, num3 };
var totalSum = GenericMath<CustomNumber>.Sum(numbers);
var totalProduct = GenericMath<CustomNumber>.Product(numbers);
var average = GenericMath<CustomNumber>.Average(numbers);
Console.WriteLine($"Total Sum: {totalSum}");
Console.WriteLine($"Total Product: {totalProduct}");
Console.WriteLine($"Average: {average}");
// 排序
var sorted = GenericMath<CustomNumber>.Sort(numbers);
Console.WriteLine($"Sorted: [{string.Join(", ", sorted)}]");
// 解析
if (CustomNumber.TryParse("42.5", out var parsed))
{
Console.WriteLine($"Parsed: {parsed}");
}
}
}