VB6里面使用多线程提高穷举速度(VB6代码)
作者:admin 日期:2009-07-04
VB6里面使用多线程提高穷举速度
刚刚几个我论坛里的小同学在群里讨论已知位数密码穷举提速的方案,我也参与了一下.
我想了想,最简单的提速,就是真正的并行执行,即物理多线程,这需要至少两个CPU的硬件支持.
而我正好是双核CPU,于是就做了这个简单的例子(代码在后面下载).
代码没有多少,但却花了点时间调试.
对于多线程的调试技术,我还非常生疏,而且经常遇到IDE与编译后结果不一致的情况,很是烦人.
不过呢,终于是整好了.
程序要解决的一个假设题是从1开始,一个一个地跑到40000000(4千万),如何提高速度.
我的做法是,简单地将目标拆分为两部分,分别扔给两个线程去执行,这样速度当然就是一倍啦!
实际测试结果也确实是这样,双线程约8秒,单线程约16秒.而将代码放到虚拟机里测试的结果,却是双
线程慢于单线程(18.X秒与17.X秒,虚拟机中是单核).看来,在只能执行一个物理线程的硬件系统中,这种
穷举使用多线程,在CPU进行逻辑线程调度时消耗的时间那还真的不少.
由于手里没有支持超线程的CPU,所以没办法测试超线程功能是啥情况.不过从超线程原理来看,貌似
只是把线程的调度从软件上改成了硬件上,本质上还是只能同时执行一个物理线程,估计也差不多....有
支持超线程CPU的朋友帮忙测试一下吧:)
扯点题外话,其实物理并行处理,我觉得并不是CPU的强项....去年在软件开发大会上看到了NVIDIA的
CUDA技术演示,那才叫牛B,由于GPU本身物理结构上的优势,它可以轻松拥有上百个物理线程并行处理的能
力....可惜NVIDIA送的那套光碟放在陈辉家里忘带走了,还有CSDN的那个包包...呃,对,那个包包已经是
莫依的了...
不过呢......我的本本是INTEL的GMA3100.....与CUDA是无缘的了- -!
扯远了.....还是把代码先发上来吧,不然还没等到各位看完,我脑袋上估计都堆了很多块砖了= =|||
源代码在此下载:
点击下载此文件
BY 嗷嗷叫的老马
紫水晶工作室
http://www.m5home.com/
2009-07-04
刚刚几个我论坛里的小同学在群里讨论已知位数密码穷举提速的方案,我也参与了一下.
我想了想,最简单的提速,就是真正的并行执行,即物理多线程,这需要至少两个CPU的硬件支持.
而我正好是双核CPU,于是就做了这个简单的例子(代码在后面下载).
代码没有多少,但却花了点时间调试.
对于多线程的调试技术,我还非常生疏,而且经常遇到IDE与编译后结果不一致的情况,很是烦人.
不过呢,终于是整好了.
程序要解决的一个假设题是从1开始,一个一个地跑到40000000(4千万),如何提高速度.
我的做法是,简单地将目标拆分为两部分,分别扔给两个线程去执行,这样速度当然就是一倍啦!
实际测试结果也确实是这样,双线程约8秒,单线程约16秒.而将代码放到虚拟机里测试的结果,却是双
线程慢于单线程(18.X秒与17.X秒,虚拟机中是单核).看来,在只能执行一个物理线程的硬件系统中,这种
穷举使用多线程,在CPU进行逻辑线程调度时消耗的时间那还真的不少.
由于手里没有支持超线程的CPU,所以没办法测试超线程功能是啥情况.不过从超线程原理来看,貌似
只是把线程的调度从软件上改成了硬件上,本质上还是只能同时执行一个物理线程,估计也差不多....有
支持超线程CPU的朋友帮忙测试一下吧:)
扯点题外话,其实物理并行处理,我觉得并不是CPU的强项....去年在软件开发大会上看到了NVIDIA的
CUDA技术演示,那才叫牛B,由于GPU本身物理结构上的优势,它可以轻松拥有上百个物理线程并行处理的能
力....可惜NVIDIA送的那套光碟放在陈辉家里忘带走了,还有CSDN的那个包包...呃,对,那个包包已经是
莫依的了...
不过呢......我的本本是INTEL的GMA3100.....与CUDA是无缘的了- -!
扯远了.....还是把代码先发上来吧,不然还没等到各位看完,我脑袋上估计都堆了很多块砖了= =|||
源代码在此下载:

BY 嗷嗷叫的老马
紫水晶工作室
http://www.m5home.com/
2009-07-04
评论: 10 | 引用: 0 | 查看次数: 2846


陈辉?CSDN和VBGOOD的陈辉530么?都是牛人啊……
admin 于 回复


是他,ID是chenhui530



老大能否把这个帖子的附件发给我,谢谢。
admin 于 回复

已发送,请查收!
另外,本页的下载连接已修复!

另外,本页的下载连接已修复!


谢谢马大师!
不过这样也挺好,采用双线程莫名其妙地提高了效率。以后有什么新情况再向您报告。
admin 于 回复
不过这样也挺好,采用双线程莫名其妙地提高了效率。以后有什么新情况再向您报告。

