Sql 具有计数字段的可更新记录集-MS Access
我不是SQL专家。也许我在这里想做的事根本不可能 我试图获得一个可更新的记录集,其中包含一个字段,该字段是聚合函数的结果 我在找这样的东西:Sql 具有计数字段的可更新记录集-MS Access,sql,ms-access,Sql,Ms Access,我不是SQL专家。也许我在这里想做的事根本不可能 我试图获得一个可更新的记录集,其中包含一个字段,该字段是聚合函数的结果 我在找这样的东西: SELECT Contact.*, Count(OrderID) as CountOfOrders FROM Contact INNER JOIN Order ON Order.ContactID = Contact.ContactID WHERE ContactID = 1 SHAPE {SELECT ContactID, ContactName
SELECT Contact.*, Count(OrderID) as CountOfOrders
FROM Contact INNER JOIN Order ON Order.ContactID = Contact.ContactID
WHERE ContactID = 1
SHAPE {SELECT ContactID, ContactName FROM Contact}
APPEND ({SELECT ContactID, OrderID FROM Orders}
RELATE ContactID TO ContactID
) As rsDetails, COUNT(rsDetails.OrderID) AS CountOfOrder
当使用MSDataShape OLE DE提供程序和Jet(或ACE)的OLE DB提供程序时,确实可以创建一个可更新的ADO记录集,并基于一个集合函数(如
COUNT()
)附加一个计算列。生成的SQL风格代码看起来更像这样:
SELECT Contact.*, Count(OrderID) as CountOfOrders
FROM Contact INNER JOIN Order ON Order.ContactID = Contact.ContactID
WHERE ContactID = 1
SHAPE {SELECT ContactID, ContactName FROM Contact}
APPEND ({SELECT ContactID, OrderID FROM Orders}
RELATE ContactID TO ContactID
) As rsDetails, COUNT(rsDetails.OrderID) AS CountOfOrder
这里有一个简短的“概念证明”:将以下内容粘贴到任何VBA模块中(例如,使用Excel),无需引用,在临时目录中创建一个新的.mdb,创建包含数据的表,以证明记录集是可更新的ContactName
值已更改,并且记录集已重新打开,以显示它确实已更改:
Sub ShapeAppendCount()
On Error Resume Next
Kill Environ$("temp") & "\DropMe.mdb"
On Error GoTo 0
Dim cat
Set cat = CreateObject("ADOX.Catalog")
With cat
.Create _
"Provider=Microsoft.Jet.OLEDB.4.0;" & _
"Data Source=" & _
Environ$("temp") & "\DropMe.mdb"
Dim jeng
Set jeng = CreateObject("JRO.JetEngine")
jeng.RefreshCache .ActiveConnection
Set .ActiveConnection = Nothing
End With
Dim con
Set con = CreateObject("ADODB.Connection")
With con
.ConnectionString = _
"Provider=MSDataShape;" & _
"Data Provider=Microsoft.Jet.OLEDB.4.0;" & _
"Data Source=" & _
Environ$("temp") & "\DropMe.mdb"
.CursorLocation = 3
.Open
.Execute _
"CREATE TABLE Contact (" & _
"ContactID INTEGER NOT NULL UNIQUE, " & _
"ContactName VARCHAR(20) NOT NULL);"
.Execute _
"CREATE TABLE Orders (" & _
"ContactID INTEGER NOT NULL REFERENCES Contact (ContactID), " & _
"OrderID INTEGER NOT NULL UNIQUE);"
.Execute _
"INSERT INTO Contact (ContactID, ContactName)" & _
" VALUES (1, 'OneDayWhen');"
.Execute _
"INSERT INTO Orders (ContactID, OrderID)" & _
" VALUES (1, 1);"
.Execute _
"INSERT INTO Orders (ContactID, OrderID)" & _
" VALUES (1, 2);"
Dim rs
Set rs = CreateObject("ADODB.Recordset")
With rs
.CursorType = 2 ' adOpenDynamic
.LockType = 4 ' adLockBatchOptimistic
.Source = _
" SHAPE {SELECT ContactID, ContactName FROM Contact} " & _
"APPEND ({SELECT ContactID, OrderID FROM Orders} " & _
"RELATE ContactID TO ContactID) As rsDetails, " & _
" COUNT(rsDetails.OrderID) AS CountOfOrder"
Set .ActiveConnection = con
.Open
.Fields("ContactName").Value = "Pink Cat"
.UpdateBatch
MsgBox .GetString
.Close
End With
With rs
.Source = _
"SELECT ContactID, ContactName FROM Contact"
Set .ActiveConnection = con
.Open
MsgBox .GetString
.Close
End With
End With
End Sub
我认为不可能有包含聚合函数的可更新记录集。@HansUp:对于DAO记录集可能不可能,但是对于ADO记录集是可行的。看我的答案:)我显然必须进入数据成形!MSDataShape提供程序是非常有问题和繁琐的。早在2000年早期,我就试图开始使用它,但遇到了各种各样的问题。例如,它是允许更新不可更新的选择的提供程序,因为使用SQL Server它直接进入基表。这可能会严重破坏您的安全,由于所有这些问题,我将其作为一个有用的工具扔掉。MS似乎也做了同样的事情,因为它是ADP和SQL Server之间的主要组件,并且他们已经反对了大约5年。@David-W-Fenton:“这可能会严重破坏您的安全,由于所有这些问题,我把它作为一个有用的工具扔掉了。”从ACE开始,访问团队还将安全性作为一种有用的工具,特别是用户级别的多样性。但说真的,我不相信你的断言:如果MSDataShape确实暴露了一个安全漏洞,那么我们都会知道的。我不认为您想发布代码来证明您的观点,但如果您愿意,可以自由编辑我的答案。您不记得Steve Jorgensen的一系列文章发现ADO绕过安全视图直接访问数据表的方式存在问题吗?我的理解是,ADO使用的功能是由数据形状组件提供的,但那是很久以前的事了,我可能会记错。你对ACE的攻击以及从其中一种文件格式中删除ULS是不值得的,因为这只是一个廉价的尝试,因为这与我所指的问题完全相反。@David-W-Fenton:对不起,我甚至不记得Steve Jorgensen了。最大的问题是,它是否得到了适当的同行评议?打个比方,艾伦·布朗(Alan Browne)曾经说过,臭名昭著的“
DECIMAL
sort bug”会产生各种奇怪的行为,这一点毫无疑问会留在你的脑海中。事实上,大部分是不可生产的,其不良影响没有报道的那么严重(即有偏见)。似乎没人记得我每隔一周就反驳一次。但我并不痛苦:)