Модераторы: Akina
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> задачка с запросом на вычисления значений полей 
:(
    Опции темы
Lunatikus
Дата 7.9.2007, 16:09 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 503
Регистрация: 29.6.2007

Репутация: 2
Всего: 6



здравствуйте снова,господа программисты.Наткнулся на задачку с составлением запроса следущего содержания:
есть таблица DEAL:data(datetime),univer(varchar),ostatok(float),prognoz(float),zakaz(float),zayavka(float):
--data-----------------------univer-----ostatok---prognoz---zakaz----zayavka--
--07.09.2007--------------A1----------100--------15----------5----------NULL------
--08.09.2007--------------A1----------NULL------15----------5----------NULL------
--09.09.2007--------------A1----------NULL------15----------5----------NULL------
--10.09.2007--------------A1----------NULL------15----------5----------NULL------
--11.09.2007--------------A1----------NULL------15----------5----------NULL------
--12.09.2007--------------A1----------NULL------15----------5----------NULL------
--13.09.2007--------------A1----------NULL------15----------5----------NULL------
--07.09.2007--------------A2----------100--------15----------5----------NULL------
--08.09.2007--------------A2----------NULL------15----------5----------NULL------
--09.09.2007--------------A2----------NULL------15----------5----------NULL------
--10.09.2007--------------A2----------NULL------15----------5----------NULL------
--11.09.2007--------------A2----------NULL------15----------5----------NULL------
--12.09.2007--------------A2----------NULL------15----------5----------NULL------
--13.09.2007--------------A2----------NULL------15----------5----------NULL------
Т.е. простая табличка с перечислением остатков по каждому универу(артикулы)на каждую дату,начиная с текущей.Задача в том,чтобы получить выборку univer всех значений ,которые сейчас NULL.
Вычисляются просто(проблема в том,как эти вычисления в запрос впихнуть):значение остатка=значение ostatok за предыдущий день-prognoz-zakaz.Программно сделать несложно,а вот я задумался,как можно с помощью запроса выбрать эти данные,а не считать программно.Есть какие-нибудь мысли?

Добавлено @ 16:18
я так понял,без связей рядом стоящих записей не обойтись.А такое возможно?Я не сталкивался с этим-программно все время делал.

Это сообщение отредактировал(а) Lunatikus - 7.9.2007, 16:18


--------------------
TheSin - небольшое игровое сообщество взрослых и молодых(L2,WoW,Aion,RFonline and other not mmorpg,not computer games).
сайт гильдии
PM MAIL   Вверх
SergKO
Дата 7.9.2007, 17:53 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 231
Регистрация: 14.3.2005

Репутация: 17
Всего: 20



как идея

Код

declare @DEAL table (data datetime ,univer varchar(10) ,ostatok float ,prognoz float ,zakaz float ,zayavka float);

    insert into @DEAL
        select '20070907','A1',100,15,5,NULL
        union all
        select '20070908','A1',NULL,15,5,NULL
        union all
        select '20070909','A1',NULL,15,5,NULL
        union all
        select '20070910','A1',NULL,15,5,NULL
        union all
        select '20070911','A1',NULL,15,5,NULL
        union all
        select '20070912','A1',NULL,15,5,NULL
        union all
        select '20070913','A1',NULL,15,5,NULL
        union all
        select '20070907','A2',100,15,5,NULL
        union all
        select '20070908','A2',NULL,15,5,NULL
        union all
        select '20070909','A2',NULL,15,5,NULL
        union all
        select '20070910','A2',NULL,15,5,NULL
        union all
        select '20070911','A2',NULL,15,5,NULL
        union all
        select '20070912','A2',NULL,15,5,NULL
        union all
        select '20070913','A2',NULL,15,5,NULL

declare    @ostatok float, @univer varchar(10);

    select @ostatok = 0, @univer = '';
    update d1
    set 
        @ostatok = d1.ostatok = case when 
                                    case when @univer = d2.univer 
                                        then  @ostatok - d2.prognoz - d2.zakaz 
                                        else d2.ostatok - d2.prognoz - d2.zakaz 
                                    end >= 0
                                then 
                                    case when @univer = d2.univer 
                                        then  @ostatok - d2.prognoz - d2.zakaz 
                                        else d2.ostatok - d2.prognoz - d2.zakaz 
                                end
                             else 0 
                            end
        , @univer = d1.univer
    from @DEAL d1
        inner join @DEAL d2 on d2.data = d1.data-1 and d2.univer = d1.univer;

    select  * from @DEAL;

PM MAIL   Вверх
Lunatikus
Дата 10.9.2007, 09:37 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 503
Регистрация: 29.6.2007

Репутация: 2
Всего: 6



идея отличная  smile ,но поясни,пожалуйста,пару вещей:где тут видно,что будет не просто вычитание значения из предыдущей записи,а то,что это начнется со значения 100 и последовательно посчитав следующую строку.Использует ее новое значение для расчет третьей.Не вижу этого,скорее всего, в силу своей необразованности.С декларом не работал.Но смысл понял =) к тому же,я так понимаю,этот вариант только для фиксированной таблицы с фиксированными значениями =) а если мы не знаем что в таблице,лишь то что остатки на самую первую дату у всех универов имеют значение и отсчет идет от него?


