Michael R Mattys
michael.mattys at adelphia.net
Wed Oct 29 22:55:46 CST 2003
John, This should bring back some memories. Message 4 in thread From: jwelz at hotmail.com (jwelz at hotmail.com) Subject: Re: bitwise operators Newsgroups: comp.databases.ms-access View this article only Date: 2000/02/08 It is possible to perform a bitwise query in Jet 3.5 without using a function. Rather than doing the operation in the 'Where' clause, do it in the Join. I keep a 'join table' in my front end. I generally limit this to single byte bit masks to keep the size of the join table down. The join table is laid out with 8 fields headed 'b1, b2, b4, b8, b16, b32, b64, b128'. In each field are all the values for which the And operation returns true, there are 128 values for each field, and the concept of row is irrelevant. I sort and index the data. Field b1 has the values '1, 3, 5, 7, 9...', Field b2 has the values '2, 3, 6, 7, 10, 11...', Field b4 has the values '4, 5, 6, 7, 12, 13, 14, 15, 20...' ....and field b128 has the values '128, 129, 130, 131....' The operation is analagous to a 'Where' clause comparing a field value with an IN(1, 2, 5...) list, without the syntactic nonsense of generating a complex list on the fly, though that is a 'Where' approach that can be made to work. To query on a bit, the sql reads: "Select [fields] From [tblData] Inner Join [JoinTable] on [tblData].[AndedField] = [JoinTable].b" & 2 ^ (bytBitNumber - 1) Where you pass the bit position (1 through 8) to the variable bytBitNumber (or just the number value of the bit(s or'ed)). By joining a field on more than one column in the join table, and in conjunction with the not operator, you can query on several bit positions and values concurrently. I find this method significantly faster than calling a function for a calculated field since the query engine does the work very efficiently (rather than calling a function n thousand times for n thousand records queried). This approach works with any version of sql that supports an inner join. Used for bitwise queries on bytes, the join table stores a mere 1k of data (datatype byte for all 8 fields, 128 rows, same amount again for indexing I assume). If you need to And a bit higher than the 128 (8th bit), I find it more efficient to store two bytes to keep the join table small and fast. Alternatively, you could parse the field into hi/low bytes or more as required for larger data types. Although a violation of normalization rules, the ability to store 8 boolean values in a single field gives measurable performance gains and I use it in any table where there is more than a single two state field. Well commented and documented usage should cause no problems. A byte can also store three state (or more) fields should that be expedient though I'd consider the latter two cases only in an extremely static design that needed a bit of tweaking since design enhancement maintenance requires customized extraction of values to forms and reports. Design requirement changes could require extensive changes to code and subsequent developers not familiar with the methodology would[... didn't bother to get the rest.]Michael R. Mattys Try MattysMapLib for MapPoint at www.mattysconsulting.com ----- Original Message ----- From: "John Colby" <jcolby at colbyconsulting.com> To: "Access Developers discussion and problem solving" <accessd at databaseadvisors.com> Sent: Wednesday, October 29, 2003 8:43 PM Subject: RE: [AccessD] brain farts > >In Access, try using a CINT(Frm_GroupVisible) etc to force it to an Int > before doing the "OR" comparison. > > Tried that, no joy. > > John W. Colby > www.colbyconsulting.com > > -----Original Message----- > From: accessd-bounces at databaseadvisors.com > [mailto:accessd-bounces at databaseadvisors.com]On Behalf Of Stuart > McLachlan > Sent: Wednesday, October 29, 2003 8:24 PM > To: John Colby; accessd at databaseadvisors.com > Subject: RE: [AccessD] brain farts > > > On 29 Oct 2003 at 17:48, John Colby wrote: > > > I tried this and it's giving me errors. This is the actual built up SQL > > statement. > > > > UPDATE MsysForms SET [FRM_GroupOpen] = [FRM_GroupOpen] ~ 4, > > [FRM_GroupVisible] = [FRM_GroupVisible] ~ 4, [FRM_GroupEdit] = > > [FRM_GroupEdit] ~ 4, [FRM_GroupAddRec] = [FRM_GroupAddRec] ~ 4, > > [FRM_GroupDelRec] = [FRM_GroupDelRec] ~ 4 WHERE (((MsysForms.FRM_ID) In > > (28,34,33,35,32,29,31,30))); > > > > Is that as you understand it to be used? Likewise it didn't like the > > vertical bar. > > > > I posted a second one, a couple of seconds later which for some reason > didn't make it to the list. > > In that I said "Sorry, I thought I was still scanning the dba-SQL list". > > In Access, try using a CINT(Frm_GroupVisible) etc to force it to an Int > before doing the "OR" comparison. > > > > > -- > Stuart McLachlan > Lexacorp Ltd > Application Development, IT Consultancy > http://www.lexacorp.com.pg > > _______________________________________________ > AccessD mailing list > AccessD at databaseadvisors.com > http://databaseadvisors.com/mailman/listinfo/accessd > Website: http://www.databaseadvisors.com > > > > _______________________________________________ > AccessD mailing list > AccessD at databaseadvisors.com > http://databaseadvisors.com/mailman/listinfo/accessd > Website: http://www.databaseadvisors.com