Starting in the middle of a grid and tracking random movement

I am currently writing a program that will start in the middle of a grid that you determine the size of. I need to track the movement that will be at random. I am currently having issues getting the grid to show the movement and actually doing a random movement. When it does a "randomizer" it doesn't switch between the y and x axis.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
#include <iostream>
#include <vector>
#include <cstdlib>
#include <sstream>

using namespace std;
struct point{
    int x;
    int y;
    int timesVisited;
    int negx;
    int negy;
} randim, randum, starther;
//this is the function to produce a random "movement" on the grid
point randomStep(){

    srand(time(0));
    while(( randim.x == 0) and ( randim.y == 0)){
        randim.x = rand()%3 - 1;
        randim.y = rand()%3 - 1;
    }

    if((randim.x > 0) or (randim.x < 0)){
        randim.y = 0;
    }
    if((randim.y > 0) or (randim.y < 0)){
        randim.x = 0;
    }

    return randim;
}
//determines if the point to move to is in the grid
bool inLimits(point L, point Bound){
    bool answer = true;
//while((randim.x <= Bound.x) and (randim.y < Bound.y) and (randim.x >= Bound.negx) and (randim.y >= Bound.negy)){
if (randim.x > 0)
        if( randim.x > Bound.x){
        randomStep();
}
if(randim.y > 0)
    if( randim.y > Bound.y){
        randomStep();
}
if(randim.x < 0)
    if(randim.x < Bound.negx){
        randomStep();
}
if (randim.y < 0)
    if(randim.y < Bound.negy){
        randomStep();
}


}
//adds the randomized point to the current location
point addPoint( point p, point q){
    p.x = p.x + q.x;
    p.y = p.y + q.y;
    p.timesVisited = p.timesVisited + 1;

    return p;
}
//makes the grid
string VecToString(vector<vector<int>> vec,int blockNum){
    stringstream sout;
    starther.x = blockNum / 2;
    starther.y = blockNum / 2;
    for(int i = 0; i < vec.size(); ++i){
        for(int j = 0; j < vec[i].size(); ++j){
            sout << vec[j][i] << " ";
        vec[starther.x][starther.y]=starther.timesVisited;
        }
        sout << endl;
    }
    return sout.str();
}

int main(){
    srand(time(0));

    //use the rand() function to create a random integer
    //      by using the mod operator randy will be between
    //      0 and 3.
    int randy = rand()%4;

    cout << randy << endl;
    int blocksNum = 0;
    int simMinutes = 0;
    cout << "Please enter the number of blocks in the city: ";
    cin >> blocksNum;
    cout << "Please enter the number of mintes to simulate: ";
    cin >> simMinutes;
//setting up the vector for the block visual
    vector<int> row (blocksNum,0);
 vector<vector<int>> vec (blocksNum, row);
//sets the bounds
    point Bounds;
    Bounds.x = blocksNum;
    Bounds.y = blocksNum;
    Bounds.negx = blocksNum * -1;
    Bounds.negy = blocksNum * -1;

for(int i = 0; i < simMinutes; i++){
randomStep();
starther = addPoint(starther,randim);
inLimits(starther,Bounds);
}

  cout << VecToString(vec,blocksNum);
    cout << endl;

    return 0;

}
1. You never return a value in your bool inLimits(point L, point Bound) function. Needs to return a bool.

2. Only call srand(time(NULL)) *once* per program, preferably in main(). Delete the srand call in randomStep().

Might be other problems as well, but that's a good start

