0

I've started learning graphs theory and was doing a question from Hackerrank https://www.hackerrank.com/challenges/bfsshortreach/problem, which is basically asking to perform a BFS, mark all elements in same level as 6*level and mark all un-reachable nodes as -1. I tried it the following way, I get a seg fault while creating my adjList, am I accessing the input vector<vector<int>> edges in a wrong way? or is it something else. This is my 2-3 bfs code, so I also wanted to know if my implementation is okay, and is it doing what it's supposed to be doing or am I off? (I know the question asks for ans vector to be 1-n not order of visited like it is currently, maybe I could use a map, or a histogram, or a pair with original value and sort it with second later or something, haven't figured that part out) Thank you.

Code:

vector<vector<int>> Graph(vector<vector<int>>& edges) {
    vector<vector<int>> ans;
    for(auto i: edges) {
        ans[i[0]].push_back(i[1]);
        ans[i[1]].push_back(i[0]);
    } return ans;
}

vector<int> bfs(int n, int m, vector<vector<int>>& edges, int s) { // no. of vertex, no. of edges, edges, start
    vector<vector<int>> adjList;
    // adjList.resize(n);
    adjList = Graph(edges);
    vector<int> ans(n + 1);
    vector<bool> visited(n + 1);
    queue<int> q;
    visited[s] = true;
    q.push(s);
    int i = 0;
    while(!q.empty()) {
        int temp = q.front(); q.pop();
        // int len = q.size();
        for(int j: adjList[temp]) {
            if(!visited[j]) {
                ans.push_back(6*i);
                visited[j] = true;
                q.push(j);
            }
        } i++;
    }
    for(int i = 1; i <= n; i++) if(i % 6 != 0 && i != s) ans[i] = -1;
    ans.erase(ans.begin() + s);
    return ans;
}

Tested on

int main() {
    vector<vector<int>> edges = {{1, 2}, {1, 3} };
    vector<int> som = bfs(4, 2, edges, 1);
    return 0;
}
Xgh05t
  • 230
  • 2
  • 11

1 Answers1

0

The vector<vector<int>> ans has to be resized to number of vertices in Graph.

Working code:

vector<vector<int>> Graph(vector<vector<int>>& edges, int n) {
    vector<vector<int>> ans(n);
    for(auto i: edges) {
        ans[i[0]].push_back(i[1]);
        ans[i[1]].push_back(i[0]);
    } return ans;
}

vector<int> bfs(int n, int m, vector<vector<int>>& edges, int s) {
    vector<vector<int>> adjList;
    adjList = Graph(edges, n + 1);
    vector<int> ans(n + 1, -1);
    ans[s] = 0;                          // starting point
    vector<bool> visited(n + 1);
    queue<int> q;
    visited[s] = true;
    q.push(s);
    while(!q.empty()) {
        int temp = q.front(); q.pop();
        for(int i: adjList[temp]) {
            if(!visited[i]) {
                ans[i] = 6 + ans[temp];   // just use it as DP array!
                visited[i] = true;
                q.push(i);
            }
        }
    }
    ans.erase(ans.begin() + s); // remove starting point(as per question)
    ans.erase(ans.begin());     // remove 0 (graph starts from 1)
    return ans;
}
Xgh05t
  • 230
  • 2
  • 11
  • *vector don't require this* -- You are looking at this in a much more complicated way than need be. Look at your code: `vector ans(n + 1);` -- That creates `n + 1` entries in the vector. If you had just `vector ans;` then you indeed need to size the vector appropriately. – PaulMcKenzie Jan 21 '20 at 15:31
  • That was just because I knew it's length beforehand, not that I didn't in the other case, but I mean it would've handled the case especially if I used ```push_back()``` and I think it's fine with ```[]``` operator too, but maybe it's not, not too confident about that. – Xgh05t Jan 21 '20 at 15:35
  • Again, you're overcomplicating things. All `operator [ ]` does is **access** the element at the position. It doesn't resize anything. The functions that resizes a vector are `push_back`, `pop_back`, `resize`, `insert`, `erase`, and maybe a couple I forgot. In addition a vector can be constructed with the number of elements. – PaulMcKenzie Jan 21 '20 at 15:36
  • Okay I think I understand, I have predominantly used index based loops for building or creating vectors, arrays and iterators won't do that unless you don't provide a length. And when I say ```[]``` I meant using a while loop of unknown length, creating an empty, length not declared vector and filling it, I know you can perform ```push_back``` in those situations, still not sure about using ```[]``` maybe I've done it, I should avoid it is what I'm realizing now, regardless of whether you even can. – Xgh05t Jan 21 '20 at 15:52