Link to home
Start Free TrialLog in
Avatar of Brook_Lane
Brook_LaneFlag for United States of America

asked on

Looking for assistance with a simple Access Query to select records where AT LEAST one column equals "True".

User generated imageI'm trying to create what I expect would be a very simple query in Microsoft Access. I've added a screenshot that shows the query for reference. I have one criterion specified the references a date range on a form, which causes the query to select all matches records, which works fine. There are multiple other columns which are true\false that I would like to design the query to select if any one of those has a "true" value. I thought this would be very simple... basically if ANY of the records have a true value for ANY of the columns, then then that record would appear in the results, however all records where there wasn't AT LEAST one true value across all of the columns would be excluded.
ASKER CERTIFIED SOLUTION
Avatar of PatHartman
PatHartman
Flag of United States of America image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
I would suggest simple logic:

Where 
    ([YourDateField] Between [Forms]![FormName]![DateFrom] And [Forms]![FormName]![DateTo]) 
    And 
    ([TrueFalse1] Or [TrueFalse2] Or [TrueFalse3] Or … Or [TrueFalseN])

Open in new window

Where's your screenshot.... or am I blind?
I specifically chose the sum method because of the way that the QBE will mangle the method Gus suggested.  It will work fine but Access will rewrite the expression From:
(a) AND (b or c or d or e)

TO
(a and b) or (a and c) or (a and d) or (a and e)

If there are only a small number of "or" options, this may not be bothersome if you find it annoying, you can prevent this rewrite by NEVER, EVER saving while in QBE view .  Sometimes even switching from SQL to QBE view will cause the rewrite.  I usually keep a copy of queries with this problem in a module even though I prefer to always use querydefs to hold queries.
one concern using the SUM() method is that if the columns are not Yes/No columns, but some other data type, then they might also contain NULL values, and when you sum anything + NULL, you get NULL, so if that is the case, you might want to consider

(nz(fld1) + nz(fld2) + nz(fld3) + nz(fld4) + nz(fld5)) <> 0

but I prefer Gustav's method

WHERE ... AND (Field1 OR Field2 or Field3 or Field4)
Dale,
My suggestion doesn't use Sum(), that would require a properly normalized schema.  I also specifically mentioned that ALL columns needed to have a non-null value.   I did use the word Sum to describe it but you can't actually use the function since unlike Excel, the Access function sums values in a column rather than columns in a row.

If you are going to use the Nz() function, it is always best to be explicit since the rules are different in VBA than they are in a query.  In a query, omitting the ValueIfNull will result in a Zero Length String which is of course a string and therefore not a numeric value.

Nz(fld1, 0) + Nz(fld2, 0) + Nz(fld3, 0), ...

https://support.office.com/en-ie/article/nz-function-8ef85549-cc9c-438b-860a-7fd9f4c69b6c
Pat, good catch on all of the above, and Sum( ) would obviously not work across multiple columns anyway.

I actually have a function fnSum() with sums across a parameter array of columns, so you can include as many columns as you want, and it is configured to ignore NULL values by default.  But in this instance, I think I would still prefer to simply use:

WHERE ...
AND (Field1 or Field2 or Field3 or ...)
Access will rewrite the expression From:
(a) AND (b or c or d or e)
TO
(a and b) or (a and c) or (a and d) or (a and e)
I can't replicate that using Access 365:

User generated imageand:

SELECT tblA.Id
FROM tblA
WHERE (((([A]) And ([B] Or [C] Or [D] Or [E]))=True));

Open in new window

If Nulls are present, you can still use Nz and straight logic:

Where 
    ([YourDateField] Between [Forms]![FormName]![DateFrom] And [Forms]![FormName]![DateTo]) 
    And 
    (Nz([TrueFalse1], False) Or Nz([TrueFalse2], False) Or Nz([TrueFalse3], False) Or … Or Nz([TrueFalseN], False))

Open in new window

OMG!!!  I think MS finally fixed this most annoying "feature.

Access used to change:
THIS:
SELECT tblClass.ClassID, tblClass.ClassTitle, tblClass.ChangedBy
FROM tblClass
WHERE tblClass.ChangedBy = "Pat"   AND (tblClass.ClassID =1 OR tblClass.ClassID =2 OR tblClass.ClassID =3 OR tblClass.ClassID =4 OR tblClass.ClassID =5)
User generated imageTO THIS:
SELECT tblClass.ClassID, tblClass.ClassTitle, tblClass.ChangedBy
FROM tblClass
WHERE (((tblClass.ClassID)=1) AND ((tblClass.ChangedBy)="Pat")) OR (((tblClass.ClassID)=2) AND ((tblClass.ChangedBy)="Pat")) OR (((tblClass.ClassID)=3) AND ((tblClass.ChangedBy)="Pat")) OR (((tblClass.ClassID)=4) AND ((tblClass.ChangedBy)="Pat")) OR (((tblClass.ClassID)=5) AND ((tblClass.ChangedBy)="Pat"));

If you switched to QBE view and saved, Access rewrote the SQL so it could present it this way:
User generated image
It still rewrites it to add an excessive number of parentheses

SELECT tblClass.ClassID, tblClass.ClassTitle, tblClass.ChangedBy
FROM tblClass
WHERE (((tblClass.ClassID)=1 Or (tblClass.ClassID)=2 Or (tblClass.ClassID)=3 Or (tblClass.ClassID)=4 Or (tblClass.ClassID)=5) AND ((tblClass.ChangedBy)="Pat"));
Have tried simply using a sub-query. A simple select query that selects all rows with the Boolean values true, and then use that as the source of your aggregating query, where, for example, you can now count the rows (or indeed use any other aggregate function you might want)...

TrueQ SQL. The fields y1, y2, y3 are Booleans...
SELECT Table1.y1, Table1.y2, Table1.y3, Table1.names
FROM Table1
WHERE (((Table1.y1)=True)) OR (((Table1.y2)=True)) OR (((Table1.y3)=True));

Open in new window

Aggregate Query SQL
SELECT Count(TrueQ.y1) AS CountOfy1, Count(TrueQ.y2) AS CountOfy2, Count(TrueQ.y3) AS CountOfy3, TrueQ.names
FROM TrueQ
GROUP BY TrueQ.names;

Open in new window


BTW. Why are people complaining about the way Access rewrites queries? What is wrong with parentheses that make things explicit. It just might be the case that Access understands how to compose a query to maximize JET's performance. Can anyone demonstrate away of writing a query by hand that turns out to be  significantly faster than the automatically written ones (pass-through queries excepted). Just wondering.