Гость
Целевая тема:
Создать новую тему:
Автор:
Форумы / FoxPro, Visual FoxPro [игнор отключен] [закрыт для гостей] / Помогите с запросом / 25 сообщений из 25, страница 1 из 1
11.12.2006, 14:07
    #34190233
rebroff
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Добрый день.Есть dbf-таблица движения материалов. Поля sklad(цех), nom (номенклатурный номер),sum (сумма прихода или расхода), vid (определяет, чем явл. сумма:приходом или расходом. 40-расход, остальные значения-приход). Задача: выбрать только те записи, сгруппировав по номенклатурному номеру и по цехам, для которых остаток (приход-расход) >1000.

Запрос "sql40" (выбираем с видом 40):

Код: plaintext
1.
2.
3.
4.
SELECT nomer,sklad,
SUM(mtb60."sum") Summ
FROM mtb60
WHERE vid = "40"
GROUP BY nomer,sklad

Запрос "sqlnot40" (с видом не равным 40, т. е. приход):

Код: plaintext
1.
2.
3.
4.
SELECT nomer,sklad,
SUM(mtb60."sum") Summ, sum(kol) skol
FROM mtb60
WHERE vid<>"40"
GROUP BY nomer,sklad

Общий запрос:

Код: plaintext
1.
2.
3.
4.
5.
6.
SELECT
a.nomer, b.nomer,a.sklad,b.sklad,a.Summ SummA, b.Summ SummB, a.Summ - b.Summ SummAB,
FROM
"sumNot40.sql" a
JOIN "sum40.sql" b ON (a.nomer = b.nomer and a.sklad=b.sklad and a.sklad=:nomskl)
WHERE
a.Summ - b.Summ >  1000 

Проблема в том, что, если по определённому номенк. номеру расхода не было, значит и нет соотв. записи для такого номера с видом "40", а значит a.Summ - b.Summ не имеет смысла. Но этом случае нужно считать расход равным 0 и в остаток попадает весь приход. Помогите реализовать. Заранее премного благодарен.
...
Рейтинг: 0 / 0
11.12.2006, 14:57
    #34190429
LeKo
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
А если так попробовать:
Код: plaintext
1.
2.
3.
4.
5.
6.
SELECT
a.nomer, b.nomer,a.sklad,b.sklad,a.Summ SummA, b.Summ SummB, a.Summ - b.Summ SummAB,
FROM
"sumNot40.sql" a
LEFT JOIN "sum40.sql" b ON (a.nomer = b.nomer and a.sklad=b.sklad and a.sklad=:nomskl)
WHERE
(a.Summ - b.Summ >  1000 ) OR (a.Summ> 1000  AND ISNULL(b.Summ))
...
Рейтинг: 0 / 0
11.12.2006, 15:00
    #34190437
AleksMed
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Код: plaintext
1.
2.
3.
4.
SELECT nomer,sklad,
SUM(iif(vid = "40",-mtb60."sum",mtb60."sum")) Summ
FROM mtb60
GROUP BY nomer,sklad
...
Рейтинг: 0 / 0
11.12.2006, 15:01
    #34190439
AleksMed
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Код: plaintext
1.
2.
3.
4.
5.
SELECT nomer,sklad,
SUM(iif(vid = "40",-mtb60."sum",mtb60."sum")) Summ
FROM mtb60
GROUP BY nomer,sklad
HAVING Summ> 1000 
...
Рейтинг: 0 / 0
11.12.2006, 15:09
    #34190479
rebroff
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Работаю через BDE. IIF отпадает.
...
Рейтинг: 0 / 0
11.12.2006, 15:13
    #34190494
AleksMed
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
rebroffРаботаю через BDE. IIF отпадает.
И что, в BDE нет аналога?
...
Рейтинг: 0 / 0
11.12.2006, 15:14
    #34190497
AleksMed
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
CASE то он должен понимать
...
Рейтинг: 0 / 0
11.12.2006, 15:18
    #34190508
rebroff
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Загвоздка в том, что для некоторых номенклатурных номеров не существует записи для данного номера с видом = "40". Т.е. расхода не было. Логически расход =0.
...
Рейтинг: 0 / 0
11.12.2006, 15:27
    #34190557
AleksMed
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
SELECT nomer,sklad,
SUM(case vid = "40" then  0  else mtb60."sum" end) Prixod,
SUM(case vid = "40" then mtb60."sum" else  0  end) Rasxod,
SUM(case vid = "40" then -mtb60."sum" else mtb60."sum" end) Summ
FROM mtb60
GROUP BY nomer,sklad
HAVING Summ> 1000 
...
Рейтинг: 0 / 0
11.12.2006, 15:35
    #34190585
