HAVING gotcha

Without a GROPY BY clause HAVING operates similar to a WHERE clause, except that the filter operates on the result set:

Create Cursor curSrc (Fld1 I, Fld2 I)
Insert into curSrc values (1,1)
Insert into curSrc values (2,2)

Select Fld1, fld1+1 as Fld3 ;
From curSrc ;
having Fld3 = 2

Select Fld1, fld1+1 as Fld2 ;
From curSrc ;
having fld2 = 2

FLD2 is only used an alias in the field list, yet the HAVING clause operates on curSrc.Fld2 instead of FLD2 from the result set. This can cause changes in program behaviour when you add a field to a table with the same name as a calculated column.

Once you aggregate the result set with GROUP BY, rules change slightly. Referring to the field name in the result set yields an error message, if a field with the same name exists in any of the source tables. In the following query, FLD1+1=2 works in the HAVING clause, FLD2=2 wouldn't:


Select Fld1, fld1+1 as Fld2 ;
From curSrc ;
group by 1,2 ;
having fld1+1 = 2

The same query is valid if the field name does not exist in any of the source tables. The following query uses FLD3 instead of FLD2 as the field name:


Select Fld1, fld1+1 as Fld3 ;
From curSrc ;
group by 1,2 ;
having fld3 = 2

This is a situation you might encounter when doing refactoring and renaming fields. Changing the local field name suddenly causes errors when you run the query.