2016-03-06 1 views
1

Je suis encore un débutant en programmation. J'écris un programme de 2D Snell's Law. Je sais que le problème peut provenir de mauvaises localisations dans Xcode, mais j'écris uniquement en C++ et g ++ me donne même une erreur de segmentation après une compilation réussie.Impossible de générer le désassemblage pour la pile car l'URL ne peut pas être traduite & Erreur de segmentation: 11

Voici mon code pour la fonction principale:

#include <string> 

#include "Snell.hpp" 

int main(int argc, const char * argv[]){//thread 1 exc_bad_access (code=2 address=0x7fff5f238304) 
    string filename; 
    double time; 
    Snell S[3600]; 

    for (int i=1; i<=1; i++) { 
     while (S[i].angle_tr>0) { 
      filename="VPVSMOD"+to_string(i)+".txt"; 
      S[i].Open(filename); 
      time=S[i].Locate(i); 
      cout<<"The "<<i<<"th event takes "<<time<<" seconds to reach the destination"<<endl; 
      S[i].angle_tr-=0.01; 
     } 
    } 

    return 0; 
} 

Voici le code pour Snell.hpp

#ifndef Snell_hpp 
#define Snell_hpp 

#include <iostream> 
#include <fstream> 
#include <sstream> 
#include <iomanip> 
#include <string> 
#include <algorithm> 
#include <cmath> 

using namespace std; 

class Snell{ 
private: 
    double GetV(double lat,double dep); 
    int ny,nz,time; 
    double la[30],h[20],v[10][30]; 
    double lat,alt,step; 
public: 
    Snell(); 
    void Open(string filename); 
    double Locate(int i); 
    double angle_tr; 
}; 

#endif /* Snell_hpp */ 

et Snell.cpp:

#include "Snell.hpp" 

Snell::Snell(){ 
    ny=1,nz=3,time=0; 
    lat=0,alt=0,step=1; 
    angle_tr=M_PI/2; 
} 

void Snell::Open(string filename){ 
    ifstream fin(filename); 
    stringstream ss; 
    string str,tok; 

    for (int i=0; i<nz; i++) { 
     (getline(fin, str)); 
     ss.str(str); 
     for (int j=0; j<ny; j++) { 
      getline(ss, tok, ','); 
      v[i][j]=stod(tok); 
      cout<<v[i][j]<<",i="<<i<<",j="<<j<<endl; 
     } 
     ss.clear(); 
    } 

    fin.close(); 
    angle_tr=v[1][0]/v[0][0]; 
} 

double Snell::GetV(double lat, double dep){ 
    int index_la = 0,index_dep = 0; 

    index_dep=round(dep); 
    return (v[index_dep][index_la]+v[index_dep+1][index_la])/2; 
} 

double Snell::Locate(int i){ 
    string filename; 
    double count_t=0; 
    double latt=lat,altt=alt,step_altt_all=0,angle=0,angle_p=0; 
    double vsy,vsz; 
    double vs,vs_n; 
    ofstream fout; 
     angle=M_PI/2-atan(angle_tr); 
     vs=GetV(lat, alt); 

     filename="Test"+to_string(i)+"_"+to_string(time)+".txt"; 
     fout.open(filename,ios::out); 
     fout<<lat<<","<<alt<<endl; 

     while (altt!=2) { 
      //cout<<"Compute Velocity in each dimension"<<endl; 
      angle_p=angle; 
      vsy=vs*cos(angle); 
      vsz=vs*sin(angle); 
      //cout<<"Check Velocity"<<endl; 
      if (vsy==0||vsz==0) { 
       break; 
      } 

      //cout<<"Compute reflection point"<<endl; 
      step_altt_all=step/vsz; 
      count_t=count_t+step/vsz;//time plus one 
      latt=latt+vsy*(step_altt_all); 
      step_altt_all=0; 
      altt=altt+step; 

      //cout<<"Compute New Velocity"<<endl;  
      vs_n=GetV(latt,altt); 
      if ((vs_n*cos(angle)/vs)>1) { 
       break; 
      } 
      else{ 
       angle=M_PI/2-asin(vs_n*cos(angle)/vs); 
       vs=vs_n; 
       if (angle!=angle_p) 
        fout<</*"position:"<<*/latt<<","<<altt<<endl; 
      } 
     } 

     fout.close(); 
     filename="Result"+to_string(i)+"_"+to_string(time)+".txt"; 
     fout.open(filename); 
     fout<<0<<" "<<latt<<" "<<altt<<" "<<step<<endl; 
     fout.close(); 
     return count_t; 
} 

Répondre

1

Je pense immédiate est : Vous devez avoir soufflé votre pile. S'il vous plaît voir why is stack memory size so limited?

.... Et oui, sur ma plate-forme, je pense ... était correcte

Reproduire votre programme, mais la modification de votre main.cpp ...

int main(int argc, const char * argv[]){//thread 1 exc_bad_access (code=2 address=0x7fff5f238304) 
    string filename; 
    double time; 
    //Snell S[3600]; 
    std::cout << sizeof(Snell) << " bytes" << std::endl; 

    return 0; 
} 

Il donne une sortie de

2848 bytes 

.... Et vous essayez d'allouer 3600 d'entre eux ... ~ 10MB !! La solution à cela est de l'allouer sur le tas en utilisant un std::unique_ptr ou mieux encore, votre bon ami, std::vector.

Modifier votre principal à cette

#include <string> 
#include <memory> 
//or #include <vector> 

#include "Snell.hpp" 

int main(int argc, const char * argv[]){//thread 1 exc_bad_access (code=2 address=0x7fff5f238304) 
    string filename; 
    double time; 
    std::unique_ptr<S[]> p(new Snell[3600]); 
    //or std::vector<Snell> S(3600); 

    for (int i=1; i<=1; i++) { 
     while (S[i].angle_tr>0) { 
      filename="VPVSMOD"+to_string(i)+".txt"; 
      S[i].Open(filename); 
      time=S[i].Locate(i); 
      cout<<"The "<<i<<"th event takes "<<time<<" seconds to reach the destination"<<endl; 
      S[i].angle_tr-=0.01; 
     } 
    } 

    return 0; 
} 
+0

Merci pour votre aide précédente. Maintenant, j'ai une autre question: Pourquoi est-ce que ça va planter juste 10Mo au total? – dinex