--------------------
TheSin - небольшое игровое сообщество взрослых и молодых(L2,WoW,Aion,RFonline and other not mmorpg,not computer games).
сайт гильдии
PM MAIL   Вверх
SergKO
Дата 10.9.2007, 11:26 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 231
Регистрация: 14.3.2005

Репутация: 17
Всего: 20



1. это просто идея.
2. вычитание начнется не со значения 100, а с первого d2.univer неравного @univer 
 
Код

                                    case when @univer = d2.univer 
                                        then  @ostatok - d2.prognoz - d2.zakaz 
                                        else d2.ostatok - d2.prognoz - d2.zakaz 
                                end
т.е. если d2.univer == @univer , то продолжаем вычислять @ostatok и апдейтить поле d1.ostatk = "@ostatok - d2.prognoz - d2.zakaz". Иначе @ostatok и поле d1.ostatk = d2.ostatok - d2.prognoz - d2.zakaz. Строка с первой датой по текущему значению @univer под апдейт не подпадает. После вычисления остатка параметру @univer присваивается значение обработанного d1.univer. При выборке следующей строки они могут уже не совпадать и вычисления начнуться заново. Т.е. это тот-же цикл.
Остальное - проверка, чтобы остаток не был меньше 0.
3. Дорабатывать надо для случая, когда даты идут не последовательно, а может быть разрыв более чем 1 день. И извлекать для расчетов с сортировкой order by univer, data.

Это сообщение отредактировал(а) SergKO - 10.9.2007, 11:31
PM MAIL   Вверх
Lunatikus
Дата 10.9.2007, 12:22 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 503
Регистрация: 29.6.2007

Репутация: 2
Всего: 6



нет,все верно,теперь врубился.Первое несовпадение по универу и соответствует первой дате.
мне все же интересно,можно ли вот это
Код

insert into @DEAL
        select '20070907','A1',100,15,5,NULL
        union all
        select '20070908','A1',NULL,15,5,NULL
        union all
        select '20070909','A1',NULL,15,5,NULL
        union all
        select '20070910','A1',NULL,15,5,NULL
        union all
        select '20070911','A1',NULL,15,5,NULL
        union all
        select '20070912','A1',NULL,15,5,NULL
        union all
        select '20070913','A1',NULL,15,5,NULL
        union all
        select '20070907','A2',100,15,5,NULL
        union all
        select '20070908','A2',NULL,15,5,NULL
        union all
        select '20070909','A2',NULL,15,5,NULL
        union all
        select '20070910','A2',NULL,15,5,NULL
        union all
        select '20070911','A2',NULL,15,5,NULL
        union all
        select '20070912','A2',NULL,15,5,NULL
        union all
        select '20070913','A2',NULL,15,5,NULL


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


--------------------
TheSin - небольшое игровое сообщество взрослых и молодых(L2,WoW,Aion,RFonline and other not mmorpg,not computer games).
сайт гильдии
PM MAIL   Вверх
SergKO
Дата 10.9.2007, 12:59 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 231
Регистрация: 14.3.2005

Репутация: 17
Всего: 20



Если я правильно понял вопрос, то 
Код

    insert into @DEAL
        select data, univer, ostatok, prognoz, zakaz, zayavka
        from DEAL
        where data between @begin_date and @end_date
        order by univer, data


И еще. Более универсально и независимо от шага даты будет, если в @DEAL добавить поле с identity и связывать по нему

Код

declare @DEAL table (id int identity (1, 1), data datetime ,univer varchar(10) ,ostatok float ,prognoz float ,zakaz float ,zayavka float);

    from @DEAL d1
        inner join @DEAL d2 on /*d2.data = d1.data-1*/ d2.id= d1.id-1 and d2.univer = d1.univer;


ЗЫ
Спасибо за "плюс в репу" smile , но алгоритм такого апдейта с параметрами не мой, сам подглядел (не помню уже где). Там собирали в строку значение поля из нескольких записей.


Это сообщение отредактировал(а) SergKO - 11.9.2007, 05:31
PM MAIL   Вверх
Lunatikus
Дата 11.9.2007, 08:41 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 503
Регистрация: 29.6.2007

Репутация: 2
Всего: 6



шаг даты всегда равняется одному дню,так что усложнения не надо =) чтож буду пробовать этот запрос подстраивать под себя...


--------------------
TheSin - небольшое игровое сообщество взрослых и молодых(L2,WoW,Aion,RFonline and other not mmorpg,not computer games).
сайт гильдии
PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "MS SQL"
Akina

Akina

Запрещается!

Публиковать ссылки и обсуждать взлом чего бы то ни было.

  • Действия модераторов можно обсудить здесь
  • С просьбами о написании курсовой, реферата и т.п. обращаться сюда
  • Вопросы составления неспецифических запросов рассматриваются здесь
  • Используйте теги [code=sql][/code] для подсветки кода. Используйтe чекбокс "транслит" (возле кнопок кодов) если у Вас нет русских шрифтов.

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Zloxa, Akina.

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | MS SQL Server | Следующая тема »


 




[ Время генерации скрипта: 0.1459 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.