Сравнить сгруппированные по строкам в одной строке - PullRequest
1 голос
/ 07 июня 2019

У меня есть таблица со списком разных сумм, и я хочу сгруппировать эти суммы из разных источников, чтобы проверить, совпадают ли они.Итак, моя таблица выглядит примерно так:

id   name  amount description startDate            endDate              location type sourceId linkId   isMatch
A111 name1 111.11 desc        2019-06-06T00:00:00Z 2019-06-06T00:00:00Z location a    INTERNAL A111X111 True
A111 name1 222.22 desc        2019-06-06T00:00:00Z 2019-06-06T00:00:00Z location b    INTERNAL A111X111 True
A111 name1 555.55 desc        2019-06-06T00:00:00Z 2019-06-06T00:00:00Z location a&b  INTERNAL A111X111 True
A111 name1 444.44 desc        2019-06-06T00:00:00Z 2019-06-06T00:00:00Z location a    EXTERNAL A111X111 True
A111 name1 444.44 desc        2019-06-06T00:00:00Z 2019-06-06T00:00:00Z location b    EXTERNAL A111X111 True

Я могу сгруппировать их так:

SELECT
  a.name,
  a.id,
  SUM(a.amount) AS total,
  a.description,
  DATEDIFF(day, a.startDate, a.endDate) AS days,
  a.location,
  a.sourceId,
  a.linkId,
  a.isMatch
FROM
  DataHistory a
GROUP BY
a.name, a.id, a.description, DATEDIFF(day, a.startDate, a.endDate), a.location, a.sourceId, a.linkId, a.isMatch 

Чтобы получить почти то, что я хочу:

name  id   total  description days location sourceId linkId   isMatch
name1 A111 888.88 desc        0    location EXTERNAL A111X111 True
name1 A111 888.88 desc        0    location INTERNAL A111X111 True

Ноя хочу иметь столбец с разницей между двумя значениями (внутренним и внешним), и поэтому я хочу, чтобы эти две записи отображались в одной строке (а также потому, что таких пар на самом деле будет много).В этом примере разница равна нулю, но я буду искать случаи, когда разница не равна нулю.Может случиться так, что нет внешних или внутренних записей (отсюда 0 для суммы) или просто суммы суммируются до разных сумм.Я подумал о том, чтобы, возможно, вставить сгруппированные записи во временную таблицу, а затем попробовать какое-то самосоединение, но я не уверен, будет ли это работать во всех случаях, и это определенно не кажется эффективным, если у меня действительно много таких записей,

Я также создал скрипту SQL здесь: http://www.sqlfiddle.com/#!18/7a5ff3/1

Буду признателен за любую помощь.

Ответы [ 2 ]

1 голос
/ 07 июня 2019

Вам нужно поворачиваться. В любом случае, когда вы группируете, условное агрегирование - самый естественный путь

SELECT
  a.name,
  a.id,
  SUM(CASE a.sourceId WHEN 'INTERNAL' THEN  a.amount ELSE 0 END) AS totalINTERNAL,
  SUM(CASE a.sourceId WHEN 'EXTERNAL' THEN  a.amount ELSE 0 END) AS totalEXTERNAL,
  a.description,
  DATEDIFF(day, a.startDate, a.endDate) AS days,
  a.location,
  a.linkId,
  a.isMatch
FROM
  DataHistory a
GROUP BY
a.name, a.id, a.description, DATEDIFF(day, a.startDate, a.endDate), a.location, a.linkId, a.isMatch
1 голос
/ 07 июня 2019

Попробуйте, уменьшите sourceId с group by и select и суммируйте всю сумму, но для external возьмите -a.amount. Это даст вам разницу:

SELECT
  a.name,
  a.id,
  SUM(CASE WHEN a.sourceId = 'INTERNAL' THEN a.amount ELSE -a.amount END) AS total,
  a.description,
  DATEDIFF(day, a.startDate, a.endDate) AS days,
  a.location,
  a.linkId,
  a.isMatch
FROM
  DataHistory a
GROUP BY
a.name, a.id, a.description, DATEDIFF(day, a.startDate, a.endDate), a.location, a.linkId, a.isMatch
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...