【问题标题】:Ising Model in C++C++ 中的伊辛模型
【发布时间】:2014-05-23 07:27:44
【问题描述】:

我正在用 C++ 为 2D Ising 模型编写代码。以下是代码应该执行的操作:

  1. 生成随机 NxN 点阵,每个站点的值为 +1 或 -1。
  2. 随机选择站点
  3. 如果翻转时的站点(+1 到 -1 或 -1 到 +1)是较低能量的状态,则翻转状态,即。如果 dE
  4. 喜欢 100 次扫描。

我在执行第 1、2 和 3 步时遇到了问题,不胜感激!对于第 1 步,我设法创建并显示了一个格子,但我似乎无法在位置 (x, y) 处提取站点的值。第 2 步和第 3 步,如何使用某种布尔表达式根据接受概率进行翻转?

 #include <cstdlib>
#include <ctime>
using namespace std;
#include <iostream>
int main() //random generation of spin configuration
{
int L;              //Total number of spins L = NxN
int N = 30          //A square lattice of length 30
double B=1;         //magnetic field
double M;           //Total Magnetization = Sum Si
double E;           //Total Energy
int T = 1.0;
int nsweeps = 100;      //number of sweeps
int de;             //change in energy when flipped
double Boltzmann;       //Boltzmann factor
int x,y;            //randomly chosen lattice site
int i,j,a,c;            //counters
  int ROWS = 5;
  int COLS = 5;
  int matrix[ROWS][COLS];
  srand ( static_cast<unsigned> ( time ( 0 ) ) );
  for ( int i = 0; i < ROWS; i++ ) 
  {
    for ( int j = 0; j < COLS; j++ )
    {
      matrix[i][j] = rand () % 2 *2-1;
    }
  }

 // showing the matrix on the screen
    for(int i=0;i<ROWS;i++)  // loop 3 times for three lines
    {
        for(int j=0;j<COLS;j++)  // loop for the three elements on the line
        {
            cout<<matrix[i][j];  // display the current element out of the array
        }
    cout<<endl;  // when the inner loop is done, go to a new line
    }
    return 0;  // return 0 to the OS.

//boundary conditions and range
if(x<0) x += N;      
if(x>=L) x -= N;
if(y<0) y += N;
if(y>=L) y -= N;

//counting total energy of configuration
{  int neighbour = 0;    // nearest neighbour count

   for(int i=0; i<L; i++)
      for(int j=0; j<L; j++)
    {  if(spin(i,j)==spin(i+1, j))     // count from each spin to the right and above 
              neighbour++;
           else 
              neighbour--;
           if(spin(i, j)==spin(i, j+1))
              neighbour++;
           else
              neighbour--;
    }

    E = -J*neighbour - B*M;

//flipping spin
int x = int(srand48()*L);   //retrieves spin from randomly choosen site
int y = int(srand48()*L);

int delta_M = -2*spin(x, y);    //calculate change in Magnetization M
int delta_neighbour = spin(spinx-1, y) + spin(x+1, y)+ spin(x, y-1) + spin(x, y+1);
int delta_neighbour = -2*spin(x,y)* int delta_neighbour;

double delta_E = -J*delta_neighbour -B*delta_M;


//flip or not
if (delta_E<=0)
    {  (x, y) *= -1;     // flip spin and update values
           M += delta_M;
           E += delta_E;

        }



}

【问题讨论】:

  • 如何测量给定翻转的 dE?
  • 计算翻转状态的能量,减去原始状态的能量。现场任何状态的能量=(相邻状态能量的乘积)+(磁化*现场状态)
  • 这段代码乱七八糟,无法编译。请给我们缺少的函数/变量,例如spin.
  • 对此我感到非常抱歉 - 我正在努力学习,请多多包涵!我已经更新了代码,定义了 N 和 delta_neighbour 以及代码部分 - 我如何使表达式“spin(x, y)”在位置 (x, y) 处提取该站点的值?每个站点可以取 +1 或 -1 的值,并在开始时随机确定。 int delta_neighbour = (spinx-1, y) + spin(x+1, y)+ spin(x, y-1) + spin(x, y+1); int delta_neighbour = -2*spin(x,y)* int delta_neighbour; //邻居能量的变化
  • 您的代码存在太多问题,无法提供一个答案。尝试逐步构建您的程序。使用执行一件事的功能,并且他们做得很好。单独测试每个功能,如有必要,尝试找出它不起作用的原因。然后再次发布具体问题。

标签: c++ algorithm boolean


【解决方案1】:

跟进我的评论:

您的代码存在太多问题,无法提供一个答案。尝试 逐步构建您的程序。使用执行一项功能的功能 事情,他们做得很好。单独测试每个功能,如果 有必要尝试找出它为什么不起作用。然后具体发帖 再次提问。

让您开始:

  • 将您的晶格存储为std::vector&lt;int&gt; lattice(N*N)
  • 访问元素(x,y)data[x+N*y]

例子:

#include <vector>

struct IsingModel
{ 
    unsigned size_;

    std::vector<int> lattice_;

    // access element (x,y)
    int& at(int x, int y) {
        return lattice_[x + y*size_];
    }
    int at(int x, int y) const {
        return lattice_[x + y*size_];
    }

    // generate size x size lattice
    IsingModel(unsigned size)
    : size_(size), lattice_(size*size, +1) {
    }

    static int BoolToSpin(bool v) {
        return v ? +1 : -1;
    }

    // initialize spin randomly
    void initializeRandom() {
        for(int y=0; y<size_; y++) {
            for(int x=0; x<size_; x++) {
                at(x,y) = BoolToSpin(rand()%2);
            }
        }
    }

    static int Energy(int a, int b) {
        return (a == b) ? +1 : -1;
    }

    // compute total energy
    unsigned computeTotalEnergy() const {
        unsigned energy = 0;
        for(int y=1; y<size_-1; y++) {
            for(int x=1; x<size_-1; x++) {
                energy += Energy(at(x,y), at(x+1,y));
                energy += Energy(at(x,y), at(x,y+1));
            }
        }
        return energy ;
    }

 };

 #include <iostream>     
 #include <cstdlib>
 #include <ctime>

 int main() {
     srand(static_cast<unsigned>(time(0))); // intialize random number generator
     IsingModel im(10);
     im.initializeRandom();
     unsigned energy = im.computeTotalEnergy();
     std::cout << energy << std::endl; // print energy
 }

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-07-31
    • 2021-12-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多