C++ Array of Array Products :exited, segmentation fault - c++

I am a newbie in cpp field.
Below is my cpp code. When I use the online c++ compiler, and
why does it happened to exited, segmentation fault, and what's wrong with my code.
Thanks guys.
Problem description:
Given an array of integers arr, you’re asked to calculate for each index i the product of all integers except the integer at that index (i.e. except arr[i]). Implement a function arrayOfArrayProducts that takes an array of integers and returns an array of the products.
Solve without using division and analyze your solution’s time and space complexities.
#include <iostream>
#include <vector>
using namespace std;
vector<long> arrayOfArrayProducts(const vector<int>& arr)
{
vector<long> res = {};
int n = arr.size();
// handles edge cases as well
if(n==0 || n==1){
return res;
}
int product;
// your code goes here
for(int i=0; i<n; i++){
product = 1;
for(int j=0; j<n; j++){
if(i!=j){
product = arr[j]*product;
}
res[i]=product;
}
}
return res;
}
int main() {
// vector initiallize
//vector<int> arr{8, 10, 2};
const vector<int> arr;
int n = arr.size();
vector<long> ans(n,0);
ans = arrayOfArrayProducts(arr);
for(int i=0; i<n; i++){
cout<< ans[i] <<' ';
}
return 0;
}