客气了...
不过有些情况还是比较怪的.比如一个朋友遇到的问题,就是双核不如单核效率高,与你的情况相反.
而他当时的情况与打开了chrome谷哥浏览器有关,开了这个浏览器后,整体效率马上提高,非常怪,帖子如下:
http://topic.csdn.net/u/20090827/00/b3b03f96-5955-40c9-b9da-9d595b2c27c1.html
看看你那里会不会有类似的情况.
不过有些情况还是比较怪的.比如一个朋友遇到的问题,就是双核不如单核效率高,与你的情况相反.
而他当时的情况与打开了chrome谷哥浏览器有关,开了这个浏览器后,整体效率马上提高,非常怪,帖子如下:
http://topic.csdn.net/u/20090827/00/b3b03f96-5955-40c9-b9da-9d595b2c27c1.html
看看你那里会不会有类似的情况.


马大师您好!
我的系统:XP专业SP2,IE:火狐3.6.14,防火墙:FortKnox个人版,杀毒软件未装。
笔记本是 三星P30 迅驰一代1.4G,内存:2*512M
CPU-Z 1.55版的检测报告:
处理器 1 ID = 0
核心数 1 (最大1)
线程数 1 (最大1)
名称 Intel Pentium M
代号 Banias
规格 Intel(R) Pentium(R) M processor 1400MHz
封装 (平台 ID) Socket 479 mPGA (0x5)
CPUID 6.9.5
扩展 CPUID 6.9
品牌 ID 22
核心步进 B1
工艺 0.13 um
核心速度 605.0 MHz
倍频 x 外频 6.0 x 100.8 MHz
额定总线速度 403.3 MHz
主频 1400 MHz
指令集 MMX, SSE, SSE2
L1 数据缓存 32 KB, 8-路成组相联, 64-字节管道尺寸
L1 指令缓存 32 KB, 8-路成组相联, 64-字节管道尺寸
L2 缓存 1024 KB, 8-路成组相联, 64-字节管道尺寸
FID/VID 控制 是
FID 范围 6.0x - 14.0x
最大VID 1.484 V
CPU 线程 0
APIC ID 0
拓扑 处理器 ID 0, 核心 ID 0, 线程 ID 0
类型 01002001h
最大 CPUID 值 00000002h
最大 CPUID 扩展值 80000004h
缓存描述符 级别 1, D, 32 KB, 1 个线程
缓存描述符 级别 1, I, 32 KB, 1 个线程
缓存描述符 级别 2, U, 1 MB, 1 个线程
有劳大师了!
admin 于 回复
我的系统:XP专业SP2,IE:火狐3.6.14,防火墙:FortKnox个人版,杀毒软件未装。
笔记本是 三星P30 迅驰一代1.4G,内存:2*512M
CPU-Z 1.55版的检测报告:
处理器 1 ID = 0
核心数 1 (最大1)
线程数 1 (最大1)
名称 Intel Pentium M
代号 Banias
规格 Intel(R) Pentium(R) M processor 1400MHz
封装 (平台 ID) Socket 479 mPGA (0x5)
CPUID 6.9.5
扩展 CPUID 6.9
品牌 ID 22
核心步进 B1
工艺 0.13 um
核心速度 605.0 MHz
倍频 x 外频 6.0 x 100.8 MHz
额定总线速度 403.3 MHz
主频 1400 MHz
指令集 MMX, SSE, SSE2
L1 数据缓存 32 KB, 8-路成组相联, 64-字节管道尺寸
L1 指令缓存 32 KB, 8-路成组相联, 64-字节管道尺寸
L2 缓存 1024 KB, 8-路成组相联, 64-字节管道尺寸
FID/VID 控制 是
FID 范围 6.0x - 14.0x
最大VID 1.484 V
CPU 线程 0
APIC ID 0
拓扑 处理器 ID 0, 核心 ID 0, 线程 ID 0
类型 01002001h
最大 CPUID 值 00000002h
最大 CPUID 扩展值 80000004h
缓存描述符 级别 1, D, 32 KB, 1 个线程
缓存描述符 级别 1, I, 32 KB, 1 个线程
缓存描述符 级别 2, U, 1 MB, 1 个线程
有劳大师了!

看这个参数,并没有什么问题呀,普通的单核单线程CPU.
我在公司同样核心不同频率的CPU上也没重现这个现象.
非常奇怪.....
要找到原因,第一步得把系统原因排除了.
这个过程会比较麻烦,如果你有空闲的时间,试试将系统GHOST备份一下,再装个干净的系统看看,会不会还有这样程度的改善.
如果没有,那再慢慢装上你之前系统中的软件,只能这样一点一点试.
我在公司同样核心不同频率的CPU上也没重现这个现象.
非常奇怪.....
要找到原因,第一步得把系统原因排除了.
这个过程会比较麻烦,如果你有空闲的时间,试试将系统GHOST备份一下,再装个干净的系统看看,会不会还有这样程度的改善.
如果没有,那再慢慢装上你之前系统中的软件,只能这样一点一点试.


