2016-07-09 10 views
0

私は外部ライブラリhttps://people.sc.fsu.edu/~jburkardt/c_src/jacobi_eigenvalue/jacobi_eigenvalue.cを使用して行列の固有値を計算しています。しかし、ライブラリ関数を呼び出した後、目的のポインタ値にアクセスしようとしたときにセグメンテーションエラーが発生しました。ライブラリ関数を呼び出した後、目的のポインタ値にアクセス/変更できません

void asphericity(particle *p, int N, float aveLTail[MAX2][MAX2], double *Nominator, double *Denominator, double *Asp ,double *cmx, double *cmy, double *cmz){ 
int i, j, k,m,n,M; 
double x[10000]; 
double y[10000]; 
double z[10000]; 
double *Q; 
double gyration[3][3]; 
double v[M*M]; 
double d[M]; 
float ut, up; 
float bs; 
double hdistance; 
double tdistance; 
double rog; 
int hcount=0; 
int tcount=0; 
int it_max; 
int it_num; 
int rot_num; 
double hx=0; 
double hy=0; 
double hz=0; 
double tx=0; 
double ty=0; 
double tz=0; 
m=0; 


it_max=100; 
for(i = 1; i<=N; i++) { 
    if (p[i].mol == p[i-1].mol){ 
     if (p[i-1].type==1 ||p[i-1].type==2 || p[i-1].type==3 || p[i-1].type==6){ 
      hcount++; 
      hx += p[i-1].x; 
      hy += p[i-1].y; 
      hz += p[i-1].z; 
     } 
     else if (p[i-1].type==4 && p[i-2].type==9){ 
      tcount++; 
      tx += p[i-1].x; 
      ty += p[i-1].y; 
      tz += p[i-1].z; 
      hcount += 2; 
      hx += p[i-2].x+p[i-3].x; 
      hy += p[i-2].y+p[i-3].y; 
      hz += p[i-2].z+p[i-3].z; 
     } 
     else if (p[i-1].type==4 && p[i-2].type!=9){ 
      tcount++; 
      tx += p[i-1].x; 
      ty += p[i-1].y; 
      tz += p[i-1].z; 
     } 

    } 
    else if (p[i].mol != p[i-1].mol && p[i-1].mol!=0) { 
      tcount++; 
      tx += p[i-1].x; 
      ty += p[i-1].y; 
      tz += p[i-1].z; 
      (hx) /= hcount; /*geometric center of head beads*/ 
      (hy) /= hcount; 
      (hz) /= hcount; 
      (tx) /= tcount; 
      (ty) /= tcount; 
      (tz) /= tcount; 
      hcount=0; 
      tcount=0; 
      hdistance=sqrt(pow((hx-*cmx),2)+pow((hy-*cmy),2)+pow((hz-*cmz),2)); 
      tdistance=sqrt(pow((tx-*cmx),2)+pow((ty-*cmy),2)+pow((tz-*cmz),2)); 
      if(hdistance>tdistance){ 
       x[m]=hx; 
       y[m]=hy; 
       z[m]=hz; 
       m++; 
      } 
      hx=0; 
      hy=0; 
      hz=0; 
      tx=0; 
      ty=0; 
      tz=0; 
     }    
    } 


for(j = 0; j<m; j++) { 
    gyration[0][0]+= pow((x[j]-*cmx),2); 
    gyration[0][1]+=(x[j]-*cmx)*(y[j]-*cmy); 
    gyration[0][2]+=(x[j]-*cmx)*(z[j]-*cmz); 
    gyration[1][0]+=(y[j]-*cmy)*(x[j]-*cmx); 
    gyration[1][1]+=pow((y[j]-*cmy),2); 
    gyration[1][2]+=(y[j]-*cmy)*(z[j]-*cmz); 
    gyration[2][0]+=(z[j]-*cmz)*(x[j]-*cmx); 
    gyration[2][1]+=(z[j]-*cmz)*(y[j]-*cmy); 
    gyration[2][2]+=pow((z[j]-*cmz),2); 
} 
for(i =0; i<3; i++){ 
    for(j=0; j<3; j++){ 
     gyration[i][j]/=m; 
     } 
} 

#define M 3 
double Gyration[M*M] = { 
      gyration[0][0],gyration[0][1],gyration[0][2], 
      gyration[1][0],gyration[1][1],gyration[1][2], 
      gyration[2][0],gyration[2][1],gyration[2][2] }; 
printf("%.6f\t%.6f\t%.6f\n", *Denominator, *Nominator, *Asp); 
jacobi_eigenvalue(M, Gyration, it_max, v, d, &it_num, &rot_num); 
printf("%.6f\t%.6f\t%.6f\n", *Denominator, *Nominator, *Asp); 
rog = sqrt(d[0]+d[1]+d[2]); 
*Denominator= 2*pow(rog,4); 
*Nominator= pow((d[2]-d[1]),2)+pow((d[2]-d[0]),2)+pow((d[1]-d[0]),2); 
* Asp = (*Nominator)/(*Denominator); 
# undef M 
} 

