ExcelHome技术论坛

 找回密码
 免费注册

QQ登录

只需一步,快速开始

快捷登录

搜索
EH技术汇-专业的职场技能充电站 妙哉!函数段子手趣味讲函数 Excel服务器-会Excel,做管理系统 Excel Home精品图文教程库
HR薪酬管理数字化实战 Excel 2021函数公式学习大典 Excel数据透视表实战秘技 打造核心竞争力的职场宝典
300集Office 2010微视频教程 数据工作者的案头书 免费直播课集锦 ExcelHome出品 - VBA代码宝免费下载
用ChatGPT与VBA一键搞定Excel WPS表格从入门到精通 Excel VBA经典代码实践指南
楼主: 老伙计2008

[讨论] 555和556有什么区别,为什么为溢出?

[复制链接]

TA的精华主题

TA的得分主题

 楼主| 发表于 2010-1-2 00:04 | 显示全部楼层
原帖由 灰袍法师 于 2010-1-1 23:52 发表
因为VBA做乘法运算的时候,取最精确的乘数作为结果的数据类型
所以以下乘法表达式是一定溢出的
16384 * 2  (最精确的乘数是16384 = Int类型, 而结果32768 超过Int的最大范围)
65535*65535 (最精确的乘数是65535 = ...

谢谢!今天终于搞明白了!VBA为了节省资源,总是尽量把常数定义成占用资源最少的数据类型,因此不小心会溢出的

TA的精华主题

TA的得分主题

 楼主| 发表于 2010-1-2 00:15 | 显示全部楼层
原帖由 灰袍法师 于 2010-1-2 00:01 发表
嗯,这里我要多嘴说一句

除非你有很特别的理由,否则永远不要用Byte类型,最好也永远不要用integer,single。

因为它的表示数据范围最小(也就是说,应付修改程序的能力最差)

同时计算速度也是最慢的(因为全 ...

试了一下,还真是Byte类型比Long类型慢,以前一直以为Byte是最快的,原来是最慢的 (下面代码证实)
Private Sub kkk()
    Dim i&, t!, BS As Byte, Ls&
    t = Timer
    For i = 1 To 10000000
        BS = 1
    Next
    MsgBox "BYTE  " & Timer - t
   
    t = Timer
    For i = 1 To 10000000
        Ls = 1
    Next
    MsgBox "LONG  " & Timer - t
End Sub

TA的精华主题

TA的得分主题

发表于 2010-1-2 00:14 | 显示全部楼层
嗯,这里我要多嘴说一句

除非你有很特别的理由,否则永远不要用Byte类型,最好也永远不要用integer,single。

因为它的表示数据范围最小(也就是说,应付程序修改,以及程序处理不同数据的能力最差)

同时计算速度也是最慢的(因为全人类都在使用64位CPU了)。

唯一的优点可能就是节约一点内存,不过谁在乎VBA的内存耗用是100M还是200M吖?

反正又不会同时运行N个VBA。

我个人是永远把整数变量都声明为Long的,有时候甚至还会用Double去存储整数(如果需要这个整数乘以一个小数的话)

小数则必定是Double,极端情况下用dec之类的高精度。

发现楼主喜欢在变量名前面加上变量类型,建议不要这么做,弊大于利的。
匈牙利命名法是一个石器时代的发明,现在还在用就表明你看的编程教材太老土了。
http://zh.wikipedia.org/wiki/%E5 ... D%E5%90%8D%E6%B3%95

[ 本帖最后由 灰袍法师 于 2010-1-2 00:16 编辑 ]

TA的精华主题

TA的得分主题

发表于 2010-1-2 00:20 | 显示全部楼层
原帖由 老伙计2008 于 2010-1-2 00:15 发表
试了一下,还真是Byte类型比Long类型慢,以前一直以为Byte是最快的,原来是最慢的 (下面代码证实)


所以我才说你看的教材老土嘛

很早很早以前,Byte就已经是最慢的数据类型了。。。。。。

不过目前VBA里面还是 integer最快, 比Long快那么一丁点,毫无意义。

其他编程语言则不一定,也许C++64位开发环境运行在64位CPU,是DoubleLong最快呢

虽然讨论这个根本毫无意义,因为变量类型对于整个程序的速度影响,是最不重要的,所以绝绝大多数情况下,你都应该用范围最大的变量类型!

下面这个有点意义
永远不要用 MsgBox (result)输出你的运行结果
改用 [a1] = result 之类的方式
不要让人手操作进入你的程序,永远不要!!!

[ 本帖最后由 灰袍法师 于 2010-1-2 00:24 编辑 ]

TA的精华主题

TA的得分主题

发表于 2010-1-2 00:27 | 显示全部楼层
这里也有一段说法。


Visual Basic作为一种高级编程语言,它也有着不可避免的缺点——开发出的程序运行速度慢。如果我们能够对程序做一些优化,那么情况将会大大改善。
  要优化程序运行的实际速度,常用的方法有三种:
  1.尽量避免使用Variant变量。由于VB不能确定Variant变量的具体类型,所以它会给该类型变量分配16个字节的空间,而且在用变量进行运算时还要考虑到数据类型的转换。这既占用了内存,又影响了速度,会使涉及到复杂运算的程序变慢。注意,一个变量的缺省类型就是Variant,其它类型的变量要用Dim语句单独声明。
  2.在遇到整型数据时尽量使用Long变量。因为Long变量是32位CPU的本机数据类型,所以处理速度会很快,尤其是在循环体中。
  3.将控件的常用属性保存在变量中。一般控件存在于DLL或OCX之类的外部程序中。众所周知,调用DLL远比访问内存慢。所以对于那些放在循环体中的常用属性,如果将它们保存在变量中,那么速度将会有成百上千倍的提升。
  我们在编写程序时应注意到,在进行长时间等待操作时,可以做一些动画之类的效果,好让用户知道程序运行正常。下面是几个常用优化方法:
  1.使用Splash屏幕。也就是我们常见的欢迎窗口。大的应用程序在启动时,往往会主动或被动地载入一大堆DLL,这要花费很长时间。所以我们在启动时可以先显示一个简单的窗口,上面只放一些作者、版权之类的信息,在这个窗口的Form_Load事件中用Load方法读入那些最常用的窗体模块。这样,虽然实际等待的时间延长了,但用户所看到的屏幕总是变化的,所以感觉上程序启动加快了。而且由于常用窗体模块事先已载入内存,以后只需用Show方法来显示它,跳过了载入过程,在程序运行过程中也会很快的。
  2.使用Timer控件。由于Timer控件的出现,使得后台作业有了可能。我们可以在每次Timer事件中完成一小部分任务。这样,由于Timer中的事件能够在很短的时间内完成,用户一般查觉不到速度的变化。如果一定要在一个循环内完成某个任务,那么不要忘了用DoEvents来释放用户。
  3.使用进度条。要使用进度条,需要事先知道数据量,所以它很适合用于对已知数据的操作,如数据库的排序。
  总之,优化程序要从自己、从用户等多方面考虑,使程序开发周期短,且高效易用。

TA的精华主题

TA的得分主题

 楼主| 发表于 2010-1-2 00:33 | 显示全部楼层
[广告] VBA代码宝 - VBA编程加强工具 · VBA代码随查随用  · 内置多项VBA编程加强工具       ★ 免费下载 ★      ★使用手册

回复 14楼 灰袍法师 的帖子

在我这里还是 Long更快些
Private Sub kkk()
    Dim i&, t!, BS As Integer, Ls&, Lks As Long
    Lks = 1
    t = Timer
    For i = 1 To 100000000
        BS = Lks
    Next
    MsgBox "Integer  " & Timer - t
   
    t = Timer
    For i = 1 To 100000000
        Ls = Lks
    Next
    MsgBox "LONG  " & Timer - t
End Sub

TA的精华主题

TA的得分主题

发表于 2010-1-2 01:06 | 显示全部楼层
[广告] VBA代码宝 - VBA编程加强工具 · VBA代码随查随用  · 内置多项VBA编程加强工具       ★ 免费下载 ★      ★使用手册
原帖由 老伙计2008 于 2010-1-2 00:33 发表
在我这里还是 Long更快些


er......结论是对的,不过证明过程是错误的。

你的代码只不过证明了 把long变量赋值给long变量

要比 把long变量赋值给integer变量 更快

这。。。。。。

正确的做法如下:
Sub 按钮1_Click()
    Dim i As Long
    Dim t
    Dim IntSUm As Integer, Int1 As Integer, Int2 As Integer
    Dim LongSum As Long, Long1 As Long, Long2 As Long
   
    [b1] = ""
    [b2] = ""
   
    Int1 = 1
    Int2 = 1
    t = Timer
    For i = 1 To 100000000
        IntSUm = Int1 + Int2
    Next
    [b1] = Timer - t
   
    Long1 = 1
    Long2 = 1
    t = Timer
    For i = 1 To 100000000
        LongSum = Long1 + Long2
    Next
    [b2] = Timer - t
End Sub

附带一提:加法表达式中的任何一个变量换成其他类型,都会影响速度,因为涉及类型转换,所以必须三个变量都是同一类型。

通常情况下,表达式当中会有常数,而且变量类型几乎肯定是不同的,那么就不一定是Long最快了

这也是我在上面说,有时候用Double去存储整数的原因。

你可以自己试试看不同组合,累死。。。。。。

[ 本帖最后由 灰袍法师 于 2010-1-2 01:29 编辑 ]

Book1.rar

11.63 KB, 下载次数: 7

TA的精华主题

TA的得分主题

 楼主| 发表于 2010-1-2 01:15 | 显示全部楼层

回复 17楼 灰袍法师 的帖子

有道理,今天学了不少东西,收获不小啊

TA的精华主题

TA的得分主题

发表于 2010-1-2 09:26 | 显示全部楼层
原帖由 灰袍法师 于 2010-1-2 00:14 发表
嗯,这里我要多嘴说一句

除非你有很特别的理由,否则永远不要用Byte类型,最好也永远不要用integer,single。

因为它的表示数据范围最小(也就是说,应付程序修改,以及程序处理不同数据的能力最差)

同时计 ...
发现楼主喜欢在变量名前面加上变量类型,建议不要这么做,弊大于利的。


多一句嘴,某些观点实在不敢苟同,尤其是最后一句。
难到一个程序写成让自己都看不懂才是真正的高手?

[ 本帖最后由 joforn 于 2010-1-2 09:28 编辑 ]

TA的精华主题

TA的得分主题

发表于 2010-1-2 11:20 | 显示全部楼层

回复 17楼 灰袍法师 的帖子

原来学C的时候有讲过这方面的知识,现在全还给老师了。

[ 本帖最后由 lb_bn 于 2010-1-2 11:29 编辑 ]
您需要登录后才可以回帖 登录 | 免费注册

本版积分规则

手机版|关于我们|联系我们|ExcelHome

GMT+8, 2024-4-28 04:43 , Processed in 0.034914 second(s), 10 queries , Gzip On, MemCache On.

Powered by Discuz! X3.4

© 1999-2023 Wooffice Inc.

沪公网安备 31011702000001号 沪ICP备11019229号-2

本论坛言论纯属发表者个人意见,任何违反国家相关法律的言论,本站将协助国家相关部门追究发言者责任!     本站特聘法律顾问:李志群律师

快速回复 返回顶部 返回列表