首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >从0到&HFFFFFFFF的随机数

从0到&HFFFFFFFF的随机数
EN

Stack Overflow用户
提问于 2013-05-01 18:30:47
回答 4查看 3.5K关注 0票数 1

是否有任何方法可以在VisualBasic6.0中生成从0到&HFFFFFFFF的随机数?

我使用以下函数

代码语言:javascript
运行
复制
Function RandomNumberLong(Lowerbound As Long, Upperbound As Long) As Long
    RandomNumberLong = Clng((Upperbound - Lowerbound + 1) * Rnd + Lowerbound)
End Function

如果我用

代码语言:javascript
运行
复制
x = RandomNumberLong(0,&HFFFFFFFF)

它总是返回0。

这里的问题是long可以容纳的最大值是7 7FFFFFFF或小数为2147483647,那么我应该如何修复这个问题呢?即使我使用单个数据类型,它也总是返回负数而不带符号数字。

按MSDN长型

长(长整数)变量存储为有符号32位(4字节)数字,其值从-2,147,483,648到2,147,483,647不等。长时间的类型声明字符是符号(&)。

但是FFFFFFFF的值等于溢出的-1或4294967294。

我想我对此感到困惑。

编辑:

由于这似乎有点复杂,我编写了一个小Shell代码来使用RDTSC指令来生成一个随机长数,包括签名和无符号。

代码语言:javascript
运行
复制
Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" _ 
(Destination As Any, Source As Any, ByVal Length As Long)

Private Declare Function CallWindowProc Lib "user32" Alias "CallWindowProcA" _ 
(ByVal lpPrevWndFunc As Long, ByVal hWnd As Long, ByVal Msg As Long, _
ByVal wParam As Long, ByVal lParam As Long) As Long

Option Explicit

 Private Sub Form_Load()
 Dim x(1 To 10) As Byte, VAL As Long

    CopyMemory x(1), &H60, 1 'PUSHAD
    CopyMemory x(2), &H310F, 2 'RDTSC EAX holds a random value

    CopyMemory x(4), &HA3, 1 'MOV EAX
    CopyMemory x(5), VarPtr(VAL), 4 'Pointer of variable // MOV DWORD [VAL],EAX 

    CopyMemory x(9), &H61, 1 'POPAD
    CopyMemory x(10), &HC3, 1 'RET
    CallWindowProc VarPtr(x(1)), 0, 0, 0, 0 'Call the shellcode

    MsgBox VAL
    End Sub
EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2013-05-01 19:47:47

&HFFFFFFFF -表示32位有符号整数,而&HFFFFFFFF的值溢出该整数并成为-1,因此,当您调用RandomNumberLong函数时,将0传递给低绑定,-1传递给上限。

为了在Vb.NET中解决这个问题,请使用&HFFFFFFFFL&HFFFFFFFF&来指示长类型文字。我不知道如何在VB6中和上面示例中的VB.NET中一样快速地修复这个问题。我想您需要编写自己的函数来将大的HEX数字转换为双倍,并传递数字而不是HEX。

编辑:我认为VB6不允许您将&HFFFFFFFF转换为除基数16以外的任何东西,这会导致-1:

编辑2:通过将&添加到末尾,可以将一些十六进制数字转换为其他数据类型:

代码语言:javascript
运行
复制
&HFFFF = -1
&HFFFF& = 65535

尽管如此,VB6中的十六进制数似乎还是有限制的(只有16?)因为:

代码语言:javascript
运行
复制
VB.NET:
&HFFFFFFFF&=4294967295

VB6:
&HFFFFFFFF&=-1

MSDN:类型字符(Visual )

编译器通常将整数文字解析为十进制(基数10)数字系统中的整数。您可以使用&H前缀强制整数文字为十六进制(基数16),也可以强制它为带有&O前缀的八进制(基8)。前缀后面的数字必须适合数字系统。

票数 1
EN

Stack Overflow用户

发布于 2013-05-01 22:48:19

事实上,VB6 Long是32位有符号整数数据类型.因此,它根本无法存储&HFFFFFFFF (MSDN)。但是(1)无论如何,您似乎都可以使用Long,(2)您不需要解释您的用例是什么,而且如果仅仅在一个积极的范围内工作真的那么关键的话。

可以使用以下函数从整个Long数据类型(即从-&H80000000&H7FFFFFFF)生成随机的Long值:

代码语言:javascript
运行
复制
Function RandomNumberLong() As Long
    RandomNumberLong = &H7FFFFFFF * Rnd() + (-1 - &H7FFFFFFF) * Rnd()
End Function
票数 1
EN

Stack Overflow用户

发布于 2013-05-02 07:26:59

问题是,VB6将任何退出"F“到-1的十六进制数转换为-1。

这将使您的函数使用-1作为其上限,并使其返回0。

通过将8个数字分成2个变量和4个数字,您仍然有相同的问题,因为VB6仍然会将&HFFFF转换为-1,这将使您的函数再次返回0。

一种解决方案是在转换前将H 10000添加到4位变量中,并在转换完成后对Val(“&H 10000”)进行减法。

在此之后,您可以使用这两个值获得2个随机数,并将它们组合成1个随机8位十六进制数。

下面是一个测试项目,它展示了我的意思:

代码语言:javascript
运行
复制
'1 form with:
'  1 command button: name=Command1
Option Explicit

Private Sub Command1_Click()
  Dim strX As String
  Dim lngX As Long
  strX = RndHex("FFFFFFFF")
  lngX = Val("&H" & strX)
  Caption = strX & " = " & CStr(Hex$(lngX)) & " = " & CStr(lngX)
End Sub

Function RndHex(strMax As String) As String
  Dim strMax1 As String, strMax2 As String
  Dim lngMax1 As Long, lngMax2 As Long
  Dim lngVal1 As Long, lngVal2 As Long
  Dim strVal1 As String, strVal2 As String
  'make sure max is 8 digits
  strMax1 = Right$("00000000" & strMax, 8)
  'split max in 2 parts
  strMax2 = Right$(strMax1, 4)
  strMax1 = Left$(strMax1, 4)
  'convert max values from string to values
  lngMax1 = Val("&H1" & strMax1) - Val("&H10000")
  lngMax2 = Val("&H1" & strMax2) - Val("&H10000")
  'calculate separate random values
  lngVal1 = CLng(lngMax1 + 1) * Rnd
  lngVal2 = CLng(lngMax2 + 1) * Rnd
  'convert values to 4 digit hex strings
  strVal1 = Right$("0000" & Hex$(lngVal1), 4)
  strVal2 = Right$("0000" & Hex$(lngVal2), 4)
  'combine 2 random values and return the result as an 8 digit hex string
  RndHex = strVal1 & strVal2
End Function

Private Sub Form_Load()
  'seed random generator with system timer
  Randomize
End Sub

运行上面的项目并单击命令按钮并查看表单标题中的值。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/16324104

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档