kamemontecarlo.cpp
1 /***************************************************************************
2  Copyright (C) 2002-2015 Kentaro Kitagawa
3  kitagawa@phys.s.u-tokyo.ac.jp
4 
5  This program is free software; you can redistribute it and/or
6  modify it under the terms of the GNU Library General Public
7  License as published by the Free Software Foundation; either
8  version 2 of the License, or (at your option) any later version.
9 
10  You should have received a copy of the GNU Library General
11  Public License and a list of authors along with this program;
12  see the files COPYING and AUTHORS.
13 ***************************************************************************/
14 //---------------------------------------------------------------------------
15 #include "analyzer.h"
16 #include "xnodeconnector.h"
17 #include "montecarlo.h"
18 #include "kamemontecarlo.h"
19 #include "ui_montecarloform.h"
20 #include <QStatusBar>
21 #include "graph.h"
22 #include "graphwidget.h"
23 
24 REGISTER_TYPE(XDriverList, MonteCarloDriver, "Monte-Carlo simulation");
25 
26 struct FFTAxis {
27  const char *desc;
28  int h,k,l;
29  int h0,k0,l0;
30 };
31 static const FFTAxis c_fftaxes[] = {
32  {"h 0 0", 1, 0, 0, 0, 0, 0},
33  {"0 k 0", 0, 1, 0, 0, 0, 0},
34  {"0 0 l", 0, 0, 1, 0, 0, 0},
35  {"h h 0", 1, 1, 0, 0, 0, 0},
36  {"h h h", 1, 1, 1, 0, 0, 0},
37  {0, 0,0,0, 0,0,0}
38 };
39 #define GRAPH_3D_FFT_INTENS_ABS "FFT3D-abs."
40 #define GRAPH_3D_FFT_INTENS_X "FFT3D-x"
41 #define GRAPH_3D_FFT_INTENS_Y "FFT3D-y"
42 #define GRAPH_3D_FFT_INTENS_Z "FFT3D-z"
43 #define GRAPH_3D_FFT_INTENS_M "FFT3D-along-H"
44 #define GRAPH_REAL_M "SPINS-along-H"
45 #define GRAPH_REAL_H "H-along-Ising"
46 #define GRAPH_REAL_P "Flipping Probability"
47 #define GRAPH_REAL_H_B_SITE "H-at-B-site"
48 #define GRAPH_REAL_H_8a_SITE "H-at-8a-site"
49 #define GRAPH_REAL_H_48f_SITE "H-at-48f-site"
50 #define GRAPH_FLIPS "Flip History"
51 
52 XMonteCarloDriver::XMonteCarloDriver(const char *name, bool runtime,
53  Transaction &tr_meas, const shared_ptr<XMeasure> &meas) :
54  XDummyDriver<XPrimaryDriver>(name, runtime, ref(tr_meas), meas),
55  m_targetTemp(create<XDoubleNode>("TargetTemp", false)),
56  m_targetField(create<XDoubleNode>("TargetField", false)),
57  m_hdirx(create<XDoubleNode>("FieldDirX", false)),
58  m_hdiry(create<XDoubleNode>("FieldDirY", false)),
59  m_hdirz(create<XDoubleNode>("FieldDirZ", false)),
60  m_L(create<XUIntNode>("Length", false)),
61  m_cutoffReal(create<XDoubleNode>("CutoffReal", false)),
62  m_cutoffRec(create<XDoubleNode>("CutoffRec", false)),
63  m_alpha(create<XDoubleNode>("Alpha", false)),
64  m_minTests(create<XDoubleNode>("MinTests", false)),
65  m_minFlips(create<XDoubleNode>("MinFlips", false)),
66  m_step(create<XTouchableNode>("Step", true)),
67  m_graph3D(create<XComboNode>("Graph3D", false, true)),
68  m_entryT(create<XScalarEntry>("Temp", false,
69  dynamic_pointer_cast<XDriver>(shared_from_this()), "%.6g")),
70  m_entryH(create<XScalarEntry>("Field", false,
71  dynamic_pointer_cast<XDriver>(shared_from_this()), "%.6g")),
72  m_entryU(create<XScalarEntry>("U", false,
73  dynamic_pointer_cast<XDriver>(shared_from_this()), "%.6g")),
74  m_entryC(create<XScalarEntry>("C", false,
75  dynamic_pointer_cast<XDriver>(shared_from_this()), "%.4g")),
76  m_entryCoT(create<XScalarEntry>("CoverT", false,
77  dynamic_pointer_cast<XDriver>(shared_from_this()), "%.4g")),
78  m_entryS(create<XScalarEntry>("S", false,
79  dynamic_pointer_cast<XDriver>(shared_from_this()), "%.6g")),
80  m_entryM(create<XScalarEntry>("M", false,
81  dynamic_pointer_cast<XDriver>(shared_from_this()), "%.6g")),
82  m_entry2in2(create<XScalarEntry>("2in2", false,
83  dynamic_pointer_cast<XDriver>(shared_from_this()), "%.4g")),
84  m_entry1in3(create<XScalarEntry>("1in3", false,
85  dynamic_pointer_cast<XDriver>(shared_from_this()), "%.4g")),
86  m_form(new FrmMonteCarlo),
87  m_wave3D(create<XWaveNGraph>("Wave3D", false,
88  m_form->m_graph, m_form->m_edDump, m_form->m_tbDump, m_form->m_btnDump)),
89  m_statusPrinter(XStatusPrinter::create(m_form.get())) {
90 
91  meas->scalarEntries()->insert(tr_meas, m_entryT);
92  meas->scalarEntries()->insert(tr_meas, m_entryH);
93  meas->scalarEntries()->insert(tr_meas, m_entryU);
94  meas->scalarEntries()->insert(tr_meas, m_entryC);
95  meas->scalarEntries()->insert(tr_meas, m_entryCoT);
96  meas->scalarEntries()->insert(tr_meas, m_entryS);
97  meas->scalarEntries()->insert(tr_meas, m_entryM);
98  meas->scalarEntries()->insert(tr_meas, m_entry2in2);
99  meas->scalarEntries()->insert(tr_meas, m_entry1in3);
100 
101  iterate_commit([=](Transaction &tr){
102  tr[ *m_targetTemp] = 100.0;
103  tr[ *m_hdirx] = 1.0;
104  tr[ *m_hdiry] = 1.0;
105  tr[ *m_hdirz] = 1.0;
106  tr[ *m_L] = 8;
107  tr[ *m_cutoffReal] = 4.0;
108  tr[ *m_cutoffRec] = 2.0;
109  tr[ *m_alpha] = 0.5;
110  tr[ *m_minTests] = 1.0;
111  tr[ *m_minFlips] = 0.2;
112 
113  // for(const FFTAxis *axis = c_fftaxes; axis->desc; axis++) {
114  // m_fftAxisX].add(axis->desc);
115  // m_fftAxisY].add(axis->desc);
116  // }
117  // m_fftAxisX] = 0);
118  // m_fftAxisY] = 1);
119 
120  tr[ *m_graph3D].add(GRAPH_3D_FFT_INTENS_ABS);
121  tr[ *m_graph3D].add(GRAPH_3D_FFT_INTENS_X);
122  tr[ *m_graph3D].add(GRAPH_3D_FFT_INTENS_Y);
123  tr[ *m_graph3D].add(GRAPH_3D_FFT_INTENS_Z);
124  tr[ *m_graph3D].add(GRAPH_3D_FFT_INTENS_M);
125  tr[ *m_graph3D].add(GRAPH_REAL_M);
126  tr[ *m_graph3D].add(GRAPH_REAL_H);
127  tr[ *m_graph3D].add(GRAPH_REAL_P);
128  tr[ *m_graph3D].add(GRAPH_REAL_H_B_SITE);
129  tr[ *m_graph3D].add(GRAPH_REAL_H_8a_SITE);
130  tr[ *m_graph3D].add(GRAPH_REAL_H_48f_SITE);
131  tr[ *m_graph3D].add(GRAPH_FLIPS);
132  });
133 
134  m_conLength = xqcon_create<XQLineEditConnector>(m_L, m_form->m_edLength);
135  m_conCutoffReal = xqcon_create<XQLineEditConnector>(m_cutoffReal, m_form->m_edCutoffReal);
136  m_conCutoffRec = xqcon_create<XQLineEditConnector>(m_cutoffRec, m_form->m_edCutoffRec);
137  m_conAlpha = xqcon_create<XQLineEditConnector>(m_alpha, m_form->m_edAlpha);
138  m_conTargetTemp = xqcon_create<XQLineEditConnector>(m_targetTemp, m_form->m_edTargetTemp);
139  m_conTargetField = xqcon_create<XQLineEditConnector>(m_targetField, m_form->m_edTargetField);
140  m_conHDirX = xqcon_create<XQLineEditConnector>(m_hdirx, m_form->m_edHDirX);
141  m_conHDirY = xqcon_create<XQLineEditConnector>(m_hdiry, m_form->m_edHDirY);
142  m_conHDirZ = xqcon_create<XQLineEditConnector>(m_hdirz, m_form->m_edHDirZ);
143  m_conMinTests = xqcon_create<XQLineEditConnector>(m_minTests, m_form->m_edMinTests);
144  m_conMinFlips = xqcon_create<XQLineEditConnector>(m_minFlips, m_form->m_edMinFlips);
145  m_conStep = xqcon_create<XQButtonConnector>(m_step, m_form->m_btnStep);
146  m_conGraph3D = xqcon_create<XQComboBoxConnector>(m_graph3D, m_form->m_cmbGraph3D, Snapshot( *m_graph3D));
147 
148  m_L->setUIEnabled(true);
149  m_cutoffReal->setUIEnabled(true);
150  m_hdirx->setUIEnabled(true);
151  m_hdiry->setUIEnabled(true);
152  m_hdirz->setUIEnabled(true);
153  m_minTests->setUIEnabled(true);
154  m_minFlips->setUIEnabled(true);
155  m_step->setUIEnabled(true);
156  m_targetTemp->setUIEnabled(true);
157  m_targetField->setUIEnabled(true);
158 
159  m_wave3D->iterate_commit([=](Transaction &tr){
160  const char *s_trace_names[] = {
161  "h or x", "k or y", "l or z", "intens.", "hx", "hy", "hz", "site"
162  };
163  tr[ *m_wave3D].setColCount(8, s_trace_names);
164  tr[ *m_wave3D].insertPlot("Intens.", 0, 1, -1, 3, 2);
165  tr[ *tr[ *m_wave3D].plot(0)->drawLines()] = false;
166 
167  tr[ *m_wave3D->graph()->backGround()] = QColor(0,0,0).rgb();
168  tr[ *tr[ *m_wave3D].plot(0)->intensity()] = 2;
169  tr[ *tr[ *m_wave3D].plot(0)->colorPlot()] = true;
170  tr[ *tr[ *m_wave3D].plot(0)->colorPlotColorHigh()] = QColor(0xFF, 0xFF, 0x2F).rgb();
171  tr[ *tr[ *m_wave3D].plot(0)->colorPlotColorLow()] = QColor(0x00, 0x00, 0xFF).rgb();
172  tr[ *tr[ *m_wave3D].plot(0)->pointColor()] = QColor(0x00, 0xFF, 0x00).rgb();
173  tr[ *tr[ *m_wave3D].plot(0)->majorGridColor()] = QColor(0x4A, 0x4A, 0x4A).rgb();
174  tr[ *m_wave3D->graph()->titleColor()] = clWhite;
175  tr[ *tr[ *m_wave3D].axisx()->ticColor()] = clWhite;
176  tr[ *tr[ *m_wave3D].axisx()->labelColor()] = clWhite;
177  tr[ *tr[ *m_wave3D].axisx()->ticLabelColor()] = clWhite;
178  tr[ *tr[ *m_wave3D].axisy()->ticColor()] = clWhite;
179  tr[ *tr[ *m_wave3D].axisy()->labelColor()] = clWhite;
180  tr[ *tr[ *m_wave3D].axisy()->ticLabelColor()] = clWhite;
181  tr[ *tr[ *m_wave3D].axisz()->ticColor()] = clWhite;
182  tr[ *tr[ *m_wave3D].axisz()->labelColor()] = clWhite;
183  tr[ *tr[ *m_wave3D].axisz()->ticLabelColor()] = clWhite;
184  tr[ *m_wave3D].clearPoints();
185  });
186 }
188  Snapshot shot( *this);
189  for(int d = 0; d < 3; d++) {
190  if(shot[ *this].m_fftlen > 0) {
191  fftw_destroy_plan(shot[ *this].m_fftplan[d]);
192  fftw_free(shot[ *this].m_pFFTin[d]);
193  fftw_free(shot[ *this].m_pFFTout[d]);
194  }
195  }
196 }
197 void
199 //! impliment form->show() here
200  m_form->showNormal();
201  m_form->raise();
202 }
203 void
205  Snapshot shot( *this);
206  MonteCarlo::setupField(shot[ *m_L], 0.0, shot[ *m_cutoffReal], shot[ *m_cutoffRec], shot[ *m_alpha]);
207  m_L->setUIEnabled(false);
208  m_cutoffReal->setUIEnabled(false);
209  m_cutoffRec->setUIEnabled(false);
210  m_alpha->setUIEnabled(false);
211  m_hdirx->setUIEnabled(false);
212  m_hdiry->setUIEnabled(false);
213  m_hdirz->setUIEnabled(false);
214  iterate_commit([=](Transaction &tr){
215  const Snapshot &shot(tr);
216  tr[ *this].m_loop.reset(new MonteCarlo(2));
217  tr[ *this].m_store.reset(new MonteCarlo(1));
218  tr[ *this].m_sumDU = tr[ *this].m_loop->internalEnergy() * N_A;
219  tr[ *this].m_sumDUav = tr[ *this].m_sumDU;
220  tr[ *this].m_sumDS = 0.0;
221  tr[ *this].m_testsTotal = 0.0;
222  tr[ *this].m_flippedTotal = 0.0;
223  tr[ *this].m_lastTemp = 300.0;
224  tr[ *this].m_lastField = 0.0;
225  tr[ *this].m_dU = 0.0;
226  MonteCarlo::Vector3<double> field_dir(tr[ *m_hdirx], tr[ *m_hdiry], tr[ *m_hdirz]);
227  field_dir.normalize();
228  tr[ *this].m_lastMagnetization = tr[ *this].m_loop->magnetization().innerProduct(field_dir);
229 
230  m_lsnStepTouched = tr[ *m_step].onTouch().connectWeakly(
231  shared_from_this(), &XMonteCarloDriver::onStepTouched);
232  m_lsnTargetChanged = tr[ *m_targetTemp].onValueChanged().connectWeakly(
233  shared_from_this(), &XMonteCarloDriver::onTargetChanged);
234  tr[ *m_targetField].onValueChanged().connect(m_lsnTargetChanged);
235  m_lsnGraphChanged = tr[ *m_graph3D].onValueChanged().connectWeakly(
236  shared_from_this(), &XMonteCarloDriver::onGraphChanged);
237 
238  int fftlen = MonteCarlo::length() * 4;
239  for(int d = 0; d < 3; d++) {
240  if(shot[ *this].m_fftlen > 0) {
241  fftw_destroy_plan(shot[ *this].m_fftplan[d]);
242  fftw_free(shot[ *this].m_pFFTin[d]);
243  fftw_free(shot[ *this].m_pFFTout[d]);
244  }
245  tr[ *this].m_pFFTin[d] = (fftw_complex*)fftw_malloc(sizeof(fftw_complex) * fftlen * fftlen * fftlen);
246  tr[ *this].m_pFFTout[d] = (fftw_complex*)fftw_malloc(sizeof(fftw_complex) * fftlen * fftlen * fftlen);
247  tr[ *this].m_fftplan[d] = fftw_plan_dft_3d(fftlen, fftlen, fftlen,
248  shot[ *this].m_pFFTin[d], shot[ *this].m_pFFTout[d],
249  FFTW_FORWARD, FFTW_ESTIMATE);
250  }
251  tr[ *this].m_fftlen = fftlen;
252  });
253 }
254 void
256  m_lsnTargetChanged.reset();
257  m_lsnStepTouched.reset();
258  m_lsnGraphChanged.reset();
260  m_L->setUIEnabled(true);
261  m_cutoffReal->setUIEnabled(true);
262  m_cutoffRec->setUIEnabled(true);
263  m_alpha->setUIEnabled(true);
264  m_hdirx->setUIEnabled(true);
265  m_hdiry->setUIEnabled(true);
266  m_hdirz->setUIEnabled(true);
267 
268  closeInterface();
269 }
270 void
272  const Snapshot &shot(tr);
273  unsigned int size = MonteCarlo::length();
274  if(reader.size() != size*size*size*16)
275  throw XRecordError("Size Mismatch", __FILE__, __LINE__);
276  MonteCarlo::Vector3<double> field_dir(shot[ *m_hdirx], shot[ *m_hdiry], shot[ *m_hdirz]);
277  field_dir.normalize();
278  MonteCarlo::Vector3<double> field(field_dir);
279  field *= shot[ *m_targetField];
280  char *spins = (char*)&reader.data()[0];
281  tr[ *this].m_store->read(spins, shot[ *m_targetTemp], field);
282 
283  double dT = shot[ *m_targetTemp] - shot[ *this].m_lastTemp;
284  tr[ *this].m_lastTemp = shot[ *m_targetTemp];
285  double m = shot[ *this].m_store->magnetization().innerProduct(field_dir);
286  double dM = m - shot[ *this].m_lastMagnetization;
287  double dH = shot[ *m_targetField] - shot[ *this].m_lastField;
288  double dU = shot[ *this].m_dU;
289  // DS += (DU + HDM + MDH)/T
290  tr[ *this].m_sumDS += (dU + dM * shot[ *m_targetField] * MU_B * N_A) / shot[ *m_targetTemp];
291  // DU += -MDH.
292  dU += -shot[ *this].m_lastMagnetization * MU_B * N_A * dH;
293  double dUav = shot[ *this].m_DUav * N_A;
294  dUav += -shot[ *this].m_Mav * MU_B * N_A * dH;
295  double c = (fabs(dT) < 1e-10) ? 0.0 : ((shot[ *this].m_sumDU + dUav - shot[ *this].m_sumDUav) / dT);
296  tr[ *this].m_sumDUav = shot[ *this].m_sumDU + dUav;
297  tr[ *this].m_sumDU += dU;
298  tr[ *this].m_lastMagnetization = m;
299  tr[ *this].m_lastField = shot[ *m_targetField];
300  double u = shot[ *this].m_sumDU;
301  if(rand() % 20 == 0) {
302  std::cerr << "Recalculate Internal Energy." << std::endl;
303  u = shot[ *this].m_store->internalEnergy() * N_A;
304  if(fabs((u - shot[ *this].m_sumDU)/u) > 1e-5) {
305  gErrPrint(formatString("SumDU Error = %g!", (double)(u - shot[ *this].m_sumDU)/u));
306  }
307  }
308  MonteCarlo::Quartet quartet = shot[ *this].m_store->siteMagnetization();
309  m_entryT->value(tr, shot[ *this].m_lastTemp);
310  m_entryH->value(tr, shot[ *this].m_lastField);
311  m_entryU->value(tr, u);
312  m_entryC->value(tr, c);
313  m_entryCoT->value(tr, c / shot[ *this].m_lastTemp);
314  m_entryS->value(tr, shot[ *this].m_sumDS);
315  m_entryM->value(tr, shot[ *this].m_Mav);
316  m_entry2in2->value(tr, 100.0*quartet.twotwo);
317  m_entry1in3->value(tr, 100.0*quartet.onethree);
318 }
319 void
321  if( !shot[ *this].time()) {
322  iterate_commit([=](Transaction &tr){
323  tr[ *m_wave3D].clearPoints();
324  });
325  return;
326  }
327 
328  bool fftx = false;
329  bool ffty = false;
330  bool fftz = false;
331  bool fft_intens_abs = false;
332  bool along_field_dir = false;
333  bool calch = false;
334  bool calcp = false;
335  bool calcasite = false;
336  bool calcbsite = false;
337  bool calc8asite = false;
338  bool calc48fsite = false;
339  bool writeflips = false;
340  if(shot[ *m_graph3D].to_str() == GRAPH_3D_FFT_INTENS_ABS) {
341  fftx = true;
342  ffty = true;
343  fftz = true;
344  fft_intens_abs = true;
345  }
346  if(shot[ *m_graph3D].to_str() == GRAPH_3D_FFT_INTENS_X) {
347  fftx = true;
348  }
349  if(shot[ *m_graph3D].to_str() == GRAPH_3D_FFT_INTENS_Y) {
350  ffty = true;
351  }
352  if(shot[ *m_graph3D].to_str() == GRAPH_3D_FFT_INTENS_Z) {
353  fftz = true;
354  }
355  if(shot[ *m_graph3D].to_str() == GRAPH_3D_FFT_INTENS_M) {
356  fftx = true;
357  ffty = true;
358  fftz = true;
359  along_field_dir = true;
360  }
361  if(shot[ *m_graph3D].to_str() == GRAPH_REAL_M) {
362  calcasite = true;
363  along_field_dir = true;
364  }
365  if(shot[ *m_graph3D].to_str() == GRAPH_REAL_H) {
366  calcasite = true;
367  calch = true;
368  }
369  if(shot[ *m_graph3D].to_str() == GRAPH_REAL_P) {
370  calcasite = true;
371  calch = true;
372  calcp = true;
373  }
374  if(shot[ *m_graph3D].to_str() == GRAPH_REAL_H_B_SITE) {
375  calcbsite = true;
376  }
377  if(shot[ *m_graph3D].to_str() == GRAPH_REAL_H_8a_SITE) {
378  calc8asite = true;
379  }
380  if(shot[ *m_graph3D].to_str() == GRAPH_REAL_H_48f_SITE) {
381  calc48fsite = true;
382  }
383  if(shot[ *m_graph3D].to_str() == GRAPH_FLIPS) {
384  writeflips = true;
385  }
386 
387  int size = shot[ *this].m_store->length();
388  std::vector<char> spins(size*size*size*16);
389  std::vector<double> fields;
390  if(calch) fields.resize(size*size*size*16);
391  std::vector<double> probabilities;
392  if(calcp) probabilities.resize(size*size*size*16);
393  shot[ *this].m_store->write((char*)&spins[0]
394  , fields.size() ? &fields[0] : 0, probabilities.size() ? &probabilities[0] : 0);
395  int fftlen = shot[ *this].m_fftlen;
396  for(int d = 0; d < 3; d++) {
397  for(int site = 0; site < 16; site++) {
398  const int *pos = cg_ASitePositions[site];
399  int ising = cg_ASiteIsingAxes[site][d];
400  for(int k = 0; k < size; k++) {
401  for(int j = 0; j < size; j++) {
402  for(int i = 0; i < size; i++) {
403  int fftidx =fftlen*(fftlen*(4*k+pos[2]) + 4*j+pos[1]) + 4*i + pos[0];
404  int spin = spins[size*(size*(size*site + k) + j) + i];
405  shot[ *this].m_pFFTin[d][fftidx][0] = spin* ising / sqrt(3.0);
406  }
407  }
408  }
409  }
410  }
411 
412  MonteCarlo::Vector3<double> field_dir(shot[ *m_hdirx], shot[ *m_hdiry], shot[ *m_hdirz]);
413  field_dir.normalize();
414 
415 
416  if(fftx || ffty || fftz) {
417  fftw_execute(shot[ *this].m_fftplan[0]);
418  fftw_execute(shot[ *this].m_fftplan[1]);
419  fftw_execute(shot[ *this].m_fftplan[2]);
420 
421  m_wave3D->iterate_commit([=](Transaction &tr){
422  tr[ *m_wave3D].setRowCount(fftlen * fftlen * fftlen );
423  double normalize = A_MOMENT / fftlen / fftlen / fftlen;
424  int idx = 0;
425  for(int l = 0; l < fftlen; l++) {
426  for(int k = 0; k < fftlen; k++) {
427  for(int h = 0; h < fftlen; h++) {
428  int qidx = fftlen*(fftlen*l + k) + h;
429  fftw_complex *ix = &shot[ *this].m_pFFTout[0][qidx];
430  fftw_complex *iy = &shot[ *this].m_pFFTout[1][qidx];
431  fftw_complex *iz = &shot[ *this].m_pFFTout[2][qidx];
432  tr[ *m_wave3D].cols(0)[idx] = (double)h * 8.0/fftlen;
433  tr[ *m_wave3D].cols(1)[idx] = (double)k * 8.0/fftlen;
434  tr[ *m_wave3D].cols(2)[idx] = (double)l * 8.0/fftlen;
435  double v = 0.0;
436  if(along_field_dir) {
437  double vr = field_dir.innerProduct(MonteCarlo::Vector3<double>
438  ((*ix)[0], (*iy)[0], (*iz)[0]));
439  double vi = field_dir.innerProduct(MonteCarlo::Vector3<double>
440  ((*ix)[1], (*iy)[1], (*iz)[1]));
441  v = vr*vr + vi * vi;
442  }
443  else {
444  if(fftx) v+= (*ix)[0]*(*ix)[0] + (*ix)[1]*(*ix)[1];
445  if(ffty) v+= (*iy)[0]*(*iy)[0] + (*iy)[1]*(*iy)[1];
446  if(fftz) v+= (*iz)[0]*(*iz)[0] + (*iz)[1]*(*iz)[1];
447  }
448  v = sqrt(v);
449  tr[ *m_wave3D].cols(3)[idx] = v * normalize;
450  tr[ *m_wave3D].cols(4)[idx] = ((*ix)[0]*(*ix)[0] + (*ix)[1]*(*ix)[1]) * normalize;
451  tr[ *m_wave3D].cols(5)[idx] = ((*iy)[0]*(*iy)[0] + (*iy)[1]*(*iy)[1]) * normalize;
452  tr[ *m_wave3D].cols(6)[idx] = ((*iz)[0]*(*iz)[0] + (*iz)[1]*(*iz)[1]) * normalize;
453  tr[ *m_wave3D].cols(7)[idx] = 0;
454  idx++;
455  }
456  }
457  }
458  m_wave3D->drawGraph(tr);
459  });
460  }
461  if(calcasite) {
462  m_wave3D->iterate_commit([=](Transaction &tr){
463  int idx = 0;
464  tr[ *m_wave3D].setRowCount(16*size*size*size);
465  for(int site = 0; site < 16; site++) {
466  const int *pos = cg_ASitePositions[site];
467  for(int k = 0; k < size; k++) {
468  for(int j = 0; j < size; j++) {
469  for(int i = 0; i < size; i++) {
470  int sidx = size*(size*(size*site + k) + j) + i;
471  int fftidx = fftlen*(fftlen*(4*k+pos[2]) + 4*j+pos[1]) + 4*i + pos[0];
472  double x = i + pos[0] * 0.25;
473  double y = j + pos[1] * 0.25;
474  double z = k + pos[2] * 0.25;
475  tr[ *m_wave3D].cols(0)[idx] = x;
476  tr[ *m_wave3D].cols(1)[idx] = y;
477  tr[ *m_wave3D].cols(2)[idx] = z;
478  double sx = shot[ *this].m_pFFTin[0][fftidx][0];
479  double sy = shot[ *this].m_pFFTin[1][fftidx][0];
480  double sz = shot[ *this].m_pFFTin[2][fftidx][0];
481  double v = 0.0;
482  if(along_field_dir) {
483  v = field_dir.innerProduct(MonteCarlo::Vector3<double>
484  (sx,sy,sz)) * A_MOMENT;
485  }
486  else {
487  if(calcp) {
488  v = probabilities[sidx];
489  }
490  else {
491  if(calch) {
492  v = fields[sidx];
493  }
494  }
495  }
496  tr[ *m_wave3D].cols(3)[idx] = v;
497  tr[ *m_wave3D].cols(4)[idx] = sx;
498  tr[ *m_wave3D].cols(5)[idx] = sy;
499  tr[ *m_wave3D].cols(6)[idx] = sz;
500  tr[ *m_wave3D].cols(7)[idx] = site;
501  idx++;
502  }
503  }
504  }
505  m_wave3D->drawGraph(tr);
506  }
507  });
508  }
509  if(calcbsite) {
510  std::vector<MonteCarlo::Vector3<double> > fields(16*size*size*size);
511  shot[ *this].m_store->write_bsite(&fields[0]);
512  m_wave3D->iterate_commit([=](Transaction &tr){
513  int idx = 0;
514  tr[ *m_wave3D].setRowCount(16*size*size*size);
515  for(int site = 0; site < 16; site++) {
516  const int *pos = cg_BSitePositions[site];
517  for(int k = 0; k < size; k++) {
518  for(int j = 0; j < size; j++) {
519  for(int i = 0; i < size; i++) {
520  int sidx = size*(size*(size*site + k) + j) + i;
521  MonteCarlo::Vector3<double> h(fields[sidx]);
522  double x = i + pos[0] * 0.25;
523  double y = j + pos[1] * 0.25;
524  double z = k + pos[2] * 0.25;
525  tr[ *m_wave3D].cols(0)[idx] = x;
526  tr[ *m_wave3D].cols(1)[idx] = y;
527  tr[ *m_wave3D].cols(2)[idx] = z;
528  tr[ *m_wave3D].cols(3)[idx] = h.abs();
529  tr[ *m_wave3D].cols(4)[idx] = h.x;
530  tr[ *m_wave3D].cols(5)[idx] = h.y;
531  tr[ *m_wave3D].cols(6)[idx] = h.z;
532  tr[ *m_wave3D].cols(7)[idx] = site;
533  idx++;
534  }
535  }
536  }
537  }
538  m_wave3D->drawGraph(tr);
539  });
540  }
541  if(calc8asite) {
542  std::vector<MonteCarlo::Vector3<double> > fields(8*size*size*size);
543  shot[ *this].m_store->write_8asite(&fields[0]);
544  m_wave3D->iterate_commit([=](Transaction &tr){
545  int idx = 0;
546  tr[ *m_wave3D].setRowCount(8*size*size*size);
547  for(int site = 0; site < 8; site++) {
548  const int *pos = cg_8aSitePositions[site];
549  for(int k = 0; k < size; k++) {
550  for(int j = 0; j < size; j++) {
551  for(int i = 0; i < size; i++) {
552  int sidx = size*(size*(size*site + k) + j) + i;
553  MonteCarlo::Vector3<double> h(fields[sidx]);
554  double x = i + pos[0] * 0.125;
555  double y = j + pos[1] * 0.125;
556  double z = k + pos[2] * 0.125;
557  tr[ *m_wave3D].cols(0)[idx] = x;
558  tr[ *m_wave3D].cols(1)[idx] = y;
559  tr[ *m_wave3D].cols(2)[idx] = z;
560  tr[ *m_wave3D].cols(3)[idx] = h.abs();
561  tr[ *m_wave3D].cols(4)[idx] = h.x;
562  tr[ *m_wave3D].cols(5)[idx] = h.y;
563  tr[ *m_wave3D].cols(6)[idx] = h.z;
564  tr[ *m_wave3D].cols(7)[idx] = site;
565  idx++;
566  }
567  }
568  }
569  }
570  m_wave3D->drawGraph(tr);
571  });
572  }
573  if(calc48fsite) {
574  std::vector<MonteCarlo::Vector3<double> > fields(48*size*size*size);
575  shot[ *this].m_store->write_48fsite(&fields[0]);
576  m_wave3D->iterate_commit([=](Transaction &tr){
577  int idx = 0;
578  tr[ *m_wave3D].setRowCount(48*size*size*size);
579  for(int site = 0; site < 48; site++) {
580  const double *pos = cg_48fSitePositions[site];
581  for(int k = 0; k < size; k++) {
582  for(int j = 0; j < size; j++) {
583  for(int i = 0; i < size; i++) {
584  int sidx = size*(size*(size*site + k) + j) + i;
585  MonteCarlo::Vector3<double> h(fields[sidx]);
586  double x = i + pos[0] * 0.125;
587  double y = j + pos[1] * 0.125;
588  double z = k + pos[2] * 0.125;
589  tr[ *m_wave3D].cols(0)[idx] = x;
590  tr[ *m_wave3D].cols(1)[idx] = y;
591  tr[ *m_wave3D].cols(2)[idx] = z;
592  tr[ *m_wave3D].cols(3)[idx] = h.abs();
593  tr[ *m_wave3D].cols(4)[idx] = h.x;
594  tr[ *m_wave3D].cols(5)[idx] = h.y;
595  tr[ *m_wave3D].cols(6)[idx] = h.z;
596  tr[ *m_wave3D].cols(7)[idx] = site;
597  idx++;
598  }
599  }
600  }
601  }
602  m_wave3D->drawGraph(tr);
603  });
604  }
605  if(writeflips) {
606  std::deque<MonteCarlo::FlipHistory> flips;
607  shot[ *this].m_loop->write_flips(flips);
608 
609  m_wave3D->iterate_commit([=](Transaction &tr){
610  tr[ *m_wave3D].setRowCount(flips.size());
611  for(int idx = 0; idx < (int)flips.size(); idx++) {
612  int lidx = flips[idx].lidx;
613  int site = flips[idx].site;
614  int i = lidx % size;
615  lidx /= size;
616  int j = lidx % size;
617  lidx /= size;
618  int k = lidx % size;
619 
620  const int *pos = cg_ASitePositions[site];
621  double x = i + pos[0] * 0.25;
622  double y = j + pos[1] * 0.25;
623  double z = k + pos[2] * 0.25;
624  tr[ *m_wave3D].cols(0)[idx] = x;
625  tr[ *m_wave3D].cols(1)[idx] = y;
626  tr[ *m_wave3D].cols(2)[idx] = z;
627  tr[ *m_wave3D].cols(3)[idx] = (flips[idx].delta > 0.0) ? 2.0 : 1.0;
628  tr[ *m_wave3D].cols(4)[idx] = flips[idx].delta;
629  tr[ *m_wave3D].cols(5)[idx] = flips[idx].tests;
630  tr[ *m_wave3D].cols(6)[idx] = 0;
631  tr[ *m_wave3D].cols(7)[idx] = site;
632  }
633  m_wave3D->drawGraph(tr);
634  });
635  }
636 }
637 void
638 XMonteCarloDriver::onGraphChanged(const Snapshot &shot, XValueNodeBase *) {
639  Snapshot shot_this( *this);
640  visualize(shot_this);
641 
642 }
643 void
644 XMonteCarloDriver::onTargetChanged(const Snapshot &shot, XValueNodeBase *) {
645  Snapshot shot_this( *this);
646  int size = shot_this[ *this].m_loop->length();
647  int spin_size = size*size*size*4*4;
648  int flips = (int)(shot_this[ *m_minFlips] * spin_size);
649  long double tests = shot_this[ *m_minTests] * spin_size;
650  execute(flips, tests);
651 }
652 void
653 XMonteCarloDriver::onStepTouched(const Snapshot &shot, XTouchableNode *) {
654  execute(1, 1);
655 }
656 void
657 XMonteCarloDriver::execute(int flips, long double tests) {
658  Snapshot shot = iterate_commit([=, &flips, &tests](Transaction &tr){
659  unsigned int size = tr[ *this].m_loop->length();
660  int spin_size = size*size*size*4*4;
661  MonteCarlo::Vector3<double> field_dir(tr[ *m_hdirx], tr[ *m_hdiry], tr[ *m_hdirz]);
662  field_dir.normalize();
663  MonteCarlo::Vector3<double> field(field_dir);
664  field *= tr[ *m_targetField];
666  tr[ *this].m_dU = tr[ *this].m_loop->exec(tr[ *m_targetTemp], field, &flips, &tests, &tr[ *this].m_DUav, &m) * N_A;
667  tr[ *this].m_testsTotal += tests;
668  tr[ *this].m_flippedTotal += flips;
669  fprintf(stderr, "Total flips = %g (%g per spin).\n",
670  ((double)tr[ *this].m_flippedTotal), ((double)tr[ *this].m_flippedTotal / spin_size));
671  tr[ *this].m_Mav = m.innerProduct(field_dir);
672  fprintf(stderr, "Total tests = %g (%g per spin).\n",
673  ((double)tr[ *this].m_testsTotal), ((double)tr[ *this].m_testsTotal / spin_size));
674  });
675  unsigned int size = shot[ *this].m_loop->length();
676  auto writer = std::make_shared<RawData>();
677  writer->resize(size*size*size*16);
678  shot[ *this].m_loop->write((char*)&writer->at(0));
679  finishWritingRaw(writer, XTime::now(), XTime::now());
680 }

Generated for KAME4 by  doxygen 1.8.3