イジングモデルの数値計算例 2 |
- プログラムソース
以下のプログラムは、イジングモデルの数値計算例 1 のプログラムをさらにエネルギーと比熱と磁化を求めるために改良したものである。
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#define n 100 //系の最大数
#define J 1.0 //交換相互作用
#define max 500 //平均エネルギーを求めるための試行回数
double ising(int seed,double T,double *M); //イジングモデルの基本的計算を行う関数
double E(double spin[n]); //エネルギーを計算する関数
int judge(double beta,double oldE,double newE); //スピンの向きを変えるのかを判断する関数
int main()
{
int i,seed;
double T,U,aveU1,aveU2,C,M,m;
FILE *output1,*output2,*output3;
output1=fopen("energy.data","w");
output2=fopen("hinetsu.data","w");
output3=fopen("zika.data","w");
/*理論的にはTはkT(ボルツマン定数X温度)に値する*/
for(T=0.1;T<10.0;T+=0.1) {
seed=0; //ここでは乱数の種をただ1ずつ増やすだけである。他の方法でもよい。
aveU1=aveU2=0;
m=0.0;
for(i=0;i<max;i++) {
M=0.0;
U=ising(seed,T,&M);
aveU1+=U;
aveU2+=U*U;
m+=M;
seed++;
}
aveU1/=max; //これはエネルギーの平均値
aveU2/=max; //これはエネルギーの2乗の平均値
m/=max; //磁化の平均値
C=(aveU2-aveU1*aveU1)/(T*T); //比熱の計算
fprintf(output1,"%f %f\n",T,aveU1);
fprintf(output2,"%f %f\n",T,C);
fprintf(output3,"%f %f\n",T,m);
}
return 0;
}
/*乱数の種と温度と磁化の値を入れる変数のポインタを受け取り、
乱数の種と温度の値に応じてイジングモデルのシミュレーションを行う*/
double ising(int seed,double T,double *M)
{
int i,m;
double spin[n];
double beta,oldE,newE,U;
beta=1.0/T;
srand(seed); //乱数の発生の仕方を変える
for(i=0;i<n;i++) {
spin[i]=-1.0; //スピン初期状態の決定
}
for(i=0;i<500;i++) {
oldE=E(spin); //前のエネルギー値
m=(int)1.0/(RAND_MAX+1.0)*rand()*n;
spin[m]*=-1.0; //スピンの向きを変える
newE=E(spin); //新しいエネルギー
if(judge(beta,oldE,newE)) spin[m]*=-1.0; //1が返されたらスピンの方向を戻す
}
/*磁化の計算*/
for(i=0;i<n;i++) {
*M+=spin[i];
}
*M=*M/n;
U=E(spin); //エネルギーの計算
return U;
}
//スピン相互作用によるエネルギーの計算
double E(double spin[n])
{
int i;
double E;
E=0.0;
for(i=0;i<(n-1);i++) {
E+=-J*spin[i]*spin[i+1];
}
return E;
}
//新しい状態が実現するなら0、しないなら1を返す
int judge(double beta,double oldE,double newE)
{
if((newE>oldE) && (exp(-beta*(newE-oldE)) <= 1.0/(RAND_MAX+1.0)*rand())) return 1;
else return 0;
}
- GNUPLOT出力結果
エネルギーと比熱と磁化についてのグラフをみてみる。横軸は kT (ボルツマン定数 X 温度) 、縦軸はそれぞれの種類の値の大きさである。
ここで比熱のグラフに注目すると、横軸の 1 付近で急激に値が大きくなっている。このときエネルギーも急激に増え始め、磁化は消え始めている。この現象を相転移といい、系は秩序状態から無秩序状態へ変化しているのである。
比熱が 0 付近あたりでのふるまいは誤差の影響と思われる。エネルギーのグラフからエネルギーはそのあたりでそれほど変化してないので、比熱は 0
付近では、小さな値であると思われるからだ。
|
|
|