MADNESS  0.10.1
displacements.h
Go to the documentation of this file.
1 /*
2  This file is part of MADNESS.
3 
4  Copyright (C) 2007,2010 Oak Ridge National Laboratory
5 
6  This program is free software; you can redistribute it and/or modify
7  it under the terms of the GNU General Public License as published by
8  the Free Software Foundation; either version 2 of the License, or
9  (at your option) any later version.
10 
11  This program is distributed in the hope that it will be useful,
12  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  GNU General Public License for more details.
15 
16  You should have received a copy of the GNU General Public License
17  along with this program; if not, write to the Free Software
18  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 
20  For more information please contact:
21 
22  Robert J. Harrison
23  Oak Ridge National Laboratory
24  One Bethel Valley Road
25  P.O. Box 2008, MS-6367
26 
27  email: harrisonrj@ornl.gov
28  tel: 865-241-3937
29  fax: 865-572-0680
30 
31  $Id$
32 */
33 #ifndef MADNESS_MRA_DISPLACEMENTS_H__INCLUDED
34 #define MADNESS_MRA_DISPLACEMENTS_H__INCLUDED
35 
36 namespace madness {
37  /// Holds displacements for applying operators to avoid replicating for all operators
38  template <std::size_t NDIM>
39  class Displacements {
40 
41  static std::vector< Key<NDIM> > disp;
42  static std::vector< Key<NDIM> > disp_periodicsum[64];
43 
44  public:
45  static int bmax_default() {
46  int bmax;
47  if (NDIM == 1) bmax = 7;
48  else if (NDIM == 2) bmax = 5;
49  else if (NDIM == 3) bmax = 3;
50  else if (NDIM == 4) bmax = 3;
51  else if (NDIM == 5) bmax = 3;
52  else if (NDIM == 6) bmax = 3;
53  else bmax = 2;
54  return bmax;
55  }
56 
57  private:
58  static bool cmp_keys(const Key<NDIM>& a, const Key<NDIM>& b) {
59  return a.distsq() < b.distsq();
60  }
61 
62  static bool cmp_keys_periodicsum(const Key<NDIM>& a, const Key<NDIM>& b) {
63  Translation twonm1 = (Translation(1)<<a.level())>>1;
64 
65  uint64_t suma=0, sumb=0;
66  for (std::size_t d=0; d<NDIM; ++d) {
67  Translation la = a.translation()[d];
68  if (la > twonm1) la -= twonm1*2;
69  if (la <-twonm1) la += twonm1*2;
70  suma += la*la;
71 
72  Translation lb = b.translation()[d];
73  if (lb > twonm1) lb -= twonm1*2;
74  if (lb <-twonm1) lb += twonm1*2;
75  sumb += lb*lb;
76  }
77  return suma < sumb;
78  }
79 
80  static void make_disp(int bmax) {
81  // Note newer loop structure in make_disp_periodic_sum
83 
84  int num = 1;
85  for (std::size_t i=0; i<NDIM; ++i) num *= (2*bmax + 1);
86  disp.resize(num,Key<NDIM>(0));
87 
88  num = 0;
89  if (NDIM == 1) {
90  for (d[0]=-bmax; d[0]<=bmax; ++d[0])
91  disp[num++] = Key<NDIM>(0,d);
92  }
93  else if (NDIM == 2) {
94  for (d[0]=-bmax; d[0]<=bmax; ++d[0])
95  for (d[1]=-bmax; d[1]<=bmax; ++d[1])
96  disp[num++] = Key<NDIM>(0,d);
97  }
98  else if (NDIM == 3) {
99  for (d[0]=-bmax; d[0]<=bmax; ++d[0])
100  for (d[1]=-bmax; d[1]<=bmax; ++d[1])
101  for (d[2]=-bmax; d[2]<=bmax; ++d[2])
102  disp[num++] = Key<NDIM>(0,d);
103  }
104  else if (NDIM == 4) {
105  for (d[0]=-bmax; d[0]<=bmax; ++d[0])
106  for (d[1]=-bmax; d[1]<=bmax; ++d[1])
107  for (d[2]=-bmax; d[2]<=bmax; ++d[2])
108  for (d[3]=-bmax; d[3]<=bmax; ++d[3])
109  disp[num++] = Key<NDIM>(0,d);
110  }
111  else if (NDIM == 5) {
112  for (d[0]=-bmax; d[0]<=bmax; ++d[0])
113  for (d[1]=-bmax; d[1]<=bmax; ++d[1])
114  for (d[2]=-bmax; d[2]<=bmax; ++d[2])
115  for (d[3]=-bmax; d[3]<=bmax; ++d[3])
116  for (d[4]=-bmax; d[4]<=bmax; ++d[4])
117 
118  disp[num++] = Key<NDIM>(0,d);
119  }
120  else if (NDIM == 6) {
121  for (d[0]=-bmax; d[0]<=bmax; ++d[0])
122  for (d[1]=-bmax; d[1]<=bmax; ++d[1])
123  for (d[2]=-bmax; d[2]<=bmax; ++d[2])
124  for (d[3]=-bmax; d[3]<=bmax; ++d[3])
125  for (d[4]=-bmax; d[4]<=bmax; ++d[4])
126  for (d[5]=-bmax; d[5]<=bmax; ++d[5])
127  disp[num++] = Key<NDIM>(0,d);
128  }
129  else {
130  MADNESS_EXCEPTION("_make_disp: hard dimension loop",NDIM);
131  }
132 
133  std::sort(disp.begin(), disp.end(), cmp_keys);
134  }
135 
136  static void make_disp_periodicsum(int bmax, Level n) {
137  Translation twon = Translation(1)<<n;
138 
139  if (bmax > (twon-1)) bmax=twon-1;
140 
141  // Make permissible 1D translations
142  Translation b[4*bmax+1];
143  int i=0;
144  for (Translation lx=-bmax; lx<=bmax; ++lx) {
145  b[i++] = lx;
146  if ((lx < 0) && (lx+twon > bmax)) b[i++] = lx + twon;
147  if ((lx > 0) && (lx-twon <-bmax)) b[i++] = lx - twon;
148  }
149  MADNESS_ASSERT(i <= 4*bmax+1);
150  int numb = i;
151 
152  MADNESS_PRAGMA_CLANG(diagnostic push)
153  MADNESS_PRAGMA_CLANG(diagnostic ignored "-Wundefined-var-template")
154 
155  disp_periodicsum[n] = std::vector< Key<NDIM> >();
156  Vector<long,NDIM> lim(numb);
157  for (IndexIterator index(lim); index; ++index) {
159  for (std::size_t i=0; i<NDIM; ++i) {
160  d[i] = b[index[i]];
161  }
162  disp_periodicsum[n].push_back(Key<NDIM>(n,d));
163  }
164 
165  std::sort(disp_periodicsum[n].begin(), disp_periodicsum[n].end(), cmp_keys_periodicsum);
166 // print("KEYS AT LEVEL", n);
167 // print(disp_periodicsum[n]);
168 
169  MADNESS_PRAGMA_CLANG(diagnostic pop)
170 
171  }
172 
173 
174  public:
176  MADNESS_PRAGMA_CLANG(diagnostic push)
177  MADNESS_PRAGMA_CLANG(diagnostic ignored "-Wundefined-var-template")
178 
179  if (disp.size() == 0) {
181 
182  if (NDIM <= 3) {
183  Level nmax = 8*sizeof(Translation) - 2;
184  for (Level n=0; n<nmax; ++n) make_disp_periodicsum(bmax_default(), n);
185  }
186  }
187 
188  MADNESS_PRAGMA_CLANG(diagnostic pop)
189  }
190 
191  const std::vector< Key<NDIM> >& get_disp(Level n, bool isperiodicsum) {
192  if (isperiodicsum) {
193  MADNESS_ASSERT(NDIM <= 3);
194  return disp_periodicsum[n];
195  }
196  else {
197  return disp;
198  }
199  }
200 
201  };
202 }
203 #endif // MADNESS_MRA_DISPLACEMENTS_H__INCLUDED
Holds displacements for applying operators to avoid replicating for all operators.
Definition: displacements.h:39
static std::vector< Key< NDIM > > disp
Definition: displacements.h:41
static bool cmp_keys_periodicsum(const Key< NDIM > &a, const Key< NDIM > &b)
Definition: displacements.h:62
static bool cmp_keys(const Key< NDIM > &a, const Key< NDIM > &b)
Definition: displacements.h:58
static void make_disp_periodicsum(int bmax, Level n)
Definition: displacements.h:136
static void make_disp(int bmax)
Definition: displacements.h:80
const std::vector< Key< NDIM > > & get_disp(Level n, bool isperiodicsum)
Definition: displacements.h:191
static std::vector< Key< NDIM > > disp_periodicsum[64]
Definition: displacements.h:42
static int bmax_default()
Definition: displacements.h:45
Displacements()
Definition: displacements.h:175
Definition: indexit.h:55
Key is the index for a node of the 2^NDIM-tree.
Definition: key.h:66
#define MADNESS_PRAGMA_CLANG(x)
Definition: madness_config.h:200
#define MADNESS_EXCEPTION(msg, value)
Macro for throwing a MADNESS exception.
Definition: madness_exception.h:119
#define MADNESS_ASSERT(condition)
Assert a condition that should be free of side-effects since in release builds this might be a no-op.
Definition: madness_exception.h:134
File holds all helper structures necessary for the CC_Operator and CC2 class.
Definition: DFParameters.h:10
int64_t Translation
Definition: key.h:54
int Level
Definition: key.h:55
static double pop(std::vector< double > &v)
Definition: SCF.cc:113
static const double b
Definition: nonlinschro.cc:119
static const double a
Definition: nonlinschro.cc:118
void d()
Definition: test_sig.cc:79
static const std::size_t NDIM
Definition: testpdiff.cc:42