我遇到了段错误,当我调试它时,我收到以下消息:
无法访问内存0x806d128
我试图在那里设置一个观察点来监控地址,但gdb给我的响应是:
无法观看常数值'0x806d128'
然而,当我打印包含地址的指针时,它识别出我存储在那里的结构:
(正文*)0x806d128
根据gdb,addForce()
发生了错误,这有点奇怪,因为init()
以下是相关代码:
#include <math.h>
#include <stdlib.h>
#include <stdio.h>
#include <time.h>
#define prec float
prec gdt = 0.0001;
typedef struct {
float Fx, Fy, vx, vy, mass;
int posX, posY;
} body;
void addForce(body* a, body* b){
int xa=(*a).posX, ya=(*a).posY;
int xb=(*b).posX, yb=(*b).posY;
float F=(*a).mass * (*b).mass * gdt /(pow(xa-xb, 2)+pow(ya-yb, 2));
float v=atan((ya-yb)/(xa-xb));
float Fx=cos(v)/F, Fy=sin(v)/F;
(*a).Fx+=Fx;
(*a).Fy+=Fy;
(*b).Fx-=Fx;
(*b).Fy-=Fy;
}
int newRandInt(int bot, int top){
return bot + (rand() % (top++));
}
prec newRand()
{
prec r = (prec)((double)rand()/(double)RAND_MAX);
return r;
}
void init(int N, body* star){
for(int i=0; i<N;i++){
star[i].posX = newRandInt(0, 800);
star[i].posY = newRandInt(0, 800);
star[i].Fx = newRand();
star[i].Fy = newRand();
star[i].vx = newRand();
star[i].vy = newRand();
star[i].mass = newRand();
}
}
int main(int argc, char* argv[]) {
int N = 200;
body* stars = malloc(sizeof(body)*N);
init(N, stars);
for(int j1=0; j1<N; j1++){
for(int j2=0; j2<N-1; j2++){
if(j1!=j2){
addForce(stars+sizeof(body)*j1, stars+sizeof(body)*j2);
}
}
}
return 0;
}
答案 0 :(得分:0)
此addForce
的来电不符合您的要求:
addForce(stars+sizeof(body)*j1, stars+sizeof(body)*j2);
您不希望此sizeof(body)
调用中的addForce
表达式。你可能想要的电话是:
addForce(stars+j1, stars+j2);
stars
是body
的数组,因此您可以使用
body *p = &stars[i]
或只是
body *p = stars + i
这两个都有类型主体*
答案 1 :(得分:0)
在这一行:
addForce(stars+sizeof(body)*j1, stars+sizeof(body)*j2);
当你执行sizeof(body)
时,它会以字节为单位计算结构大小,然后乘以j1
。所以你有some_nr*j1
这个值是added
到星星,它是指向身体的指针
指针算术评估some_nr*j1*sizeof(pointer to body)
你想要做的只是stars+j1
,它将被正确评估为指向body的指针并添加到数组中
同样的事情发生在addForce的第二部分。
你错过的是使用指针算术,重新计算'+'运算符的第二个操作数以匹配指针的大小。