Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Assigning values to objects in C++

Tags:

c++

I can be considered a beginner in programming. I am trying to write a class in C++ that can hold multi-dimensional data (such as an MxN matrix). I don't want to do it via the way of vector of a vector. I wrote the following piece of code, but when I compile it with g++, I get the segmentation fault: 11 error. When I try to compile it with Xcode on the other hand, it gives "Thread 1: EXC_BAD_ACCESS (code = 1, address = 0x0)" at the line

particles[i].x = x0 + R*cos(theta*i);

So, I guess I'm getting a sort of memory error related to assigning objects a value.

Is this kind of syntax even allowed in C++:

particles_old[i].x = particles[i].x;

Or can I something like this:

// say A is a class with x a vector this time, instead of a double data. 
// in nested for loops
vector<A> B;
B[i].x[j] = some value;

I know it's a bit vague, but is it at least correct from a syntax point of view?

#include <iostream>
#include <cmath>
#include <fstream>
#include <string>
#include <vector>
#include <random>
using namespace std;

class Particle{
public:
    double x; // x position
    double y; // y position
    double vx; // velocity in the x direction
    double vy; // velocity in the y direction
    double Fx; // force in the x direction
    double Fy; // force in the y direction

    // Default constructor
    Particle()
    : x(0.0),y(0.0),vx(0.0),vy(0.0),Fx(0.0),Fy(0.0){
    }
};

int main() {

    const float pi = 3.14;
    int N = 30; // Number of 'particles' that make up the cell
    float theta = 2*pi/N; // Angle between two particles in radians
    float x0 = 0; // Center of the cell [x]
    float y0 = 0; // Center of the cell [y]
    float R = 5e-6; // Radius of the cell
    vector<Particle> particles; // particles

    // Assigning the initial points onto the circle
    for(int i = 0; i < N; i++) {
        particles[i].x = x0 + R*cos(theta*i);
        particles[i].y = y0 + R*sin(theta*i);
    }

    float k = 4.3e-7; // Spring constant connecting the particles
    float m = 2e-8; // Mass of the particles

    // Calculating the initial spring force between the particles on the cell
    particles[0].Fx = -k*(particles[1].x - particles[N].x);
    particles[0].Fy = -k*(particles[1].y - particles[N].y);
    for(int i = 1; i < N-1; i++) {
        particles[i].Fx = -k*(particles[i+1].x - particles[i-1].x);
        particles[i].Fy = -k*(particles[i+1].y - particles[i-1].y);
    }
    particles[N].Fx = -k*(particles[0].x - particles[N-1].x);
    particles[N].Fy = -k*(particles[0].y - particles[N-1].y);

    // Initial velocities are given to each particle randomly from a Gaussian distribution
    random_device rdx; // Seed
    default_random_engine generatorx(rdx()); // Default random number generator
    random_device rdy; // Seed
    default_random_engine generatory(rdy()); // Default random number generator
    normal_distribution<float> distributionx(0,1); // Gaussian distribution with 0 mean and 1 variance
    normal_distribution<float> distributiony(0,1); // Gaussian distribution with 0 mean and 1 variance
    for(int i = 0; i < N; i++) {
        float xnumber = distributionx(generatorx);
        float ynumber = distributiony(generatory);
        particles[i].vx = xnumber;
        particles[i].vy = ynumber;
    }


    // Molecular dynamics simulation with velocity Verlet algorithm

    // 'Old' variables
    vector<Particle> particles_old;

    for(int i = 0; i < N; i++) {
        particles_old[i].x = particles[i].x;
        particles_old[i].y = particles[i].y;
        particles_old[i].vx = particles[i].vx;
        particles_old[i].vy = particles[i].vy;
        particles_old[i].Fx = particles[i].Fx;
        particles_old[i].Fy = particles[i].Fy;
    }

    // Sampling variables
    int sampleFreq = 2;
    int sampleCounter = 0;

    // MD variables
    float dt = 1e-7;
    float dt2 = dt*dt;
    float m2 = 2*m;
    int MdS = 1e+4; // Molecular dynamics step number

    // MD
    for(int j = 0; j < MdS; j++) {

        // Update x
        for(int i = 0; i < N; i++) {
            particles[i].x = particles_old[i].x + dt*particles_old[i].vx + dt2*particles_old[i].Fx/m2;
            particles[i].y = particles_old[i].y + dt*particles_old[i].vy + dt2*particles_old[i].Fy/m2;
        }

        // Update F
        particles[0].Fx = -k*(particles[1].x - particles[N].x);
        particles[0].Fy = -k*(particles[1].y - particles[N].y);
        for(int i = 1; i < N-1; i++) {
            particles[i].Fx = -k*(particles[i+1].x - particles[i-1].x);
            particles[i].Fy = -k*(particles[i+1].y - particles[i-1].y);
        }
        particles[N].Fx = -k*(particles[0].x - particles[N-1].x);
        particles[N].Fy = -k*(particles[0].y - particles[N-1].y);

        // Update v
        for(int i = 0; i < N; i++) {
            particles[i].vx = particles_old[i].vx + dt*(particles_old[i].Fx + particles[i].Fx)/m2;
            particles[i].vy = particles_old[i].vy + dt*(particles_old[i].Fy + particles[i].Fy)/m2;
        }

        // Copy new variables to old variables
        for(int i = 0; i < N; i++) {
            particles_old[i].x = particles[i].x;
            particles_old[i].y = particles[i].y;
            particles_old[i].vx = particles[i].vx;
            particles_old[i].vy = particles[i].vy;
            particles_old[i].Fx = particles[i].Fx;
            particles_old[i].Fy = particles[i].Fy;
        }

    }

}

Thanks in advance.

like image 761
melampyge Avatar asked Aug 07 '26 22:08

melampyge


1 Answers

You have already two excellent answers. Here is another variant:

If you know in advance the size of your vector, you may as well define it as follows:

vector<Particle> particles(N);  // create a vector with N particles default initialized. 

The rest of your code should then work, because particles[i] will refer to a particle that already exists.

And yes, old_particles = particles; will copy the whole vector. No need to copyelement by element in atedious loop.

like image 144
Christophe Avatar answered Aug 10 '26 12:08

Christophe



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!