30 июля 2011 г.

Как вычислить произведение всех чисел в столбце таблицы одним SQL запросом

Я думаю, каждый знает такую статистическую функцию SQL, как SUM(). Она позволяет посчитать сумму всех значений по определённому столбцу (если не задано дополнительных условий). Но что, если нам вдруг понадобиться посчитать не сумму, а произведение всех значений?

Как ни странно, функция SUM() нам тоже пригодится. Как нам от произведения перейти к сумме? Вспомним начала матанализа: логарифм произведения равен сумме логарифмов. Будем использовать натуральный логарифм в паре с функцией возведения экспоненты в степень EXP(). Привожу пример для SQL SERVER, но должно работать и в других СУБД:

SELECT EXP(SUM(LOG(FIELD))) FROM TABLE

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

Вот так мы от суммы переходим к произведению в рамках одного изящного SQL запроса. С ходу не могу сказать, может ли это пригодиться в реальных проектах, но согласитесь - выглядит впечатляюще.

То же самое, только уже средствами LINQ to Objects:

// произведение этих чисел равно 120
int[] array = new int[] { 1, 2, 3, 4, 5 };

var result = Math.Exp((from a in array
  select Math.Log(a)).Sum());

Console.WriteLine("Произведение чисел равно: {0}", result);
Console.ReadKey();

В результате программа выдаст 120.

3 комментария:

  1. Всё гениальное просто! Но везде есть свои исключения. Если в поле хотя бы одной строки будет 0, то результат запроса будет неверен.

    ОтветитьУдалить
  2. Как вычислить произведение всех чисел в столбце таблицы одним SQL запросом:
    SELECT EXP(SUM(LOG(FIELD))) FROM TABLE

    Замечательное решение - огромное спасибо за данный вариант.
    Никогда не думал, что с таким столкнусь.

    Только вот ОПИСКА получилась у автора:
    Вместо "LOG" необходимо брать "LN", т.е. НАТУРАЛЬНЫЙ ЛОГАРИФМ.
    А так все замечательно.





    ОтветитьУдалить
  3. Если в колонке допустимы числа <=0, то запрос сильно усложняется.

    ОтветитьУдалить