2

ターミナルを介してMac(10.8.2)でこのコードを実行していますが、特定のnに対して「Illegal Instruction 4」で終了します。理由や停止方法を知っている人はいますか?

n=43、45、47、および 57 を除いてコードが正常に実行されるので、私は混乱しています。

また、n=60 以降はすべての n で発生するようです。n の値が小さい場合は正常に機能するため、メモリの問題である可能性があります。

注: 整数 c を使用することは、純粋に最初の while ループを減らすためです。できれば、while ループで b<251 を読み取って 250 回の反復を実行したいのですが、代わりに b<51 for c=1,2,3,4,5 のようなものを実行して、1 ではなく 50 の結果を持つ 5 つの異なるファイルを取得しています。 250で。

コードは次のとおりです。

#include <stdio.h> 
#include <string.h>
#include <math.h>
#include <iostream>
#include <iomanip>
#include <fstream>
#include <time.h>
#include <stdlib.h>
#include <sstream>
using namespace std;

int main()
{

  int a,b,c,f,i,j,k,m,n,s;
  double p,Time,Averagetime,Energy,energy,Distance,Length,DotProdForce,Forcemagnitude,
         ForceMagnitude[101],Force[101][4],E[10001],En[501],x[101][4],y[101][4];

  clock_t t1,t2;
  t1=clock();

  b=1;
  c=1;
  Time=0.0;

  while(b<251){

    clock_t t3,t4;
    t3=clock();

    /*  set the number of points */
    n=45;

    /* check that there are no more than 100 points */
    if(n>100){
      cout << n << " is too many points for me :-( \n";
      exit(0);
    }

    /* reset the random number generator */
    srand((unsigned)time(0));  

    for (i=1;i<=n;i++){
      x[i][1]=((rand()*1.0)/(1.0*RAND_MAX)-0.5)*2.0;
      x[i][2]=((rand()*1.0)/(1.0*RAND_MAX)-0.5)*2.0;
      x[i][3]=((rand()*1.0)/(1.0*RAND_MAX)-0.5)*2.0;

      Length=sqrt(pow(x[i][1],2)+pow(x[i][2],2)+pow(x[i][3],2));

      for (k=1;k<=3;k++){
        x[i][k]=x[i][k]/Length;
      }
    }

    /* calculate the energy */
    Energy=0.0;

    for(i=1;i<=n;i++){
      for(j=i+1;j<=n;j++){
        Distance=sqrt(pow(x[i][1]-x[j][1],2)+pow(x[i][2]-x[j][2],2)
                    +pow(x[i][3]-x[j][3],2));

        Energy=Energy+1.0/Distance;
      }
    }

    /* Save Original Points */
    for(i=1;i<=n;i++){
      y[i][1]=x[i][1];
      y[i][2]=x[i][2];
      y[i][3]=x[i][3];
    }

    /* Loop for random points m times*/
    m=10;

    if (m>100){
      cout << "The m="<< m << " loop is inefficient...lessen m \n";
      exit(0);
    }

    a=1;

    while(a<m){

      /* assign random points */
      for (i=1;i<=n;i++){
        x[i][1]=((rand()*1.0)/(1.0*RAND_MAX)-0.5)*2.0;
        x[i][2]=((rand()*1.0)/(1.0*RAND_MAX)-0.5)*2.0;
        x[i][3]=((rand()*1.0)/(1.0*RAND_MAX)-0.5)*2.0;

        Length=sqrt(pow(x[i][1],2)+pow(x[i][2],2)+pow(x[i][3],2));

        for (k=1;k<=3;k++){
          x[i][k]=x[i][k]/Length;
        }
      }

      /* calculate the energy */
      energy=0.0;

      for(i=1;i<=n;i++){
        for(j=i+1;j<=n;j++){
          Distance=sqrt(pow(x[i][1]-x[j][1],2)+pow(x[i][2]-x[j][2],2)
                        +pow(x[i][3]-x[j][3],2));

          energy=energy+1.0/Distance;
        }
      }

      if(energy<Energy)
        for(i=1;i<=n;i++){
          for(j=1;j<=3;j++){
            Energy=energy;
            y[i][j]=x[i][j];
          }
        }
      else
        for(i=1;i<=n;i++){
          for(j=1;j<=3;j++){
            energy=Energy;
            x[i][j]=y[i][j];
          }
        }

      a=a+1;
    }

    /* Create string stream 1 */
    ostringstream String1;
    String1 << "Bestrandonpoints_" << n;  //add number

    /* Output these points */
    ofstream File1 (String1.str().c_str());
    File1 << "Energy=" << Energy << "\n";
    for(i=1;i<=n;i++){
      File1 << x[i][1] << " " <<   x[i][2] << " " << x[i][3] << "\n";
    }
    File1.close(); 

    /* For energy file later */
    E[0]=Energy;

    /* Start doing gradient flow approach */
    a=1;
    s=0;
    f=0;
    Forcemagnitude=1.0;

    if(n>80)
      p=0.005;
    else if(n>60)
      p=0.01;
    else if(n>40)
      p=0.02;
    else
      p=0.05;

    while(Forcemagnitude>0.00005){

      /* Reset initial force and energy change */

      for(i=1;i<=n;i++){ 
        Force[i][1]=0.0; 
        Force[i][2]=0.0; 
        Force[i][3]=0.0; 
      } 
      /* Calculate force on each particle */

      for(i=1;i<=n;i++){ 
        for(j=1;j<i;j++){

          Distance=sqrt(pow(x[i][1]-x[j][1],2)+pow(x[i][2]-x[j][2],2)
                        +pow(x[i][3]-x[j][3],2));
          Force[i][1]=Force[i][1]+((x[i][1]-x[j][1])/(pow((Distance),3))); 
          Force[i][2]=Force[i][2]+((x[i][2]-x[j][2])/(pow((Distance),3))); 
          Force[i][3]=Force[i][3]+((x[i][3]-x[j][3])/(pow((Distance),3))); 
        } 

        for (j=i+1;j<=n;j++){ 

          Distance=sqrt(pow(x[i][1]-x[j][1],2)+pow(x[i][2]-x[j][2],2)
                        +pow(x[i][3]-x[j][3],2));
          Force[i][1]=Force[i][1]+((x[i][1]-x[j][1])/(pow((Distance),3))); 
          Force[i][2]=Force[i][2]+((x[i][2]-x[j][2])/(pow((Distance),3))); 
          Force[i][3]=Force[i][3]+((x[i][3]-x[j][3])/(pow((Distance),3)));
        }
      }

      /* Add the force to my points */
      for(i=1;i<=n;i++){

        DotProdForce=Force[i][1]*x[i][1]+Force[i][2]*x[i][2]+Force[i][3]*x[i][3];

        y[i][1]=x[i][1];
        y[i][2]=x[i][2];
        y[i][3]=x[i][3];

        Force[i][1]=Force[i][1]-DotProdForce*y[i][1];
        Force[i][2]=Force[i][2]-DotProdForce*y[i][2];
        Force[i][3]=Force[i][3]-DotProdForce*y[i][3];

        x[i][1] = y[i][1]+p*(Force[i][1]);
        x[i][2] = y[i][2]+p*(Force[i][2]);
        x[i][3] = y[i][3]+p*(Force[i][3]);

        /* Bring it back onto sphere */

        Length=sqrt(pow(x[i][1],2)+pow(x[i][2],2)+pow(x[i][3],2));

        for (j=1;j<=3;j++){
          x[i][j]=x[i][j]/Length;
        }
      }

      /* Calculate the new energy */

      energy=0.0;

      for(i=1;i<=n;i++){
        for(j=i+1;j<=n;j++){

          Distance=sqrt(pow(x[i][1]-x[j][1],2)+pow(x[i][2]-x[j][2],2)
                        +pow(x[i][3]-x[j][3],2));
          energy=energy+1.0/Distance;
        }
      }

      E[a]=energy;

      /* Choose best energy and therefore best points */
      if (energy<Energy)
        Energy=energy,s=s+1;
      else
        energy=Energy,f=f+1,p=(9.5*p)/10;

      for(i=1;i<=n;i++){
        ForceMagnitude[i]=pow((pow(Force[i][1],2)+pow(Force[i][2],2)
                               +pow(Force[i][3],2)),0.5);
      }

      for(i=1;i<=n-1;i++){
        if(ForceMagnitude[i]<ForceMagnitude[i+1])
          ForceMagnitude[i]=ForceMagnitude[i+1];
        else
          ForceMagnitude[i+1]=ForceMagnitude[i];
      }

      Forcemagnitude=ForceMagnitude[n];

      a=a+1;
    }

    En[b]=Energy;

    b=b+1;

    t4=clock();
    float diff ((float)t4-(float)t3);
    float seconds = diff / CLOCKS_PER_SEC;

    Time = Time + seconds;

  }

  Averagetime = Time/(b-1);

  cout << fixed << setprecision (4) << "Average Time: " << Averagetime << "(s) \n";
  cout << fixed << setprecision(10) << "Energy=" << Energy << "\n";

  t2=clock();
    float diff ((float)t2-(float)t1);
    float seconds = diff / CLOCKS_PER_SEC;

  /* Create string stream 2 */
  ostringstream String2;
  String2 << "GFPoints_" << n;  //add number

  /* Output these points */
  ofstream File2 (String2.str().c_str());
  for(i=1;i<=n;i++){
    File2 << x[i][1] << " " <<   x[i][2] << " " << x[i][3] << "\n";
  }
  File2.close(); 

   /* Create string stream 3 */
  ostringstream String3;
  String3 << "GFEnergies_" << n;  //add number

  /* Output these points */
  ofstream File3 (String3.str().c_str());
  for(i=1;i<a;i++){
    File3 << fixed << setprecision (10) << E[i] << "\n";
  }
  File3.close(); 

  /* Output to help with gnuin.txt */
  ofstream File4 ("mypoints");
  for(i=1;i<=n;i++){
    File4 << x[i][1] << " " <<   x[i][2] << " " << x[i][3] << "\n";
  }
  File4.close(); 

  /* Create string stream 4 */
  ostringstream String4;
  String4 << "GFInfo_" << n;  //add number

  /* Output these points */
  ofstream File5 (String4.str().c_str());
  File5 << "Iterations=" << a-1 << "\n";
  File5 << "Successes=" << s << " Failures=" << f << "\n";
  File5 << fixed << setprecision(20) << "Energy=" << Energy << "\n";
  File5 << fixed << setprecision(5) << "Total run time: " << seconds << "(s) \n";
  File5 << fixed << setprecision(5) << "Average run time: " << Averagetime << "(s) \n";
  File5.close(); 

  /* Create string stream 5 */
  ostringstream String5;
  String5 << "GF%Energies_" << n << "_" << c;  //add number

  /* Output these points */
  ofstream File6 (String5.str().c_str());
  for(i=1;i<b;i++){
    File6 << fixed << setprecision(20) << En[i] << "\n";
  }
  File6.close();

  cout << fixed << setprecision(5) << "Run time: " << seconds << "(s)" << "\n";
  return 0;

}

Aさん、この話題に光を当ててくれてありがとう。

4

2 に答える 2

0

次のようにコンパイルしてみてください:

-mmacosx-version-min=10.6
于 2013-01-10T16:02:31.997 に答える
0

明らかな問題は次の行です。

E[a]=energy;
En[b]=Energy;

ループの反復ごとにaandをインクリメントしますが、それらを固定配列の境界に対してチェックしません。bしたがって、ループの反復回数が多すぎる場合は、配列の外側に書き込みます。

これらを動的配列 ( ) に置き換えたい場合や、またはが大きくなりすぎたstd::vector<double>場合に中止したい場合があります。ab

于 2013-01-10T16:06:15.917 に答える