Python Oracle11g-即使有NOCACHE提示,查询也会缓存

Python Oracle11g-即使有NOCACHE提示,查询也会缓存,python,oracle,oracle11g,cx-oracle,Python,Oracle,Oracle11g,Cx Oracle,我正在使用cx_Oracle模块用Python进行一些数据库基准测试。为了对结果进行基准测试,我运行了150个独特的查询,并为每个查询的执行计时。我在做这样的事情: c = connection.cursor() starttime = time.time() c.execute('SELECT /*+ NOCACHE */ COUNT (*) AS ROWCOUNT FROM (' + sql + ')') endtime = time.time() runtime = endtime - s

我正在使用cx_Oracle模块用Python进行一些数据库基准测试。为了对结果进行基准测试,我运行了150个独特的查询,并为每个查询的执行计时。我在做这样的事情:

c = connection.cursor()
starttime = time.time()
c.execute('SELECT /*+ NOCACHE */ COUNT (*) AS ROWCOUNT FROM (' + sql + ')')
endtime = time.time()
runtime = endtime - starttime
每个查询都是通过变量
sql
传入的,它们的长度、运行时间和访问的表都有很大的不同。尽管如此,所有查询都表现出以下行为:

第一次运行:非常慢(相对而言)

第二次跑步:速度明显加快(需要1/2到1/5的时间)

第三次跑步:略快于第二次跑步

所有后续运行>=4:大约等于第三次运行

我需要禁用缓存以获得准确的结果,但前几次运行确实会丢失我的数据;这就好像
NOCACHE
根本不起作用。。。这是怎么回事

编辑:艾伦回答了我的问题,但对于任何可能感兴趣的人,我做了更多的研究,发现这两页也很有用:

来自:

NOCACHE提示指定为表检索的块是 将LRU列表中最近至少使用过的一端放置在缓冲区中 执行完整表扫描时缓存。这是正常的行为 缓冲区缓存中的块数

从这一点看来,
nocache
提示并没有达到您期望的效果


您可以通过运行
ALTER SYSTEM FLUSH shared_POOL
清除共享缓存,通过运行
ALTER SYSTEM FLUSH buffer_cache
清除缓冲缓存。您需要在每个查询之间执行此操作,以防止缓存被使用。

您希望实时系统执行缓存,因为这样可以提高性能。那么,您是否应该安排基准测试,以便放弃每个查询的前两次运行(也称为“老化”)。您在
sql
中有哪些查询?您当前传入查询的方式不允许使用绑定变量,即,如果查询包含输入参数,这些参数将嵌入到查询文本中,这将导致在每次执行之前出现一个,我认为这会导致#1中的延迟。我有点困惑。由于我假设查询将在生产中被硬解析,所以我希望保持较慢的运行速度。事实上,我实际上是想让它们与第一次跑步保持一致。这种情况需要不缓存的查询,因为测试是在具有不同配置的多个数据库之间进行的,系统上的用户只会运行一次查询,这使得缓存时间对于基准测试无效。好的,我不知道您正在测试只会在生产中运行一次的查询。如果查询非常繁重,那么硬解析可能不是这里最大的因素,而是查询执行非常慢。您能使用像tkprof这样的Oracle实用程序进行评测吗?我可能会在周一研究这个问题。我不是DBA,我只是为他编写基准脚本的人。我对这东西很陌生,所以我还有很多东西要学@McGlothlin需要注意的是,Oracle不会缓存查询结果,而是缓存最常用的表和索引块。这意味着不同的查询可以利用相同的缓存。您很可能希望在任何OLTP测试中排除“老化”时间。通常是
改变系统刷新缓冲区\u缓存只能帮助在数据仓库中进行实际测试。不幸的是,这使您的测试更加困难—如果查询、数据和环境不完全匹配,就很难复制缓存行为。