找到Postgresql最高总薪水的部门的最佳方法

时间:2017-12-03 15:24:38

标签: sql postgresql aggregate-functions

让我们有2个标准表Employees and Departments

CREATE TABLE departments (
  id SERIAL PRIMARY KEY,
  name VARCHAR
);

CREATE TABLE employees (
  id SERIAL PRIMARY KEY,
  department_id INTEGER,
  name VARCHAR,
  salary NUMERIC(13,2)
);

找到拥有最多员工的部门名称的最佳方法是什么?总薪水。

我找到了两个解决方案,它们看起来太复杂了,不能完成这么简单的任务。

使用rank()

SELECT name FROM (
   SELECT name, rank() OVER ( ORDER BY salary DESC ) AS rank
   FROM (
          SELECT
            departments.name,
            sum(salary) AS salary
          FROM employees
            JOIN departments ON department_id = departments.id
          GROUP BY departments.name
        ) AS t1
 ) AS t2
WHERE rank = 1;

使用子查询

WITH t1 AS (SELECT
         departments.name,
         sum(salary) AS salary
       FROM employees
       JOIN departments ON departments.id = employees.department_id
       GROUP BY departments.name
)
SELECT name FROM t1
WHERE t1.salary = (SELECT max(salary) FROM t1);

乍一看使用rank应该效率较低,因为它执行不必要的排序。虽然EXPLAIN表明第一个选项更有效。 或许有人建议另一种解决方案。

那么,使用postgres找到最高工资总额的最佳方法是什么?

1 个答案:

答案 0 :(得分:-1)

我会将apply plugin: 'com.android.application' android { compileSdkVersion 26 buildToolsVersion "27.0.1" useLibrary 'org.apache.http.legacy' defaultConfig { applicationId "net.majorkernelpanic.spydroid" minSdkVersion 16 targetSdkVersion 26 versionCode 1 versionName "1.0" testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner" } buildTypes { release { minifyEnabled false proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } } } dependencies { compile fileTree(include: ['*.jar'], dir: 'libs') androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', { exclude group: 'com.android.support', module: 'support-annotations' }) compile 'com.android.support:appcompat-v7:26.+' testCompile 'junit:junit:4.12' compile files('libs/acra-4.4.0.jar') compile files('libs/GoogleAdMobAdsSdk-6.1.0.jar') compile files('libs/sc-light-jdk15on-1.47.0.2.jar') compile files('libs/scpkix-jdk15on-1.47.0.2.jar') compile files('libs/scprov-jdk15on-1.47.0.2.jar') compile files('libs/android-support-v4.jar') compile files('libs/gcm.jar') } 写为:

rank()

(附加子查询不应该影响性能,但它也不会增加任何内容来澄清查询。)

由于窗口函数是内置于数据库的,因此数据库具有使它们更有效的方法。获得SELECT * FROM (SELECT d.name, SUM(e.salary) AS salary, RANK() OVER (ORDER BY SUM(e.salary)) as rnk FROM employees e JOIn departments d ON e.department_id = d.id GROUP BY d.name ) d WHERE rnk = 1; 也有开销。但是,说实话,我希望这两种方法都有相似的表现。

我应该注意,如果你只想要一个部门返回 - 即使有关系 - 那么最简单的方法是:

MAX()