4

有谁知道如何使用 SQL 将几个字节传递给二进制(或 varbinary)字段,最好是在 ADO(经典)和 VBScript(或 Visual Basic 6)中?

我希望编码 10-20(也许更多)字节的数据并将这些数据存储在 SQL db 字段中。(它不是 MS-SQLSVR,但我希望标准 SQL 支持的格式可以工作!)

这些字节可以作为通过 AscB/ChrB 获得的字节字符串,或者是“字节”数组(实际上是通过“cbyte”获得的字节类型的变体)并存储在数组中。

第一个选项:使用字符串格式 ,我在创建 SQL 插入时取得了一些(有限)成功:

x = ".>?hD-&91k[="    '<psuedo string of chars, some unprintable
Insert Into rawtest (byt) Values (CAST('" & x & "' as SQL_BINARY(12)))

但我担心字符串空值会截断字段中的数据,并且其他非打印控制字符会妨碍处理数据。有没有办法避免这种情况?

第二个选项:字节数组 我可以很容易地将数据放入数组中,但看不到如何传递给 SQL 插入语句。如果我尝试传入 12 个字节,则由于 CAST 尝试将数据存储到整数(4 字节)中,因此插入失败。如果我传入一个字节,它就可以工作,例如:

x = a(0)

并继续工作 4 个字节,但在 Integer 溢出时失败。此外,它对数据进行重新排序

我尝试使用各种解决方法:

Insert Into rawtest (byt) Values (CAST('12,34,45' as SQL_BINARY(12)))
Insert Into rawtest (byt) Values (CAST(&h12&h34 as SQL_BINARY(12)))
Insert Into rawtest (byt) Values (CAST(0x123456789012 as SQL_BINARY(12)))

我也尝试过类似的组合:

Insert Into rawtest (byt) Values (CONVERT('" & x & "', SQL_BINARY)

但这些都失败了!

理想情况下,我想要一个方法,任何方法,它需要一个最多 20 个字节的小型二进制数组(理想情况下是完整的字节范围 0-255,但可能需要更少)并将它们传递给一个普通的、原始的、二进制 SQL 字段。

理想情况下,我需要在 VBScript/ADO 中执行此操作,但如果可用,可以采用基于 VB6 的解决方案。我希望这是“原始”二进制文件,我不想使用 ascii 编码,比如 Base64。

我已经用谷歌搜索了,直到我麻木了,并且没有发现太多与 SQL 中的二进制字段相关的东西。

你能帮我吗?任何答案表示赞赏。很多谢谢。

4

3 回答 3

5

经典 ADO 可以直接操作非常大 (>8000) 的 varbinary 和图像 (blob) 字段,而无需分块。下面是一个针对 MS SQL Server 的示例,该示例将二进制数据插入到具有 INT ID 字段和 varbinary(100) 字段的表中。在此示例中,参数化 SQL 查询正在插入来自 Variant 的二进制数据。Variant 只需要填充二进制数据。

Dim vntBlobData As Variant
vntBlobData = "ReplaceThisWithBinaryData - A byte array will work"

Dim cn As ADODB.Connection
Set cn = New ADODB.Connection
cn.ConnectionString = "Provider = sqloledb; Data Source = DBServerName; Initial Catalog = DBName; User ID = UserID; Password = Password; Persist Security Info = False"
cn.Open

Dim strQry As String
strQry = "INSERT INTO TestBinaryTable (ID, BlobData) VALUES (?, ?)"

Dim cm As ADODB.Command
Set cm = New ADODB.Command
cm.ActiveConnection = cn
cm.CommandText = strQry
cm.Parameters.Append cm.CreateParameter("@ID", adInteger, adParamInput, , 1)
cm.Parameters.Append cm.CreateParameter("@BlobData", adVarBinary, adParamInput, 100, vntBlobData)
cm.CommandType = adCmdText
cm.Execute
于 2009-05-29T02:06:58.190 回答
1

VB6 可以使用 ADO 字段类的 GetChunk 和 AppendChunk 方法访问二进制列。请参阅此知识库文章

博客文章具有将十六进制字符串转换为 varbinary 的功能:

CREATE FUNCTION dbo.HexStrToVarBinary(@hexstr varchar(8000))
RETURNS varbinary(8000)
AS
BEGIN 
    DECLARE @hex char(1), @i int, @place bigint, @a bigint
    SET @i = LEN(@hexstr) 

    set @place = convert(bigint,1)
    SET @a = convert(bigint, 0)

    WHILE (@i > 0 AND (substring(@hexstr, @i, 1) like '[0-9A-Fa-f]')) 
     BEGIN 
        SET @hex = SUBSTRING(@hexstr, @i, 1) 
        SET @a = @a + 
    convert(bigint, CASE WHEN @hex LIKE '[0-9]' 
         THEN CAST(@hex as int) 
         ELSE CAST(ASCII(UPPER(@hex))-55 as int) end * @place)
    set @place = @place * convert(bigint,16)
        SET @i = @i - 1

     END 

    RETURN convert(varbinary(8000),@a)
END
于 2009-05-28T19:49:07.003 回答
1

Matt 给了我一个解决方案的引子:虽然目标不是 blob 字段,并且大部分代码指示如何通过 ADO 将字符串传递到数据库中,但我需要的一点是如何创建要输入的字节变量'vntBlobData',通过使用charb/ascb从源字节创建一个VBS'字节字符串',我得到了我的解决方案。我现在有一个 VBS 解决方案(并且使用了适当的字节数组,还有一个 VB6 解决方案!)非常感谢马特。

'VBS $2Bin:

Function a2b(x)
    For i = 1 To Len(x)+1 Step 2
        d = Mid(x, i, 2)
        a2b = a2b & chrb(CByte(d))
    Next
End Function

'VBS Bin2$

Function eb2s(c)
    If IsNull(c) Then
        eb2s = ""
    else
        For i = 1 To lenb(c)
        eb2s = eb2s & ascb(Midb(c, i, 1))
        Next
    End if
End Function
于 2009-05-31T20:39:12.257 回答