Main Page   Class Hierarchy   Compound List   File List   Compound Members   Related Pages  

storage.h

00001 //
00002 // storage.h
00003 //
00004 // Copyright (C) 1996 Limit Point Systems, Inc.
00005 //
00006 // Author: Curtis Janssen <cljanss@limitpt.com>
00007 // Maintainer: LPS
00008 //
00009 // This file is part of the SC Toolkit.
00010 //
00011 // The SC Toolkit is free software; you can redistribute it and/or modify
00012 // it under the terms of the GNU Library General Public License as published by
00013 // the Free Software Foundation; either version 2, or (at your option)
00014 // any later version.
00015 //
00016 // The SC Toolkit is distributed in the hope that it will be useful,
00017 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00018 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00019 // GNU Library General Public License for more details.
00020 //
00021 // You should have received a copy of the GNU Library General Public License
00022 // along with the SC Toolkit; see the file COPYING.LIB.  If not, write to
00023 // the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
00024 //
00025 // The U.S. Government is granted a limited license as per AL 91-7.
00026 //
00027 
00028 #ifndef _chemistry_qc_intv3_storage_h
00029 #define _chemistry_qc_intv3_storage_h
00030 
00031 #ifdef __GNUC__
00032 #pragma interface
00033 #endif
00034 
00035 #ifdef __cplusplus
00036 
00037 #include <stddef.h>
00038 #include <util/class/class.h>
00039 #include <util/keyval/keyval.h>
00040 #include <util/container/eavlmmap.h>
00041 
00042 // the max shell number is 2^15 (sizeof(int) must be >= 4)
00043 #define SH_BITS 15 // the number of bits holding a shell index
00044 #define PE_BITS 1  // the number of bits holding a permutation
00045 
00046 #define SH_MASK ((1<<SH_BITS)-1)
00047 #define PE_MASK ((1<<PE_BITS)-1)
00048 
00049 #define SH0_SHIFT 0
00050 #define SH1_SHIFT (SH_BITS + SH0_SHIFT)
00051 #define P12_SHIFT (SH_BITS + SH1_SHIFT)
00052 #define P34_SHIFT (PE_BITS + P12_SHIFT)
00053 #define SH2_SHIFT 0
00054 #define SH3_SHIFT (SH_BITS + SH2_SHIFT)
00055 #define P13P24_SHIFT (SH_BITS + SH3_SHIFT)
00056 class IntegralKey {
00057   public:
00058     unsigned int sh0_sh1_p12_p34;
00059     unsigned int sh2_sh3_p13p24;
00060   public:
00061     IntegralKey(int,int,int,int,int,int,int);
00062     IntegralKey(const IntegralKey&);
00063     int sh0() const { return (sh0_sh1_p12_p34>>SH0_SHIFT) & SH_MASK; }
00064     int sh1() const { return (sh0_sh1_p12_p34>>SH1_SHIFT) & SH_MASK; }
00065     int p12() const { return (sh0_sh1_p12_p34>>P12_SHIFT) & PE_MASK; }
00066     int p34() const { return (sh0_sh1_p12_p34>>P34_SHIFT) & PE_MASK; }
00067     int sh2() const { return (sh2_sh3_p13p24>>SH2_SHIFT) & SH_MASK; }
00068     int sh3() const { return (sh2_sh3_p13p24>>SH3_SHIFT) & SH_MASK; }
00069     int p13p24() const { return (sh2_sh3_p13p24>>P13P24_SHIFT) & PE_MASK; }
00070 };
00071 
00072 inline
00073 IntegralKey::IntegralKey(int sh1_, int sh2_, int sh3_, int sh4_,
00074                          int p12_, int p34_, int p13p24_)
00075 {
00076   sh0_sh1_p12_p34 = (sh1_<<SH0_SHIFT)
00077                     |(sh2_<<SH1_SHIFT)
00078                     |(p12_<<P12_SHIFT)
00079                     |(p34_<<P34_SHIFT);
00080   sh2_sh3_p13p24 = (sh3_<<SH2_SHIFT)
00081                    |(sh4_<<SH3_SHIFT)
00082                    |(p13p24_<<P13P24_SHIFT);
00083 }
00084 
00085 inline
00086 IntegralKey::IntegralKey(const IntegralKey& ik)
00087 {
00088   sh0_sh1_p12_p34 = ik.sh0_sh1_p12_p34;
00089   sh2_sh3_p13p24 = ik.sh2_sh3_p13p24;
00090 }
00091 
00092 inline int
00093 compare(const IntegralKey&k1, const IntegralKey&k2)
00094 {
00095   if (k1.sh0_sh1_p12_p34 < k2.sh0_sh1_p12_p34) return -1;
00096   else if (k1.sh0_sh1_p12_p34 > k2.sh0_sh1_p12_p34) return 1;
00097 
00098   if (k1.sh2_sh3_p13p24 < k2.sh2_sh3_p13p24) return -1;
00099   else if (k1.sh2_sh3_p13p24 > k2.sh2_sh3_p13p24) return 1;
00100   else return 0;
00101 }
00102 
00103 class IntegralLink {
00104   public:
00105     EAVLMMapNode<IntegralKey, IntegralLink> intlist;
00106     EAVLMMapNode<int, IntegralLink> costlist;
00107     int size;
00108   public:
00109     IntegralLink(IntegralKey& key, int cost, int size);
00110     static int size_to_actualsize(int size);
00111     ~IntegralLink();
00112     int actualsize() const;
00113     int hash() const;
00114     static int shells_to_hash(int,int,int,int);
00115     int cost() const { return costlist.key; }
00116     void print();
00117 
00118     // the integrals are squirreled away after this
00119     double* buffer() { return (double*)&this[1]; }
00120     void* operator new(size_t, int);
00121     void operator delete(void*, int);
00122     void operator delete(void*);
00123 };
00124 
00125 inline int
00126 IntegralLink::shells_to_hash(int sh1,int sh2,int sh3,int sh4)
00127 {
00128   return sh1 ^ (sh4<<4) ^ (sh2<<8) ^ (sh3<<12);
00129 }
00130 
00131 inline int
00132 IntegralLink::hash() const
00133 {
00134   return shells_to_hash(intlist.key.sh0(),
00135                         intlist.key.sh1(),
00136                         intlist.key.sh2(),
00137                         intlist.key.sh3());
00138 }
00139 
00140 inline int
00141 IntegralLink::size_to_actualsize(int size)
00142 {
00143   return size*sizeof(double) + sizeof(IntegralLink) + sizeof(void*)*2;
00144 }
00145 
00146 inline int
00147 IntegralLink::actualsize() const
00148 {
00149   return size_to_actualsize(size);
00150 }
00151 
00152 class IntegralStorer: public DescribedClass {
00153   private:
00154     int table_size_;
00155     EAVLMMap<int,IntegralLink> costlist;
00156     EAVLMMap<IntegralKey,IntegralLink>* table_;
00157     int maxsize_;
00158     int currentsize_;
00159     int n_integrals_;
00160     int n_shellquart_;
00161   public:
00162     IntegralStorer();
00163     IntegralStorer(const Ref<KeyVal>&);
00164     ~IntegralStorer();
00165     void init(int nbytes);
00166     void done();
00167     IntegralLink *find(IntegralKey&);
00168     int should_store(int cost, int actualsize);
00169     void store(IntegralKey& key, const double *buf,
00170                int size, int cost, int actualsize);
00171     void print_stats();
00172     int table_size() const { return table_size_; }
00173 };
00174 
00175 
00176 #endif
00177 
00178 #endif
00179 
00180 // Local Variables:
00181 // mode: c++
00182 // c-file-style: "CLJ"
00183 // End:

Generated at Thu Oct 4 18:08:47 2001 for MPQC 2.0.0 using the documentation package Doxygen 1.2.5.