方法性能比较的好帮手:CodeTimer的扩展应用
在09年的.NET技术大会上Jeffery Richard展示的性能测试代码中,功能强大的CodeTimer引起了大家的注意,由于Jeffery Richard还没有公布源码,于是园子里的老赵就自己写了一个,适用于在Console应用程序中输出性能测试的各个指标。
最近参与的项目中有很多想要进行方法性能比较的地方,于是就想起了这个CodeTimer,便狗尾续貂在老赵原有的代码上加上了一个Time方法的重载,以适用于非Console应用程序中快速的性能测试,比如Winform、Web、UnitTest、WindowsService等等。
修改后的代码如下:
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Runtime.InteropServices; using System.Diagnostics; using System.Threading; namespace PerformanceTest { public static class CodeTimer { public static void Initialize() { Process.GetCurrentProcess().PriorityClass = ProcessPriorityClass.High; Thread.CurrentThread.Priority = ThreadPriority.Highest; Time("", 1, () => { }); } public static void Time(string name, int iteration, Action action) { Time(name, iteration, action, Console.WriteLine); } public static void Time(string name, int iteration, Action action, Action<string> output) { if (String.IsNullOrEmpty(name)) return; // 1. ConsoleColor currentForeColor = Console.ForegroundColor; Console.ForegroundColor = ConsoleColor.Yellow; output(name); // 2. GC.Collect(GC.MaxGeneration, GCCollectionMode.Forced); int[] gcCounts = new int[GC.MaxGeneration + 1]; for (int i = 0; i <= GC.MaxGeneration; i++) { gcCounts[i] = GC.CollectionCount(i); } // 3. Stopwatch watch = new Stopwatch(); watch.Start(); ulong cycleCount = GetCycleCount(); for (int i = 0; i < iteration; i++) action(); ulong cpuCycles = GetCycleCount() - cycleCount; watch.Stop(); // 4. Console.ForegroundColor = currentForeColor; output("\tTime Elapsed:\t" + watch.ElapsedMilliseconds.ToString("N0") + "ms"); output("\tCPU Cycles:\t" + cpuCycles.ToString("N0")); // 5. for (int i = 0; i <= GC.MaxGeneration; i++) { int count = GC.CollectionCount(i) - gcCounts[i]; output("\tGen " + i + ": \t\t" + count); } output(string.Empty); } private static ulong GetCycleCount() { ulong cycleCount = 0; QueryThreadCycleTime(GetCurrentThread(), ref cycleCount); return cycleCount; } [DllImport("kernel32.dll")] [return: MarshalAs(UnmanagedType.Bool)] static extern bool QueryThreadCycleTime(IntPtr threadHandle, ref ulong cycleTime); [DllImport("kernel32.dll")] static extern IntPtr GetCurrentThread(); } }
这样一来,就能够在Winform、Web、UnitTest、Service等各种应用程序中方便快捷的使用CodeTimer了,比如在Winform中的一个应用:
StringBuilder result; private void button1_Click(object sender, EventArgs e) { string s = string.Empty; PerformanceTest.CodeTimer.Time("String Concat", 10000, () => { s += "a"; }, Print); StringBuilder sb = new StringBuilder(); PerformanceTest.CodeTimer.Time("StringBuilder", 10000, () => { sb.Append("a"); }, Print); this.textBox1.Text = result.ToString(); } void Print(string msg) { if (result == null) result = new StringBuilder(); result.AppendLine(msg); Console.WriteLine(msg); }
分类:
05. Daily Work
, 08. Common Lib
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 单线程的Redis速度为什么快?
· SQL Server 2025 AI相关能力初探
· 展开说说关于C#中ORM框架的用法!
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
2009-01-13 Outlook Express邮件客户端的自动化配置