对不起老马大师!
我刚好填反了,应该是双线程11秒,单线程22秒!
我奇怪的是为什么单核双线程还能改善得这么好?!
admin 于 回复
admin 于 回复
我刚好填反了,应该是双线程11秒,单线程22秒!
我奇怪的是为什么单核双线程还能改善得这么好?!

如果真是这样,就非常奇怪了.
PM1.4我查了一下资料,单核,不支持超线程,那么只能有一个线程,这样的话双线程使用的时间一定比单线程长.
而我刚刚找了公司一台PM1.6的本本,测试结果也与我上面的推测相同,单线程16秒,双线程41秒.
不知道你那里的软件环境是怎么回事?
能否详细告知你的系统版本,当时运行的软件等,我怕是新的系统对于这些有可能有优化(上面的测试环境是XP专业版SP3,运行360,以及三个IE情况下.其硬件是PM1.6,1G内存)
PM1.4我查了一下资料,单核,不支持超线程,那么只能有一个线程,这样的话双线程使用的时间一定比单线程长.
而我刚刚找了公司一台PM1.6的本本,测试结果也与我上面的推测相同,单线程16秒,双线程41秒.
不知道你那里的软件环境是怎么回事?
能否详细告知你的系统版本,当时运行的软件等,我怕是新的系统对于这些有可能有优化(上面的测试环境是XP专业版SP3,运行360,以及三个IE情况下.其硬件是PM1.6,1G内存)

http://product.pconline.com.cn/notebook_cpu/intel/183375_detail.html
这里是PM1.4的资料,单核,不支持超线程.
我觉得你那里会不会看错CPU了..?
这里是PM1.4的资料,单核,不支持超线程.
我觉得你那里会不会看错CPU了..?


查了一下我的PM1.4不支持超线程,请问为什么单线程和双线程测试中会有这样的差距?
admin 于 回复

由于CPU只能运行一个物理线程,那么操作系统中的多线程,就纯粹是靠分时来实现的.
这样的话,线程多了反而会因为增加了线程切换与调度的时间而让执行效率下降.
不过一般来说这样的情况只会造成多线程比单线程耗时多一点点,比如单10秒,多11秒这样.多的那一点时间,就是系统执行线程调度与切换所消耗的时间.
而你这个时间差了一倍.....太可怕了....系统当时难道很忙么?或者运行的进程/线程很多,忙不过来?
消耗在线程调度与切换上的时间,居然这么多!
这样的话,线程多了反而会因为增加了线程切换与调度的时间而让执行效率下降.
不过一般来说这样的情况只会造成多线程比单线程耗时多一点点,比如单10秒,多11秒这样.多的那一点时间,就是系统执行线程调度与切换所消耗的时间.
而你这个时间差了一倍.....太可怕了....系统当时难道很忙么?或者运行的进程/线程很多,忙不过来?
消耗在线程调度与切换上的时间,居然这么多!


我测试了一下,我的机器很老2002年的,PM1.4G超线程。
单线程耗时约11.17,双线程22.75.
这么看来超线程表现还不错。
单线程耗时约11.17,双线程22.75.
这么看来超线程表现还不错。


其实对于这种密集型运算来说,的确不太适合VB6来做.
我对于VB6的单元线程,也仅是作为一种提高用户体验的手段来使用的.
要是真的需要进行高效率密集型运算,我宁愿会选择C或汇编来完成,这个代码只是一个例子而已,用于说明一下实现的思路.
我对于VB6的单元线程,也仅是作为一种提高用户体验的手段来使用的.
要是真的需要进行高效率密集型运算,我宁愿会选择C或汇编来完成,这个代码只是一个例子而已,用于说明一下实现的思路.


我可能是泼冷水,lz别介意哦。
你的想法是好的,但是我觉得VB6下的多线程不太有意义。原因如下:
1 Visual Basic 6 的运行时库不是线程安全的。VB6的运算符、库函数都无法保证重入的时候不会出现问题,所以在VB6里面实现的多线程是不可靠的。
2 Visual Basic 6 的运行效率非常低下。我写过一个算圆周率的程序,简单用VB.NET升级向导编译了下,速度比VB6快了6倍多。所以在性能优先的场合,使用更快速并且支持MT的VB.NET才是最佳选择。
最后我在我的双PIII 550上测试了下lz的程序。双线程平均CPU占用在75%左右,我觉得可能是同步的开销太大了,损失了不少效率。
你的想法是好的,但是我觉得VB6下的多线程不太有意义。原因如下:
1 Visual Basic 6 的运行时库不是线程安全的。VB6的运算符、库函数都无法保证重入的时候不会出现问题,所以在VB6里面实现的多线程是不可靠的。
2 Visual Basic 6 的运行效率非常低下。我写过一个算圆周率的程序,简单用VB.NET升级向导编译了下,速度比VB6快了6倍多。所以在性能优先的场合,使用更快速并且支持MT的VB.NET才是最佳选择。
最后我在我的双PIII 550上测试了下lz的程序。双线程平均CPU占用在75%左右,我觉得可能是同步的开销太大了,损失了不少效率。
VB6里最稳定的方案就是这个方案了,这也是微软官方的方案,详细情况可以看看MSDN中的介绍