使用基于传递查询的表单访问 2010 膨胀
Posted
技术标签:
【中文标题】使用基于传递查询的表单访问 2010 膨胀【英文标题】:access 2010 bloat with forms based on pass through queries 【发布时间】:2014-06-11 14:45:11 【问题描述】:我的 access 2010 数据库非常庞大。仅在 VBA 的几次运行中,它就从 44mb 变为 282mb。这是我设置的:
本地表 - 这些计算表单的统计信息,通常不会移动太多。
通过查询 - 我个人的怀疑。在查看表单时,如果用户单击记录,我会使用用户单击的记录运行直通查询。所以用户点击“joe”,通过查询运行 sql string = "select * from sqlserver where name=" &[forms]![myform]![firstname]
此查询运行后,我的 vba 删除传递查询,然后在选择另一条记录后重新创建它。所以用户回到名字列表,然后点击 BRIAN。然后我的 vba 删除传递查询并创建另一个查询以从 sql server 中选择所有名为 brian 的记录,使用与上面相同的代码。
表单 - 我的表单使用传递查询作为源。
我做的不是很聪明吗?如何更好地构建它以防止访问文件大小爆炸?我尝试了紧凑和修复,以及在 access 2010 中分析数据库性能。任何帮助都非常感谢,我一直在谷歌搜索 access2010 bloat 并阅读了关于 temptables 以及关闭 DAO(我正在使用,并且我做到了)明确关闭)。谢谢!
这是我正在使用的一种形式的一些代码 -
Private Sub name_Click()
'set dims
Dim db As DAO.Database
Dim qdExtData As QueryDef
Dim strSQL As String
Dim qdf As DAO.QueryDef
'close form so it will refresh
DoCmd.Close acForm, "myform", acSaveNo
'delete old query so a new one can be created with the same name
For Each qdf In CurrentDb.QueryDefs
If qdf.Name = "QRY_PASS_THROUGH" Then
DoCmd.Close acQuery, "QRY_PASS_THROUGH", acSaveNo
DoCmd.SetWarnings False
DoCmd.DeleteObject acQuery, "QRY_PASS_THROUGH"
DoCmd.SetWarnings True
Exit For
End If
Next
Set db = CurrentDb
'sql for the data
strSQL = "select fields from (table1 inner join table2 on stuff=stuff and stuff=stuff) left join table3 on stuff=stuff and stuff=stuff where flag='P' and table.firstname = " & [Forms]![myform]![firstname]
Set qdExtData = db.CreateQueryDef("QRY_PASS_THROUGH")
'how you connect to odbc
qdExtData.Connect = "ODBC;DSN=server;UID=username;PWD=hunter2;"
qdExtData.SQL = strSQL
DoCmd.OpenForm ("names")
Forms!returns!Auto_Header0.Caption = "Names for " & Me.name & " in year " & Me.year
qdExtData.Close
db.Close
qdf.Close
Set db = Nothing
Set qdf = Nothing
End Sub
【问题讨论】:
Compact & Repair 没有明显的效果?为什么你需要删除查询而不是仅仅提供不同的参数? WHERE 子句是唯一改变的还是一个全新的查询? 感谢 Brad 的回复,我真的很感激,因为我碰壁了。压缩和修复使总文件大小从 282mb 到 281mb。我正在尝试将其恢复到更合理的 44mb。我需要删除查询,因为它不允许我创建具有相同名称的查询,尽管我只在 where 子句中更改查询中的一个变量。所以整个查询是相同的,查询的代码是相同的,但是当用户单击“名称”字段时,我想将该名称放入 SQL 中。这就是为什么我有上面的代码 [forms]![myform]![firstname] 【参考方案1】:没有理由不将表单绑定到视图并使用打开表单命令的“where 子句”。它将消除所有这些代码。
然后您可以简单地使用:
strWhere = "table.FirstName = '" & me.FirstName & "'"
Docmd.OpenForm "Names”,,,strWhere
此外,C + R 不返回可用空间几乎没有意义。这里还有其他严重错误。
另外,你真的不需要每次都删除查询。只需假设传递始终存在,然后使用它:
strSQl = “your sql goes here as you have now”
Currentdb.Querydef("MyPass").SQL = strSQL
Docmd.Openform “your form”
以上就是你所需要的。我在这里计算了大约 3 行代码,它们将取代您现在拥有的所有内容。请注意,连接字符串信息当然是与 pass-through 一起保存的,不需要每次都设置或弄乱。
我还会对您的数据库进行反编译。我在所有开发机器上都有一个捷径设置,所以我只需右键单击即可反编译。以下是反编译的一些信息:
http://www.granite.ab.ca/access/decompile.htm
真的,我不知道你为什么不使用开放式表单的 where 子句?只需将表单绑定到 SQL 视图,无需任何条件。然后使用 open form 命令 - 您只从网络管道中拉取符合您的条件的记录。
请注意如何将 SQL 直接填充到查询 def 的 .SQL 属性中,如上所示 - 再次不需要删除代码,这也意味着您也不会在代码中弄乱连接信息。总共大约 3 行。
【讨论】:
...通过查询是一个很好的理由吗? :P以上是关于使用基于传递查询的表单访问 2010 膨胀的主要内容,如果未能解决你的问题,请参考以下文章