rebroff
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
case ему (BDE) тоже невдомёк:(
...
Рейтинг: 0 / 0
11.12.2006, 16:01
    #34190699
-=AlexiS=-
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
а Full Join понимает ?
...
Рейтинг: 0 / 0
11.12.2006, 16:18
    #34190795
rebroff
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Обязательно!
...
Рейтинг: 0 / 0
11.12.2006, 16:21
    #34190814
-=AlexiS=-
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Может поймет что-то типа такого


Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
SELECT
nvl(a.nomer, b.nomer) as nomer ,
nvl(a.sklad,b.sklad) as sklad ,
,nvl(a.Summ, 0 ) - nvl(b.Summ, 0 ) as  SummAB,
FROM
"sumNot40.sql" a
FULL JOIN "sum40.sql" b ON (a.nomer = b.nomer and a.sklad=b.sklad and a.sklad=:nomskl)
WHERE
nvl(a.Summ, 0 ) - nvl(b.Summ, 0 )  >  1000 

или даже такого

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
SELECT
nomer,sklad,sum(Sum) as  SummAB,
FROM
( SELECT nomer,sklad,
     mtb60.sum
FROM mtb60
WHERE vid = "40"
union all
SELECT nomer,sklad,
     mtb60.sum
FROM mtb60
WHERE vid <> "40"
)
where SummAB> 1000 

PS Не проверял , поэтому не знаю работает ли , но думаю направление указал
...
Рейтинг: 0 / 0
11.12.2006, 16:22
    #34190821
-=AlexiS=-
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Вай , копи пасте ....

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
SELECT
nomer,sklad,sum(Sum) as  SummAB,
FROM
( SELECT nomer,sklad,
     mtb60.sum
FROM mtb60
WHERE vid = "40"
union all
SELECT nomer,sklad,
     - mtb60.sum
FROM mtb60
WHERE vid <> "40"
)
where SummAB> 1000 
...
Рейтинг: 0 / 0
11.12.2006, 16:23
    #34190827
-=AlexiS=-
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
тху , опят поспешил

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
SELECT
nomer,sklad,sum(Sum) as  SummAB,
FROM
( SELECT nomer,sklad,
     mtb60.sum
FROM mtb60
WHERE vid = "40"
union all
SELECT nomer,sklad,
     mtb60.sum
FROM mtb60
WHERE vid <> "40"
)
group by nomer,sklad
where SummAB> 1000 
...
Рейтинг: 0 / 0
11.12.2006, 16:25
    #34190831
-=AlexiS=-
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
не , ну что ты сделаешь - блин туплю после обеда

2 последних варианта соедени - короче в 1 гроуп бай добавь
...
Рейтинг: 0 / 0
12.12.2006, 21:32
    #34194783
Jevgeniy
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Добрый вечер.
Есть база. Опишу подробнее. В таблице реализована древовидное подчинение клиентов, т.е. есть id клиента, который имеет id_parent, а этот в свою очередь может быть равен одному из id клиентов. Поле level создано для индификации уровня данного клиента в иерархической структуре.

Талица __client: id (уникальный ключ), name (имя клиента), id_parent (ключ родителя, может быть равен id другой записи), level (уровень в иерархической структуре), id_status

Таблица __buy: id_client, __idzakaz

Таблица __zakaz: id (номер заказа), summ (сумаа заказа), overball (каждый товар имеет свой балл, это сумма всех баллов товаров входящих в заказ), data (дата заказа)

Таблица __status: id, name - статусы клиентов, зависят и изменяются от количества набраных баллов за 1 месяц.

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

Подскажите пожалуйста как вывести хотябы дерево подчиненных для определенного клиента.

Заранее спасибо.
...
Рейтинг: 0 / 0
13.12.2006, 11:03
    #34195673
-=AlexiS=-
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Сходите на форум MS SQL - там в факах и поиском по слову TREE - есть масса решений.
...
Рейтинг: 0 / 0
13.12.2006, 11:59
    #34195981
Aleksey-K
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
JevgeniyДобрый вечер.
Есть база. Опишу подробнее. В таблице реализована древовидное подчинение клиентов, т.е. есть id клиента, который имеет id_parent, а этот в свою очередь может быть равен одному из id клиентов. Поле level создано для индификации уровня данного клиента в иерархической структуре.

Талица __client: id (уникальный ключ), name (имя клиента), id_parent (ключ родителя, может быть равен id другой записи), level (уровень в иерархической структуре), id_status

Таблица __buy: id_client, __idzakaz

Таблица __zakaz: id (номер заказа), summ (сумаа заказа), overball (каждый товар имеет свой балл, это сумма всех баллов товаров входящих в заказ), data (дата заказа)

Таблица __status: id, name - статусы клиентов, зависят и изменяются от количества набраных баллов за 1 месяц.

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

Подскажите пожалуйста как вывести хотябы дерево подчиненных для определенного клиента.

Заранее спасибо.
Проблема неоднократно обсуждалась. Я такие вещи делаю через серверную функцию, возвращающую таблицу:
Пусть есть таблица клиентов CLIENT вида:
CLENT_ID INT
Parent_ID INT
NAME CHAR(40)
Level TINYINT
Возможно есть и другие поля, но для данного примера они не важны.

Определяем на сервере такую функцию:
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
CREATE   FUNCTION dbo._CLENT_Tree (@CLIENT_ID INT)
RETURNS @ListC TABLE (CLIENT_ID INT, NAME CHAR( 40 ), Parent_ID  INT, Level  TINYINT)
AS  
BEGIN 
	DECLARE @LEVEL  TINYINT
	IF ISNULL(@CLIENT_ID,  0 )  =  0 
	BEGIN
		SET @LEVEL =  0 
		INSERT INTO @ListC (CLIENT_ID, NAME, Parent_ID, Level)
		SELECT CLIENT_ID, Name, ISNULL(Parent_ID,  0 ),  Level
		FROM CLIENT WHERE Level = @LEVEL
	END
	ELSE
	BEGIN
		INSERT INTO @ListC (CLIENT_ID, NAME, Parent_ID, Level)
		SELECT CLIENT_ID, Name, ISNULL(Parent_ID,  0 ),  Level
		FROM CLIENT WHERE CLIENT_ID = @CLIENT_ID
		SELECT @LEVEL = Level FROM @ListC
	END
	WHILE @@ROWCOUNT >  0 
	BEGIN
		SET @LEVEL = @LEVEL +  1 
		INSERT INTO @ListC (CLIENT_ID, NAME, Parent_ID, Level)
		SELECT p.CLIENT_ID, p.Name, ISNULL(p.Parent_ID,  0 ),  p.Level
		FROM CLIENT p INNER JOIN @ListC t ON p.Parent_ID = t.CLIENT_ID 
			AND t.Level = @LEVEL -  1 
	END
	RETURN
END
Эта функция по переданному CLIENT_ID возвращает всех его "потомков"
А далее, во всех запросах используете эту функцию в виде ...FROM dbo._CLENT_Tree(@CLIENT_ID)
Например, надо в каком-то подзапросе выбрать только данного клиента (@MY_CLIENT_ID) и всех его потомков. Тогда можно, напрмиер, так:
Код: plaintext
1.
SELECT ... FROM...
WHERE CLIENT_ID IN (SELECT CLIENT_ID FROM dbo._CLENT_Tree((@MY_CLIENT_ID ))
С уважением, Алексей.
...
Рейтинг: 0 / 0
13.12.2006, 18:28
    #34197760
Jevgeniy
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Огромное спасибо, Aleksey, подскажите пожалуйста как эту серверную функцию впихнуть в fox pro?
...
Рейтинг: 0 / 0
13.12.2006, 20:11
    #34198035
Aleksey-K
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
JevgeniyОгромное спасибо, Aleksey, подскажите пожалуйста как эту серверную функцию впихнуть в fox pro?
В каком смысле "впихнуть в fox pro" !? Это функция СЕРВЕРА!
Вы должны ее создать на MS SQL Server через EM (Enterprise Manager) или QA (Query Analyser) и использовать и при вызове или из клиента (SQLEXEC) или с сервера (Хранимые процедуры, которые тоже можно вызывать из клиента через SQLEXEC).
С уважением, Алексей.
...
Рейтинг: 0 / 0
13.12.2006, 22:49
    #34198240
Jevgeniy
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Вот что я делаю:
Работа делается на фокс про 6.0 поэтому сторонних программ я не использую.

1. Добавляю предварительно отредактированую процедуру в Stored Procedure. При закрытии система орет благим матом о синтаксических ошбках, не дает закрыть окно.

2. Создаю New Query, пихаю фукцию туда, запускаю на выполнение - не работает. Никакие исправления не помогают.

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

_http://www.sql.ru/forum/actualthread.aspx?tid=363425&pg=-1&hl=%e4%e5%f0%e5%e2%ee
Тут описание как можно сделать что-то приближенное при помощи select, но ограниченая глубина - явный минус. Причем глубина и ширина дерева переменна. Так что этот метод явно не подходит.

Пошу помощи
...
Рейтинг: 0 / 0
13.12.2006, 23:20
    #34198274
Aleksey-K
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
О.. тогда извините, я прочитал только предыдущий пост -=AlexiS=- , который отправлял вас на форум по SQL Server и подумал, что вы разрабатываете приложение клиент-сервер. Тогда все отменяется. Я вам привел код функции на Transact-SQL (T-SQL) - это язык MS Server.
Для VFP он не годится.
С уважением, Алексей
...
Рейтинг: 0 / 0
14.12.2006, 11:40
    #34199203
-=AlexiS=-
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Отправлял на MS SQL форум именно за алгоритмами , за идеями как можно решить задачу
Но некак не за готовым кодом.
Там есть масса красивых решений - через рекурсию , через циклы , через функции ...

НО даже готовый код - переделать под фокс - не проблема.
В том числе и код приведенный выше ...
...
Рейтинг: 0 / 0
14.12.2006, 22:06
    #34201415
Jevgeniy
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Помогите с запросом
Всем спасибо за участие и помощи в решении проблемы.
...
Рейтинг: 0 / 0
Форумы / FoxPro, Visual FoxPro [игнор отключен] [закрыт для гостей] / Помогите с запросом / 25 сообщений из 25, страница 1 из 1
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]