if((randim.x > 0) or (randim.x < 0)){
Are you sure this is doing what you want it to do?
You do realize this is the same thing as saying if (randim.x != 0) {...}, right? Just seems more complicated than necessary.
Last edited on
I decided to do the inLimits last for the sake of keeping the headache off. As of right now I am trying to get the grid to show where the "point" is and has been.
You could also try to create a struct where to save all your relevant information, like the already visited positions on the grid.

Example (not optimised and untidy - also, no check performed):
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
#include <chrono>
#include <iomanip>
#include <iostream>
#include <limits>
#include <random>
#include <sstream>
#include <string>
#include <vector>

struct PosOnScreen {
    char empty,
         filled,
         current;
    int visited;

    PosOnScreen() : empty { '.' }, filled { '*' }, current { empty }, visited { 0 } {}

    friend std::ostream& operator<<(std::ostream& os, const PosOnScreen& rhs)
    { return os << rhs.current; }
};

struct Point {
    int x, // columns
        y; // rows
    Point() : x {}, y {} {}
    Point(int x_arg, int y_arg) : x {x_arg}, y {y_arg} {}
};

void displayGrid(const std::vector<std::vector<PosOnScreen>>& v);
void displayVisitedGrid(const std::vector<std::vector<PosOnScreen>>& v);
void waitForEnter();

int main()
{
    std::cout << "What are the dimensions of the grid (rows x columns)?\n"
                 "Please type 2 numbers and press ENTER: ";
    std::string line;
    std::getline(std::cin, line);
    std::istringstream iss(line);
    int rows {}, cols{};
    iss >> rows >> cols;
    std::vector<std::vector<PosOnScreen>> grid(rows, std::vector<PosOnScreen>(cols));

    std::mt19937 rng(std::chrono::high_resolution_clock::now().time_since_epoch().count());
    std::uniform_int_distribution<> rrow(0, rows-1);
    std::uniform_int_distribution<> rcol(0, cols-1);
    
    // Decide initial position:
    Point pos { rcol(rng), rrow(rng) };
    grid.at(pos.y).at(pos.x).current = grid.at(pos.y).at(pos.x).filled;
    grid.at(pos.y).at(pos.x).visited++;
    displayGrid(grid);

    std::cout << "\nHow many movements do you want to simulate? ";
    std::getline(std::cin, line);
    iss.clear();
    iss.str(line);
    int moves {};
    iss >> moves;

    for(int i{}; i<moves; ++i) {
        grid.at(pos.y).at(pos.x).current = grid.at(pos.y).at(pos.x).empty;
        pos.x = rcol(rng);
        pos.y = rrow(rng);
        grid.at(pos.y).at(pos.x).current = grid.at(pos.y).at(pos.x).filled;
        grid.at(pos.y).at(pos.x).visited++;
        // Uncomment the following lines to check every movement
        // displayGrid(grid);
        // waitForEnter();
    }

    displayVisitedGrid(grid);

    waitForEnter();
    return 0;
}

void displayGrid(const std::vector<std::vector<PosOnScreen>>& v)
{
    for(const auto& ve : v) {
        for(const auto& p : ve) { std::cout << p; }
        std::cout << '\n';
    }
}

void displayVisitedGrid(const std::vector<std::vector<PosOnScreen>>& v)
{
    for(const auto& ve : v) {
        for(const auto& p : ve) { std::cout << std::setw(4) << p.visited; }
        std::cout << '\n';
    }
}

void waitForEnter()
{
    std::cout << "\nPress ENTER to continue...\n";
    std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
}

Output:
What are the dimensions of the grid (rows x columns)?
Please type 2 numbers and press ENTER: 15 25
.........................
.........................
.........................
.........................
.........................
.........................
.........................
.........................
.........................
.........................
.*.......................
.........................
.........................
.........................
.........................

How many movements do you want to simulate? 1000
   1   3   2   1   4   1   1   5   2   4   4   4   1   1   4   4   3   1   2   1   2   2   6   5   0
   2   2   2   3   6   4   1   3   3   0   4   1   3   1   3   1   2   1   5   2   3   0   2   2   5
   5   4   3   3   2   2   1   1   1   5   4   2   1   2   4   1   5   2   1   2   1   2   3   2   1
   3   4   4   4   1   1   1   3   1   5   2   1   6   1   3   0   3   4   5   0   3   3   2   3   3
   4   3   3   1   1   6   2   4   2   3   3   3   2   2   3   8   2   1   2   5   2   2   4   5   6
   0   3   3   1   1   5   2   0   4   2   2   3   7   6   1   5   3   3   2   2   2   3   5   5   5
   5   4   5   0   2   3   4   3   1   5   3   3   2   2   5   2   1   1   1   0   1   4   2   0   5
   0   2   1   1   1   5   2   1   3   1   2   1   4   1   1   3   4   2   6   2   3   3   1   0   3
   3   2   2   4   0   6   3   4   0   2   2   3   1   1   2   2   4   3   5   7   1   2   4   4   1
   6   3   6   1   1   2   1   2   2   2   3   6   1   5   2   2   4   5   3   6   4   1   1   1   2
   2   4   7   1   7   3   4   2   4   1   2   3   3   3   3   5   2   3   3   2   1   6   3   3   0
   4   1   3   4   3   3   0   4   1   2   2   3   5   1   4   5   1   1   6   2   4   2   5   4   5
   1   3   8   3   1   1   5   4   2   7   5   4   2   2   2   3   1   3   3   4   4   2   2   4   5
   2   4   0   2   1   2   2   2   0   2   2   4   1   1   5   4   1   0   2   2   3   3   2   3   1
   2   1   3   3   1   2   2   3   1   2   3   4   1   1   1   1   2   1   6   2   2   2   2   4   3

Press ENTER to continue...

Thank yall for the assistance, I have got the code to work and I will post it here for any others that may need it in the future.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
#include <iostream>
#include <iomanip>
#include <vector>
#include <cstdlib>
#include <sstream>

using namespace std;
struct point{
    int x;
    int y;
    int timesVisited;
};
//determines the next movement at random
point randomStep(){
    int rands = rand()%2;
    point ranher;
    ranher.x = 0;
    ranher.y = 0;
    if(rands == 0){
        ranher.x = rand()%3-1;
    }else if(rands == 1){
        ranher.y = rand()%3-1;
    }
    return ranher;
}

//determines if the next movement is in bounds
bool inLimits(point Loc, point bound){
    if((Loc.x >= bound.x) or (Loc.y >= bound.y) or (Loc.x < 0) or (Loc.y < 0)){
        return false;
    }else{
        return true;
    }

}
//adds the random movement to the current point
point addPoint( point pos, point ran){

    pos.x = pos.x + ran.x;
    pos.y = pos.y + ran.y;


    return pos;
}

//makes the grid
string VecToString(vector<vector<int>> vec){
    stringstream sout;
    for(int i = 0; i < vec.size(); ++i){
        for(int j = 0; j < vec[i].size(); ++j){
            if(vec[j][i] == 0){
                sout << setw(3) << '.' << " ";
            }else{
                sout << setw(3) << vec[j][i]  << " ";
            }
        }
        sout << endl;
    }
    return sout.str();
}

int main(){
    srand(time(0));
    //use the rand() function to create a random integer
    //      by using the mod operator randy will be between
    //      0 and 3.
    point bounds;
    int blocksNumber = 0;
    int simulationMinutes = 0;
    cout << "Please enter the number of blocks in the city: ";
    cin >> blocksNumber;
    cout << "Please enter the number of mintes to simulate: ";
    cin >> simulationMinutes;
    //determines the position
    point student={blocksNumber-1};
    student.y = blocksNumber - 1;
    bounds.x = blocksNumber * 2;
    bounds.y = blocksNumber * 2;
    point move;
    //setting up the vector for the block visual
    vector<int> row (blocksNumber*2);
    vector<vector<int>> vec (blocksNumber*2, row);
    //adds the amount of times visited to the grid
    for(int i = 0; i < simulationMinutes; i++){
        move = addPoint(student,randomStep());
        if(inLimits(move,bounds)){
            ++vec[student.x][student.y];
            student = move;
        }else {
            ++vec[student.x][student.y];
  }


    }
    cout << VecToString(vec);
    cout << endl;

    return 0;

}
Topic archived. No new replies allowed.