【发布时间】:2018-01-28 19:41:47
【问题描述】:
我正在考虑在选项 2 here 中设置的配置表,其中每个配置选项(或“事实”)有一行,其中包含事实的名称和事实的值。
将这些信息合并到具有一个或多个连接的另一个查询中的适当/最佳方法是什么?请注意,我明确不考虑过程 SQL 或 ORM 系统;仅限纯 SQL。
例如,考虑这些表作为一个人为的例子:
tbl_facts (Option_Name, Option_Value)
tbl_employees (Employee_ID, Name, Salary)
tbl_projects (Project_ID, Name, Manager_ID, Revenue)
Manager_ID 链接到 tbl_employees 以获取管理项目的员工。每个项目只有一名经理,但一名员工可以管理多个项目。在本示例中,Option_Value 为 numeric/double。
忽略项目其他员工的成本等,让我们找出每个项目的毛利润作为收入 - [经理]工资:
SELECT tbl_projects.Project_ID, tbl_projects.Name,
(tbl_projects.Revenue - tbl_employees.Salary) AS Gross_Profit
FROM tbl_projects INNER JOIN tbl_employees ON
tbl_projects.Manager_ID = tbl_employees.Employee_ID;
很简单。现在假设我们知道利润的税率是 20%,所以我们将 ("Tax Rate", 0.2) 存储在 tbl_facts(以及其他事实)中。我们想知道净利润。问题是,目前还没有明确的方法将此信息与我们现有的信息结合起来。
我看到/考虑过的选项:
-
与 tbl_facts 的笛卡尔/交叉连接。但是,某些 SQL 风格不支持这一点,或者至少不能始终如一地支持它(有时有效,有时无效)。
SELECT tbl_projects.Project_ID, tbl_projects.Name, (tbl_projects.Revenue - tbl_employees.Salary) AS Gross_Profit, tbl_facts.Option_Value * (tbl_projects.Revenue - tbl_employees.Salary) AS Net_Profit FROM (tbl_projects INNER JOIN tbl_employees ON tbl_projects.Manager_ID = tbl_employees.Employee_ID), tbl_facts WHERE tbl_facts.Option_Name="Tax Rate"; -
某些类型的 SQL 支持查找函数(例如,MS Access 的 dlookup())。但是,这不太好,因为您必须将值转换为所需的类型,而且我怀疑这会影响性能。
SELECT tbl_projects.Project_ID, tbl_projects.Name, (tbl_projects.Revenue - tbl_employees.Salary) AS Gross_Profit, cdbl(dlookup("Option_Value","tbl_facts","Option_Name='Tax Rate'")) * (tbl_projects.Revenue - tbl_employees.Salary) AS Net_Profit FROM tbl_projects INNER JOIN tbl_employees ON tbl_projects.Manager_ID = tbl_employees.Employee_ID; -
使用子查询添加人为的“连接列”。这似乎是一个糟糕的选择。
SELECT tbl_projects.Project_ID, tbl_projects.Name, (tbl_projects.Revenue - sq_employees.Salary) AS Gross_Profit, sq_facts.Option_Value * (tbl_projects.Revenue - sq_employees.Salary) AS Net_Profit FROM tbl_projects INNER JOIN (SELECT 1 AS Join_Col, tbl_employees.* FROM tbl_employees) AS sq_employees ON tbl_projects.Manager_ID = sq_employees.Employee_ID), INNER JOIN (SELECT 1 AS Join_Col, Option_Value FROM tbl_facts WHERE Option_Name="Tax Rate") AS sq_facts ON sq_employees.Join_Col = sq_facts.Join_Col;
从这样的配置表中获取此信息的首选方法是什么?它是上述选项之一,还是我没有考虑过的其他选项?
【问题讨论】:
-
您的标签让人们感到困惑:您是在追求 Oracle 还是 MS Access 解决方案?这两种风格支持不同的语法,因此您的问题不太可能有一个统一的解决方案。
-
我追求的是通用解决方案。我目前正在研究 MS Access 中的一个项目并参考上面的 dlookup,但问题陈述一般适用于 RDBMS。我也经常在 Oracle 工作,在那里遇到过这个问题。
-
没有通用的解决方案。不同的数据库产品将适合不同的实现。
-
好的,那么我将我的范围限制为 Access 和 Oracle,如已标记。我知道可能有特定于实现的解决方案,但我对如何最好地使用 SQL 标准来处理这种情况很感兴趣。如果我在这里天真/理想主义,我深表歉意——我试图了解这个非常常见的问题在多大程度上得到了解决。
标签: sql database oracle ms-access