分母、推薦、およびAspは、main関数内の二重の変数として定義され、ポインタとして渡されました。しかし、ライブラリ関数呼び出しの後にアクセスしようとしたときにセグメント違反が発生しました。出力v []とd []にアクセスできました。

最初のprintfは、*分母、* Nominatorおよび* Aspゼロを示し、セグメンテーションフォルトは2番目のprintfに表示されます。したがって、ライブラリ関数では何かが正しくありません。しかし、私は問題がどこにあるのか、それをどう解決するのかは分かりません。

ありがとうございます。

+1

行ごとのデバッグと変数の検査で明らかになるのは何ですか? – Ian

+1

完全なプログラムコードを共有できますか?または、少なくとも1つを減らしましたが、それでも問題は明らかです。 – Sergio

+0

ライブラリ関数呼び出しの前に、* Denominator、* Nominator、* Asp(すべて0)にアクセスできました。 (gdbを使ってチェック)しかし、* Denominator = 2 * pow(rog、4)にsigsegv segmentation faultメッセージがあります。この変数のメモリにアクセスできません。だから私は何かがライブラリの機能に混乱していると思う。 – Sean

答えて

0

コードのサマリービューには、いくつかの潜在的な「ゼロ除算」エラーが表示されます。焦点を当て*分母、次は潜在的な落とし穴です:

* Asp = (*Nominator)/(*Denominator); 

*分母がゼロであれば、あなたは(ゼロによる除算)がクラッシュします。また、あなたはforループでこれを持っています:

int hcount=0; 

// some code 

if (p[i].mol == p[i-1].mol){ 

    if (p[i-1].type==1 ||p[i-1].type==2 || p[i-1].type==3 || p[i-1].type==6){ 

    hcount++; 

    } 
    else { 
    // hcount incremented 
    } 
    // some code 
} 
else if (p[i].mol != p[i-1].mol && p[i-1].mol!=0) { 
     tcount++; 
     tx += p[i-1].x; 
     ty += p[i-1].y; 
     tz += p[i-1].z; 
     (hx) /= hcount; /*geometric center of head beads*/ 
     (hy) /= hcount; 
     (hz) /= hcount; 
     (tx) /= tcount; 
     (ty) /= tcount; 
     (tz) /= tcount; 
    } 

これは、hcountで除算することに注意してください。 hcountは宣言時にゼロに初期化され、forループ内の最初のif文でのみインクリメントされます。最初の反復が最初の条件を満たしておらず、elseでその方法を見つけたら、ゼロで割ります。

また

、最初の場合は条件が失敗した場合、それは必ずしも以下のため

else if (p[i].mol != p[i-1].mol && p[i-1].mol!=0) 

p[i].mol != p[i-1].mol 

は必要ありません。

関連する問題