Single row subquery produced more than one row

5 отговора 0 прегледа
#1

Single row subquery produced more than one row

Не мога да разбера къде бъркам в следния SQL
UPDATE items
SET items.tempkol=items.tempkol-(SELECT Giselect.WKOL
FROM "Items.DB" Items, "giselect.DB" Giselect
WHERE (Giselect.Item = Giselect.Item)
AND (Giselect.Sel <> '') )
where exists
(SELECT Giselect.WKOL
FROM "Items.DB" Items, "giselect.DB" Giselect
WHERE (Giselect.Item = Giselect.Item)
AND (Giselect.Sel <> '') )

Отговор
в отговор на SCO #2

Re: Single row subquery produced more than one row

Нека първо да уточним какво точно искаш с тази заявка:

UPDATE items
SET items.tempkol=items.tempkol-(
SELECT Giselect.WKOL
FROM "Items.DB" Items,
"giselect.DB" Giselect
WHERE (Giselect.Item = Giselect.Item) /* Това винаги е True */
AND (Giselect.Sel <> '')
)
where exists(
SELECT Giselect.WKOL
FROM "Items.DB" Items, "giselect.DB" Giselect
WHERE (Giselect.Item = Giselect.Item) /* Това винаги е True */
AND (Giselect.Sel <> '')
)

1. Ако e изпълнено за един ред на Giselect условието:
exists(

SELECT Giselect.WKOL
FROM "Items.DB" Items, "giselect.DB" Giselect
WHERE (Giselect.Item = Giselect.Item) /* Това винаги е True */
AND (Giselect.Sel <> '')
)

т.е. ако има само един ред в Giselect, за който Sel <> '', то ъпдейта ще се изпълни за всички редове на items.
2. Ако не е изпълнено за нито един ред - няма ъпдейт
3. Ако е изпълнено за повече от един ред ще получиш грешката от заглавието в:
SET items.tempkol=items.tempkol-(

SELECT Giselect.WKOL ...

За да гарантираш връщането на само един ред можеш да ползваш някоя агрегатна функция като MAX, MIN или пък, ако базата ти позволява, нещо от рода на Select First 1...

Отговор
в отговор на NDeu #3

Re: Single row subquery produced more than one row

Целта е да намаля с Giselect.WKOL всички items.tempkol където Giselect.Sel <> ''
колкото до

WHERE (Giselect.Item = Giselect.Item) /* Това винаги е True */

грешка !!!

Това е вярно
WHERE (Giselect.Item = Items.Item)

Отговор
в отговор на SCO #4

Re: Single row subquery produced more than one row

Докато (или с корекцията )
(SELECT Giselect.WKOL
FROM "Items.DB" Items, "giselect.DB" Giselect
WHERE (Giselect.Item = Giselect.Item)
AND (Giselect.Sel <> '') )

връща повече от един ред, то ти ще получаваш тази грешка.
Или ползвай предложението на NDeu (мин или макс ...) или Top 1 или ROWNUM =1 ама това зависи от това каква ти е базата (MSSQL, Oracle....). Ама най- добре направи да връща точно един ред.

Отговор
в отговор на SCO #5

Re: Single row subquery produced more than one row

Доколкото виждам искаш да се предпазиш от получаване на null стойност в -(SELECT ...) заявката. Ако е това, прегледай функциите IsNull за SQL Server или Decode за Oracle.

чети и дишай по-леко
Отговор
в отговор на Pechenia #6

Re: Single row subquery produced more than one row

В Oracle за null стойностите е най-добре да се използва готовата nvl фунсция.
Т.е nvl(tablename.fieldname,0) ако полето ти е тип integer, или
nvl(tablename.fieldname, '-') примерно, ако полето ти е тип varchar.

Отговор