Here is the line where the failure comes:
res[i] = product;
and the reason is because you declared res like this:
vector<long> res = {};
so you are trying to access the long element located at 'cell' i of an empty vector... that is not allowed in C++ and the result is undefined behavior
fix it:
the same way as in the main function
std::vector<long> arrayOfArrayProducts(const std::vector<int>& arr)
{
int n = arr.size();
std::vector<long> res(n, 0);
....

Segmentation faults typically occur when you try to read past the bounds of an array. This fault in your code means that you're trying to read/ write something from an array which is not allocated. If you take a closer look, res[i]=product means that your accessing elements from the vector res. But you haven't reallocated or inserted data into it. This is the reason for the segmentation fault.
To resolve this, resize the res vector to the size of arr so that the vector will have the elements in memory to be accessed,
vector<long> arrayOfArrayProducts(const vector<int>& arr)
{
vector<long> res(srr.size());
...

You are getting this error because you are trying to access the index i of the vector<int> res that you never initialized. on this line:
res[i] = product;
For that you have to understand how Vector works, Vector is dynamic container which can shrink and expand based on its usage, in your case, You Initialized it with default constructor, which did not allocated any memory to hold int. So when you try to access that you get undefined behavior.
In case of default construction of vector. You cannot assign to a particular index. but you have can put data in it via this:
res.push_back(data);
You can fix it by using these constructors:
std::vector<int> res(arr.size(), 0); // In second parameter you can pass default values for all the elements in the vector.
std::vector<int> res(arr.size()); //This will simply initialize elements with default constructor

Related

vector push_back memory access denied in Visual Studio

#include <stdio.h>
#include <vector>
using namespace std;
int main()
{
vector<int> numbers;
numbers.resize(10001);
for (int i = 0; i < 10000; i++)
{
numbers.push_back(1);
}
return 0;
}
If I put more than 5000 1s in the vector, I get the following error, I don't understand.
There is no doubt about it other than the memory overflow. But int type = 4 bytes, so 4byte * 10000 = 40000byte 0.04mb
Why am I getting an error?
The error seems unrelated to the code that you've shown.
Now, looking at your code there is no need to use resize and then using push_back as you can directly create a vector of size 10001 with elements initialized to 1 as shown below:
std::vector<int> numbers(10001,1);// create vector of size 10001 with elements initialized to 1
Or you can used std::vector::reserve instead of std::vector::resize, though this is totally unnecessary as you can use the first method shown above.
vector<int> numbers;
numbers.reserve(10001); //use reserve instead of resize
for (int i = 0; i < 10000; i++)
{
numbers.push_back(1);
}

Using vectors in C++ program is not printing anything

I have written a C++ program to find fibonacci numbers. It's running successfully but is not printing anything.
#include<bits/stdc++.h>
using namespace std;
int main(){
int n = 5;
vector<int> fib;
fib[0] = 0;
fib[1] = 1;
for (int i = 2; i <= n; i++){
fib[i] = fib[i-1] + fib[i-2];
}
cout<<fib[n];
}
If I do the same thing using array instead of vector it prints successfully.
#include<bits/stdc++.h>
using namespace std;
int main(){
int n = 5;
int fib[10];
fib[0] = 0;
fib[1] = 1;
for (int i = 2; i <= n; i++){
fib[i] = fib[i-1] + fib[i-2];
}
cout<<fib[n];
}
I have tested this on sublime text and onlinegdb.
int fib[10];
This creates an array of 10 integers.
vector<int> fib;
This creates a vector of size 0, with 0 integers.
For these two snippets to match, you need to initialize the vector with 10 integers like the array. So:
vector<int> fib(10);
Some notes on vectors
One of the big differences between std::vector and primitive arrays is that std::vector is resizable! So while initializing the vector with 10 ints like above will work, you could also add them on the fly using push_back() or by calling resize().
Likewise, std::vector has a .at() function for access. It's marginally slower than the subscript operator ([]), so I would not suggest using it in production-level code. But while you're learning, I would strongly suggest using .at(), as it will do bounds checking for you. So this program would've told you you were trying to access locations in the vector that don't exist--instead of just running with Undefined Behavior.
Note that when you wrote :
vector<int> fib;//creates an empty vector that is a vector of size 0
fib[0] = 0; //UNDEFINED BEHAVIOR
fib[1] = 1; //UNDEFINED BEHAVIOR
In the above code snippet, you created an empty std::vector. That is a vector of size 0.
Next when you wrote fib[0] = 0; you're trying access the first element of the vector. That is, the element at index 0. But note that there is no element inside the vector and so you have undefined behavior in your program.
Similarly when you wrote fib[1] = 1;, you're trying to access the second element of the vector. But since there is no element inside the vector, this again leads to undefined behavior.
To solve this you can create a vector of some size(say 10) and then access its elements as shown below:
vector<int> fib(10);//create vector of size 10
fib[0] = 0;//OK NOW
fib[1] = 1;//OK NOW
Since you're using indices to access the elements of the vector, i have not suggested push_back. std::vector::push_back is a member function that can be used to add an element into the vector.

What's the difference between vector<vector<int>> vec and vector<vector<int>> vec(n)? [duplicate]

This question already has answers here:
Why does my vector print out all zeroes?
(4 answers)
Closed 1 year ago.
I was trying to access vector elements today, so when I used vector<vector<int>> vec and then added elements to it. I was able to access those elements like vec[1][2].
But when I use vector<vector<int>> vec(n) and then added elements, I was not able to access the elements using vec[1][2]. I keep getting a segmentation error. Does anyone know what am I missing here?
I am adding the elements to the vector through with the help of the below code snippet.
int n;
cin >> n;
vector<vector<int>> vh;
int size, input;
for (int i = 0; i < n; i++)
{
vector<int> temp;
cin >> size;
for (int j = 0; j < size; j++)
{
cin >> input;
temp.push_back(input);
}
vh.push_back(temp);
}
I think I can guess what the problems is...
When you use the constructor with an argument:
vector<vector<int>> vh(n);
you create a vector with the size n, it means it will already have n elements, where each element will be a default-constructed vector<int>. Which means that each vector will be empty.
Then you push back a new vector:
vh.push_back(temp);
This will increase the size of the vector. After one such push_back call the size of vh will be n + 1. The new vector you add will be at index n, i.e. vh[n] is the new vector.
If you set the size when you define the vector, then you need to use indexing and assignment to set the sub-vectors:
vh[i] = temp;
To summarize:
Either you create an empty vector and push back new elements:
vector<vector<int>> vh;
and
vh.push_back(temp);
Or you create a vector with a size, and use indexing and assignment:
vector<vector<int>> vh(n);
and
v[i] = temp;
Don't mix these ways.
Now when you got your current code working (hopefully) and understand how these things work a little better, it's time to show a way how to do your code in a more "C++-ish" way... :)
// The first part is much like your current code
size_t n;
std::cin >> n;
std::vector<std::vector<int>> vh(n);
// Now iterate over all the elements in the vector
for (auto& v : vh)
{
// Get the size of the current sub-vector
size_t size;
std::cin >> size;
// Create the vector with size elements
v = std::vector<int>(size);
// Read size integers into the vector
std::copy_n(std::istream_iterator<int>(std::cin), size, begin(v));
}

Why I can't input into my std::vector in C++

I'm a newbie in C++. I've just learnt about vector in STL.
However, when I tried to input an integer into my vector:
vector<int> v;
cin>>v[i]
The program returned segmentation fault. Please help me out.
Your vector doesn't have any elements in it, so the internal array is null. When you try to read something into it, you're trying to deference a null pointer (resulting in the segfault). Add elements to the vector first:
vector<int> v(100); //Create vector with 100 elements
for(int i = 0; i < 100; i++) {
cin >> v[i];
}
Alternatively, you could read elements into a local variable, then add them into the vector:
vector<int> v;
for(int i = 0; i < 100; i++) {
int new_val;
cin >> new_val;
v.push_back(new_val);
}

pushback data from vector to vector of map

i have created a map called select_p and vector of this map is called pts. i have stored data in a array and i want to pushbcak these data into my vector of map. i tried this by inserting value of array into new vector and then pushback into my map.but it is not working please help me to correct these codes? thanks
#include<iostream>
#include<cstdlib>
#include <map>
#include <vector>
using namespace std;
int main()
{
int M=7;
int N=6;
int i=0;
int * temp;
map<int,vector<int> > select_p;
vector<int>pts;
for (int m=0; m<M; m++)
{
for (int n=0; n<N; n++)
{
vector<int>id;
if (n==0 && m==5)
{
temp = new int[3,i+N,i+N+1,i+1];
unsigned ArraySize = sizeof(temp) / sizeof(int);
id.insert(id.begin(),temp[0], temp[ArraySize]);
select_p[i].push_back(id);
}
i++;
}
}
delete[] temp;
system("PAUSE");
return 0;
}
for (int m=0; m<M; m++) {
for (int n=0; n<N; n++) {
if (n==0 && m==5) {
Why are you looping when you only actually do anything for a single pair of values of m and n? The loops are completely useless here; you would get the same effect by just setting n = 0 and m = 5.
temp = new int[3,i+N,i+N+1,i+1];
Whatever you think this does, that's not what it does. This is equivalent to temp = new int[i+1];. The rest of the expression inside of the [] has no effect.
That said, you should not use new to create arrays in your program. Use std::vector; it is far easier to use correctly.
unsigned ArraySize = sizeof(temp) / sizeof(int);
This does not work. When you dynamically allocate an array, you are responsible for keeping track of how many elements are in it. Given a pointer to a dynamically allocated array (like temp here) there is no way to determine the number of elements in the array.
What you have is equivalent to sizeof(int*) / sizeof(int), which is not going to do what you expect.
id.insert(id.begin(),temp[0], temp[ArraySize]);
std::vector::insert takes a range of iterators: you have provided it with two values. Presumably you want to use temp, which points to the initial element of the dynamically allocated array, and temp + i + 1, which points one past the end of the array. That said, since you haven't set the values of the elements in the array, you are copying uninitialized memory, which probably isn't what you mean to do.
select_p[i].push_back(id);
select_p[i] is a std::vector<int>. std::vector<int>::push_back() takes a single int that is appended to the sequence. Presumably you just mean to use assignment to assign id to select_p[i].
You should get a good introductory C++ book if you want to learn to program in C++. I am sorry to say that your program is nonsensical.