Database 版 (精华区)
发信人: wodeji (西西), 信区: Database
标 题: [转载] PowerBuilder 开 发 系 列 谈 (18)
发信站: 紫 丁 香 (Tue Sep 29 17:52:12 1998), 站内信件
【 以下文字转载自 Programming 讨论区 】
【 原文由 two 所发表 】
我 们 使 用PowerBuilder 编 程 时 总 是 会 大 量 的 用 到 数 据 库 的 查 询 语 句, 对 于 一
条 复 杂 的 查 询 语 句 来 说, 对 相 同 的 查 询 条 件 的 实 现 一 般 总 可 以 有 多 种 不 同 的
表 达 方 法, 而 不 同 的 表 达 会 使 数 据 库 的 响 应 速 度 大 相 径 庭。 据 统 计, 约 有90%
性 能 问 题 是 由 于 应 用 开 发 的 程 序 员 或 用 户 使 用 了 不 恰 当 的 查 询 语 句 而 使 系 统
的 响 应 速 度 减 慢, 因 此 提 高 书 写SQL 语 句 的 质 量 对 软 件 性 能 的 提 高 有 很 大 关
系, 然 而 查 询 语 句 的 好 坏 往 往 是 同 实 际 运 行 系 统 的 数 据 库 结 构、 记 录 的 数 量
等 具 体 情 况 有 关 的, 我 们 无 法 只 用 几 条 简 单 的 普 遍 适 用 的 规 律 来 总 结 应 当 怎
样 优 化 查 询 语 句, 以 得 到 更 高 的 性 能。 不 过 我 们 首 先 应 当 对 数 据 库 管 理 系 统
最 基 本 的 工 作 规 律 有 一 些 了 解, 这 样 才 能 使 我 们 在 对 查 询 进 行 时 优 化 有 所 根
据。
由 于SQL 语 言 是 面 向 结 果 而 不 是 面 向 过 程 的 查 询 语 言, 所 以 一 般 支 持SQL
语 言 的 大 型 关 系 型 数 据 库 都 需 要 使 用 一 个 基 于 成 本 的 优 化 器, 为 一 个 即 时 查
询 提 供 一 个 最 佳 的 执 行 策 略。 对 于 优 化 器, 输 入 是 一 条 查 询 语 句, 输 出 是 一
个 执 行 策 略。 这 个 执 行 策 略 是 执 行 这 个 查 询 所 需 要 的 一 系 列 步 骤。 数 据 库 的
反 应 速 度 经 常 就 体 现 在 这 一 个 优 化 算 法 上。 不 同 的 查 询 策 略 和 查 询 步 骤 可 使
得 服 务 器 的 反 应 不 同, 因 此 采 用 适 当 的 查 询 策 略 可 使 得 系 统 性 能 大 大 的 提
高。
优 化 器 的 优 化 是 基 于 用 户 对 所 查 询 表 的 内 容 和 其 他 一 些 服 务 器 的 有 关 因
素 如Cache 大 小、Cache 策 略、I/O 大 小 等。 一 般 来 说 硬 盘 访 问 是 成 本 最 高 的 操
作, 因 此 对 用 户 来 讲, 使 优 化 器 能 对 字 段 的 索 引 进 行 操 作 是 优 化 查 询 的 关
键。
SQL 查 询 语 句 都 可 以 有 很 多 种 执 行 策 略, 优 化 器 将 估 计 出 全 部 的 执 行 方 法
中 所 需 时 间 最 少 的 也 就 是 所 谓 成 本 最 低 的 那 一 种 方 法。 一 般 来 讲, 最 为 重 要
的 选 择 就 是 使 用 什 么 索 引 和 采 用 何 种 表 的 连 接 手 段, 而 所 有 优 化 的 进 行 都 是
基 于 用 户 所 使 用 的 查 询 语 句 中 的where 子 句。
优 化 器 对where 子 句 中 的 优 化 分 为 以 下 几 类:
搜 索 参 数(searchargument)
搜 索 参 数 的 核 心 就 是 数 据 库 能 否 使 用 表 中 字 段 的 索 引 来 查 询 数 据, 而 不
必 直 接 查 询 记 录 中 的 数 据。 如 带 有=,<,>,>=,<= 等 操 作 符 的 条 件 系 统 就 可 以 直 接
使 用 索 引。
如 下 列 条 件 是 搜 索 参 数:
id = " T0001”
salary > 30000
a = 1 and c = 7
而下列则不是搜索参数:
salary = commission
dept != 10
salary *12 >= 30000
a = 1 or c = 7
当然优化器有时可以将非搜索参数转化为搜索参数,如:
SELECT name FROM employee WHERE salary BETWEEN $10000 AND $15000
SELECT name FROM employee WHERE salary >= $10000 AND salary <= $15000
SELECT name FROM employee WHERE name like "a%"
SELECT name FROM employee WHERE name >= "a" AND name<= "b"
SELECT name FROM employee WHERE salary > $3000 * 12
SELECT name FROM employee WHERE salary > $36000
因 此 我 们 在 查 询 中 应 当 提 供 能 一 些 冗 余 的 搜 索 参 数, 使 优 化 器 有 更 多 的
选 择 余 地, 如title 和titleauthor 两 张 表 是 一 对 多 的 关 系, 同 样 的 查 询 条 件 我 们 有 以
下 三 种 表 现 方 法:
SELECT title_id, title FROM titles, titleauthor
WHERE title.title_id = titleauthor.title_id
AND titleauthor.title_id = 'T81002'
SELECT title_id, title FROM titles, titleauthor
WHERE title.title_id = titleauthor.title_id
AND title.title_id = 'T81002'
SELECT title_id, title FROM titles, titleauthor
WHERE title.title_id = titleauthor.title_id
AND title.title_id = 'T81002'
AND titleauthor.title_id = 'T81002'
显 然 三 种 方 法 一 种 比 一 种 要 好, 因 为 后 者 为 优 化 器 提 供 了 更 多 的 选 择 机
会。
连 接 条 件
接 连 时 优 化 器 将 所 有 连 接 的 方 法 全 部 列 举 出 来, 计 算 每 一 种 连 接 的 成 本,
选 择 成 本 最 低 的 一 种。 如 连 接 时 用 到 的 数 据 无 法 获 得, 一 般 系 统 会 使 用 平 均
密 度 作 为 依 据, 估 算 可 能 的 命 中 率。 ' 或' 运 算 条 件
当 查 询 语 句 中 有IN 这 样 的 关 键 词 时, 优 化 器 将 转 化 其 中 的 内 容 以OR 并 列
条 件。 例 如:
SELECT * FROM author
WHERE au_lname in ('Berry','Densham')
将转化为:
SELECT * FROM author
WHERE au_lname = 'Berry' or au_lname = 'Densham'
数 据 库 管 理 系 统 将 对 每 一 个OR 从 句 进 行 查 询, 将 所 有 的 结 果 合 并 后 去 除
重 复 项 作 为 最 终 结 果。
基 于 对 上 述 数 据 库 优 化 器 的 了 解, 为 确 保 对 我 们 将 要 执 行 的 查 询 语 句 得
以 进 行 准 确 的 优 化, 我 们 应 注 意 以 下 几 点:
1. 避 免 使 用 不 兼 容 的 数 据 类 型。 例 如float 和int,char 和varchar,binary 和varbinary 是
不 兼 容 的。 数 据 类 型 的 不 兼 容 可 能 使 得 优 化 器 无 法 执 行 一 些 本 来 可 以 进 行 的
优 化 操 作。 例 如:
SELECT name FROM employee
WHERE salary > 60000
在 这 条 语 句 中, 如salary 字 段 是money 型 的, 则 优 化 器 很 难 对 其 进 行 优 化, 因
为60000 是 个 整 型 数。 我 们 应 当 在 编 程 是 使 用 一 个 函 数 将 整 型 数 转 化 成 为 钱 币
型 的 数, 而 不 要 等 到 运 行 时 转 化。
2. 如 果 在 一 个 存 储 过 程 或 触 发 器 中, 有 表 达 式 的 值 在 编 译 时 无 法 得 到, 优
化 器 就 只 能 使 用 它 的 平 均 密 度 来 估 计 命 中 的 记 录 数。 例 如:
DECLARE @value money
SELECT name
FROM employee
WHERE salary = @value
这 样 的 命 令 是 可 优 化 的。 只 是 由 于@value 的 值 在 执 行 前 不 知 道, 它 只 能 使
用 其 平 均 密 度, 来 估 计 这 条 命 令 将 要 命 中 的 记 录 数。
3. 避 免 对 搜 索 参 数 使 用 其 他 数 学 操 作 符。 如 要 将
SELECT name FROM employee
WHERE SUBSTRING(id, 1, 1) = 'B'
SELECT name FROM emplyee
WHERE salary * 12 > 30000
写成为:
SELECT name FROM employee
WHERE id like 'B%'
SELECT name FROM emplyee
WHERE salary > 3000
4. 避 免 使 用!= 或<> 等 这 样 的 操 作 符, 因 为 这 会 使 系 统 无 法 使 用 索 引, 而 只
能 直 接 搜 索 表 中 的 数 据。 例 如:
SELECT id FROM employee
WHERE id != 'B%'
优 化 器 将 无 法 通 过 索 引 来 确 定 将 要 命 中 的 行 数。
上 述 我 们 提 到 的 是 一 些 基 本 的 提 高 查 询 速 度 的 注 意 事 项, 但 是 在 更 多 的
情 况 下, 程 序 员 往 往 需 要 反 复 地 试 验 比 较 不 同 的 语 句 以 得 到 最 佳 的 方 案。 此
外 更 为 重 要 的 是 需 要 数 据 库 管 理 员 在 数 据 库 的 服 务 器 一 端 调 整 数 据 库 管 理 系
统 的 参 数, 以 得 到 更 快 的 响 应 性 能, 这 就 超 出 了 本 文 的 讨 论 范 围。
--
※ 来源:.紫 丁 香 bbs.hit.edu.cn.[FROM: 202.97.236.132]
--
※ 转载:.紫 丁 香 bbs.hit.edu.cn.[FROM: whs.hit.edu.cn]
--
※ 转载:.紫 丁 香 bbs.hit.edu.cn.[FROM: cadcam.hit.edu.c]
Powered by KBS BBS 2.0 (http://dev.kcn.cn)
页面执行时间:5.249毫秒