【问题标题】:What are the implicit type conversion rules in vba?vba中的隐式类型转换规则是什么?
【发布时间】:2017-10-04 12:37:57
【问题描述】:

我知道在 vba 中可以进行以下操作:

If Len(str) Then

如果Len(str)0Len(str) 将评估为false,否则为true

vba 的具体转换规则是什么?如果可能,请提供官方文档的链接。

【问题讨论】:

  • Len() 返回一个整数值,而不是布尔值。是的,VBA 中的False 是零,但以这种方式编码并不好。

标签: vba type-conversion coercion type-coercion


【解决方案1】:

boolean 变量只能有两种状态,TrueFalse。在所有编程语言中都是如此(除非存在可为空的数据类型,例如 C# 中的 bool?,其中变量也可以具有值 null,表示它未定义)。

在 VBA 中,布尔值存储为 16 位整数。 False 定义为 0,True 定义为 -1。这在其他语言中也是类似的,只是因为 0 将所有位设置为 0,而 -1 将所有位设置为 1。但这是一个实现细节,您的编程不应该关心它。您使用ANDORNOT 处理TrueFalse 和布尔代数。

隐式转换规则直截了当:如果数值数据类型为 0,则将其转换为布尔值 False,在所有其他情况下(即,如果值具有 any 位,则转换为 True设置为 1)。将布尔值转换为数字会分别得到 0。 -1.

Dim i As Integer
Dim b As Boolean    
i = 3
b = i   ' Implicit conversion from 3 to TRUE
i = b   ' Implicit conversion from TRUE to -1

首先将字符串转换为数字,如果失败,则会出现运行时错误。日期在 VBA 中实现为数字(双精度),因此每个日期/时间都是 True,除了表示为 0 的日期+时间(即 1899 年 12 月 30 日 00:00)

但从我的观点(以及 >30 年的编程经验)来看,隐式转换是邪恶的,应该避免。它们是许多错误的来源,它们导致代码更难阅读 - 根本没有理由依赖隐式对话。没有理由写If len(str) Then。你想检查一个字符串的长度是否大于0,所以写成:If len(str) > 0 Then。总是。

看看下面的例子:显然,VBA运行时需要执行一个隐式转换,但你能告诉结果吗?

Dim i As Integer
Dim b As Boolean  
i = 3
b = i
If b = i Then Debug.Print "B=I"

你可以在这里找到微软官方文档:https://docs.microsoft.com/en-US/office/vba/language/reference/user-interface-help/boolean-data-type

【讨论】:

  • 一个布尔变量只能有两种状态......一个实现细节,你的编程不应该关心它 - 除非你have to
  • @GSerg:很好 - 不知道。坦率地说,这似乎是 VBA 中的一个错误(而且我通常对这样的声明并不那么快),因为该示例中的结果设法将 1 写入布尔变量 - 这与它的定义背道而驰。跨度>
  • InputBox 如果取消则返回 False:Microsoft documentation。那么从在 InputBox 上单击 Cancel 以返回“Falsch”字符串german problem here on SO 的路径是什么?这个荒谬的结果或/和选角如何涉及区域设置? BoolLong 转换在这里很明显,但是 Bool String 像 False = "False" 并给出 "Falsch" 的情况呢?
  • InputBox 存在问题,它返回一个布尔值 (False) 或包含输入内容的字符串。将结果读入 Variant 并检查 VarType(请参阅接受的答案),以便您可以区分 Cancel 和输入类似“0”的内容。这避免了从布尔值到字符串的隐式转换。
  • 我知道这种情况下的解决方案。我只是在问如何将 False 转换为字符串“Falsch”,这对我来说很奇怪...... Bool->String 转换是否记录在案?顺便说一句,感谢您的努力。
【解决方案2】:

我在最近阅读的一本关于 C++ 的教科书中遇到了这个问题——我将在最后添加一个链接。虽然语言不同,但在某种程度上都有相似之处。这些相似之处之一就是您所说的“隐式类型转换”,或者更专业地说,类型转换。

当您编译 VBA 项目(调试 > 编译 VBAProject)时,对于项目中的任何布尔表达式,任何非零值都将被视为值 true,并将值 0 视为 false。本质上,这归结为编译器如何处理这些语句以及运算符优先级规则和布尔表达式规则。

如需进一步阅读,请参阅以下链接:

  1. Operator precedence
  2. Boolean data type

在 C++ 中(据我所知),这个术语称为复制初始化,您可以在此处阅读更多内容:

  1. Copy initialization

最近引发这种深刻思考的书:

Problem Solving with C++: The Object of Programming

我知道这不一定能回答您的问题,但希望一些参考资料有所帮助。

【讨论】:

  • 小心,您的链接指向 VB.Net,而不是 VBA
  • @Dean 没有人对我的“赏金”给出好的答案。 FunThomas 和 GSerg 将标题的主题范围缩小到最简单的有据可查的案例。甚至问题的作者罗兰也写道:“问题是关于任何两种类型的”。但我必须选择奖励的答案。你的回答也不好,但是你链接了一些非常有趣的离题链接,赏金是你的。
猜你喜欢
  • 2020-05-30
  • 2019-12-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-09-29
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多