Вопрос:

SQL-запрос, чтобы получить все данные в определенном диапазоне

sql

8344 просмотра

9 ответа

1870 Репутация автора

У меня есть таблица (предложение) с тремя столбцами, id, product_id и price.

offer
----- 
id (integer)   
product_id (integer)
price (decimal)

Я хотел запустить SQL-запрос, который будет возвращать количество предложений в диапазоне цен. диапазон должен быть как 0-1, 1-2, 2-3 и т. д.

price_lower   price_upper    number_of_offers
-------------------------------------------------------------
0                     1            4
1                     2            1
2                     3            0
3                     4            6
4                     5            2
... etc

Я сделал это, чтобы получить количество предложений от 0 до 1

SELECT * FROM offer WHERE price BETWEEN 0 and 1;

Каким должен быть запрос, чтобы получить желаемый результат.

Любая помощь будет оценена. Заранее спасибо.

Автор: aatifh Источник Размещён: 17.11.2009 08:20

Ответы (9)


1 плюс

43943 Репутация автора

ВЫБЕРИТЕ СУММУ (number_of_offers) ОТ предложения WHERE price_lower> = [самая низкая цена] И price_upper <= [самая высокая цена].

Биты в квадратных скобках, которые вы должны будете заполнить, например, вы можете подставить туда параметры.

Автор: slugster Размещён: 17.11.2009 08:26

0 плюса

5078 Репутация автора

Это должно быть правильно. Одно предостережение: если что-то стоит целую сумму, оно будет отображаться в зависимости от вашего вида sql, потому что «между» иногда включительно.

Автор: Anthony Potts Размещён: 17.11.2009 08:26

1 плюс

272889 Репутация автора

Чтобы получить вывод, который вы перечислили:

SELECT MIN(t.price) 'price_lower',
       MAX(t.price) 'price_upper',
       COUNT(*) 'number_of_offers'
  FROM OFFER t
 WHERE t.price BETWEEN 0 AND 1
UNION ALL
SELECT MIN(t.price) 'price_lower',
       MAX(t.price) 'price_upper',
       COUNT(*) 'number_of_offers'
  FROM OFFER t
 WHERE t.price BETWEEN 1 AND 2
UNION ALL
...

... добавление различных операторов SQL для каждой группы, которую вы хотите, изменяя предложение WHERE в соответствии с вашими потребностями.

Автор: OMG Ponies Размещён: 17.11.2009 08:28

3 плюса

138537 Репутация автора

Вы можете попробовать что-то вроде этого

DECLARE @Offer TABLE(
        ID INT IDENTITY (1,1),
        Product_ID INT,
        Price FLOAT
)

INSERT INTO @Offer SELECT 1, 0
INSERT INTO @Offer SELECT 1, .25
INSERT INTO @Offer SELECT 1, .5
INSERT INTO @Offer SELECT 1, .75
INSERT INTO @Offer SELECT 1, 1.
INSERT INTO @Offer SELECT 1, 1.25
INSERT INTO @Offer SELECT 1, 1.5
INSERT INTO @Offer SELECT 1, 1.75
INSERT INTO @Offer SELECT 1, 2.

INSERT INTO @Offer SELECT 2, 1
INSERT INTO @Offer SELECT 2, 1.25
INSERT INTO @Offer SELECT 2, 1.5
INSERT INTO @Offer SELECT 2, 1.75
INSERT INTO @Offer SELECT 2, 2.
INSERT INTO @Offer SELECT 2, 2.25
INSERT INTO @Offer SELECT 2, 2.5
INSERT INTO @Offer SELECT 2, 2.75
INSERT INTO @Offer SELECT 2, 3.

SELECT  Product_ID,
        FLOOR(Price) StartPrice,
        FLOOR(Price) + 1 EndPrice,
        COUNT(1) NumberItems
FROM    @Offer
GROUP BY Product_ID,
        FLOOR(Price)
ORDER BY 1, 2
Автор: Adriaan Stander Размещён: 17.11.2009 08:30

1 плюс

4330 Репутация автора

Я использовал:

select floor(price) as price_lower,
       ceiling(price) as price_upper,
       count(*) as offercount
   from tbl_offer
   group by floor(price), ceiling(price)

Для следующих тестовых данных:

insert into tbl_offer ([product_id],[price]) values (1, 1.9)
insert into tbl_offer ([product_id],[price]) values (2, 2.2)
insert into tbl_offer ([product_id],[price]) values (3, 2.3)
insert into tbl_offer ([product_id],[price]) values (4, 4.5)
insert into tbl_offer ([product_id],[price]) values (5, 2.7)

Я получил следующие результаты:

price_lower price_upper offercount  
----------- ----------- ----------- 
1 2 1
2 3 3
4 5 1

Единственное, чего не хватает в приведенном вами примере таблицы, это то, что у меня нет строки с price_lower 3, price_upper 4, offercount 0.

Автор: Chris Размещён: 17.11.2009 08:38

0 плюса

512 Репутация автора

create table offer_range (price_lower integer, price_upper integer);

insert into offer_range (price_lower, price_upper) 
values (0, 1), (1, 2), (2, 3), (3, 4), (4, 5), -- ...etc
;

select r.price_lower,
r.price_upper,
(
select count(*)
from offer o 
where o.price between r.price_lower and r.price_upper
) as number_of_offers
from offer_range r
;
Автор: hongliang Размещён: 17.11.2009 09:05

0 плюса

19393 Репутация автора

Этот позволяет вам установить отдельную таблицу PriceRange с диапазонами для каждого продукта.

DECLARE @Offer TABLE(
     ID INT IDENTITY (1,1)
     ,Product_ID INT
     ,Price decimal(8,2)
)

DECLARE @PriceRange TABLE(
     ID INT IDENTITY (1,1)
     ,Product_ID INT
     ,price_lower decimal(8,2)
     ,price_upper decimal(8,2)
)

SELECT x.Product_ID,  x.price_lower, x.price_upper, COUNT(*) as "number_of_offers"
   FROM 
    (
    SELECT o.Product_ID, o.Price, p.price_lower, p.price_upper,
      CASE 
        WHEN o.Price >= p.price_lower and o.Price < p.price_upper THEN 1
        ELSE 0
      END AS InRange           
    FROM @Offer AS o
      JOIN  @PriceRange as p ON o.Product_ID = p.Product_ID
    ) AS x
WHERE x.InRange = 1
GROUP BY x.Product_ID, x.price_lower, x.price_upper
Автор: Damir Sudarevic Размещён: 17.11.2009 09:33

4 плюса

1870 Репутация автора

Решение

Пока проверяю все ответы. Мне удалось написать запрос, конечно, с вашей помощью. Как немногие из вас предложили создать новую таблицу для хранения ассортимента предложений, чего я не хочу делать.

Итак, вот запрос SQL, что я хотел:

SELECT price as price_lower, (price + 1) as price_upper, (SELECT count(*) from offer WHERE price BETWEEN o.price and (o.price + 0.99)) from offer o GROUP BY price;

Спасибо всем за ваши большие усилия. Вы, ребята, молодцы.

Автор: aatifh Размещён: 18.11.2009 08:44

0 плюса

377 Репутация автора

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

declare @Max_Steps int
set @Max_Steps= 6

select Price_Group * data.Price_Step as price_lower, (Price_Group+1)*data.Price_Step as price_upper, count(id) as number_of_offers
from
(
    select id, price, ceiling(price/Price_Step) as Price_Group, Price_Step
    from
    (
        select cast((max(price) - min(price))/@Max_Steps as decimal(15,2))  as Price_Step
        FROM offer
    ) PriceRangeCalculator
cross join  
    (
        SELECT id, price
        FROM offer
    ) SourceData
) data
group by data.Price_Group, data.Price_Step
order by data.Price_Group
Автор: Santiago Regojo Размещён: 18.11.2009 11:32
Вопросы из категории :
32x32