C++ Subscript operator - c++

I have written a code but it doesn't seems to work. Every time I execute the program, I get this error
Run-Time Check Failure #2 - Stack around the variable 'ary' was
corrupted
anyway here is my code(it is a small code)
#include <iostream>
using namespace std;
class Arrayz{
private:
int arry[5];
public:
Arrayz(){}
void setInf(){
for(int i = 0; i < 5; ++i){
cout << "Enter age of your friends: ";
cin >> arry[5];
}
}
const int& operator [](const int pos){
return arry[pos];
}
};
int main(){
Arrayz ary;
ary.setInf();
cout << "Here are your friend's age: " << endl;
for (int i = 0; i < 5; ++i){
cout << ary[i] << endl;
}
return 0;
}
also can you also help in subscript operator, I just don't seem to understand how to declare and use them. Also it seems pretty foolish to write a program without first understanding it first but anyway help would be appreciated :)

You probably mean cin >> arry[i]; – i, not 5.

You made a typo in member function setInf. Instead of cin >> arry[5]; there shall be cin >> arry[i];
void setInf(){
for(int i = 0; i < 5; ++i){
cout << "Enter age of your friends: ";
cin >> arry[i];
}
}
As for the subscript operator then you defined it correctly
const int& operator [](const int pos){
return arry[pos];
}
though there is no need to declare the parameter with qualifier const. Also the operator itself should have qualifier const You could write simply
const int& operator [](int pos) const {
return arry[pos];
}
Or
int operator [](int pos) const {
return arry[pos];
}
Also you could define its non-const version when the user could change elements of the array arry.
int & operator []( int pos) {
return arry[pos];
}
Also it is a good idea that your class had a member function that would return the size of the array. For example
class Arrayz{
private:
static const size_t N = 5;
int arry[N];
public:
Arrayz(){}
void setInf(){
for(int i = 0; i < N; ++i){
cout << "Enter age of your friends: ";
cin >> arry[i];
}
}
int operator [](int pos) const {
return arry[pos];
}
int & operator []( int pos) {
return arry[pos];
}
size_t size() const { return N; }
};
And in main you could write
for (int i = 0; i < ary.size(); ++i){
cout << ary[i] << endl;
}

Related

Problem using std::sort with custom class

Doing hackerrank problem "Attending Workshops" https://www.hackerrank.com/challenges/attending-workshops/problem
I have the problem that I can't sort my vector. I tried with a lambda (in commentary) and then by overloading the operator >.
My vector never turn out to be sorted. Can you help me find what I did wrong. Here is my code:
#include<bits/stdc++.h>
using namespace std;
//*************ABOVE IS LOCKED CODE BY HACKERRANK****************;
//Define the structs Workshops and Available_Workshops.
//Implement the functions initialize and CalculateMaxWorkshops
struct Workshop
{
int startTime;
int endTime;
int duration;
Workshop(){}
Workshop(int pStartTime, int pDuration)
:startTime(pStartTime), duration(pDuration)
{
endTime = startTime + duration;
}
bool operator < (const Workshop &other) const
{
cout << "trace inside operator never showing up" << endl;
return endTime < other.endTime;
}
};
struct Available_Workshops
{
int nbWorkshop;
vector<Workshop> workshops;
Available_Workshops(int *start_times, int *durations, int n)
:nbWorkshop(n)
{
workshops.reserve(n);
for(int i = 0; i < n; ++i)
{
workshops[i] = Workshop(start_times[i], durations[i]);
}
}
};
Available_Workshops *initialize(int *start_time, int *duration, int n)
{
return new Available_Workshops(start_time, duration, n);
}
int CalculateMaxWorkshops(Available_Workshops *avai_work_ptr)
{
//The two for loops are just there to trace the content of avai_work_ptr->nbWorkshop to validate sorting...
for(int i = 0; i < avai_work_ptr->nbWorkshop; ++i)
cout << avai_work_ptr->workshops[i].startTime << " " << avai_work_ptr->workshops[i].endTime << endl;
std::sort(avai_work_ptr->workshops.begin(), avai_work_ptr->workshops.end());//, [](const Workshop &a, const Workshop &b){cout << "compar"; return a.startTime < b.startTime;});
for(int i = 0; i < avai_work_ptr->nbWorkshop; ++i)
cout << avai_work_ptr->workshops[i].startTime << " " << avai_work_ptr->workshops[i].endTime << endl;
int maxWorkshop = 0;
//Chunk of code removed because it is not related to the sort problem...
//...
return maxWorkshop;
}
//*************BELOW IS LOCKED CODE BY HACKERRANK****************;
int main(int argc, char *argv[]) {
int n; // number of workshops
cin >> n;
// create arrays of unknown size n
int* start_time = new int[n];
int* duration = new int[n];
for(int i=0; i < n; i++){
cin >> start_time[i];
}
for(int i = 0; i < n; i++){
cin >> duration[i];
}
Available_Workshops * ptr;
ptr = initialize(start_time,duration, n);
cout << CalculateMaxWorkshops(ptr) << endl;
return 0;
}
Thank you.
workshops.reserve(n);
is wrong. It just do allocation and not inclease the number of valid elements, so the end() iterator will still be the top of the array.
You should use
workshops.resize(n);
instead.

I can enter the inputs but I'm not able to see the output when I run my code (CTRL+F5) in C++ in visual studio 2017

I can enter the inputs but I'm not able to see the output when I run my code (CTRL+F5) in C++ in visual studio 2017. This code is written to overload the operator *, ">>" & "<<" through the friend functions. one constructor initializes the vector elements to zero while the other constructor is used to initialize the elements of vector through the array.
My code is as below:
//vector.h
#pragma once
const int SIZE = 3;
#include<iostream>
using namespace std;
class vector
{
int v[SIZE];
public:
vector();
vector(int *x);
friend vector operator *(vector a, int b);
friend vector operator *(int b,vector a);
friend istream & operator >>(istream &input, vector &x);
friend ostream & operator <<(ostream &output, vector &y);
};
//vector.cpp
#include "vector.h"
#include<iostream>
using namespace std;
vector::vector()
{
for (int i = 0; i < SIZE; i++)
v[i] = 0;
}
vector::vector(int *x)
{
for (int i = 0; i < SIZE; i++)
v[i] = x[i];
}
vector operator *(vector a, int b) {
vector temp;
for (int i = 0; i < SIZE; i++)
temp.v[i] = a.v[i]*b;
return temp;
}
vector operator *(int a, vector b) {
vector temp;
for (int i = 0; i < SIZE; i++)
temp.v[i] = a * b.v[i];
return temp;
}
istream & operator >>(istream &input, vector &x) {
for (int i = 0; i < SIZE; i++)
input >> x.v[i];
return (input);
}
ostream & operator <<(ostream &output, vector &y) {
output << "(" << y.v[0];
for (int i = 1; i < SIZE; i++)
output <<","<< y.v[i];
output << ")";
return (output);
}
//main.cpp
#include "vector.h"
#include<iostream>
using namespace std;
int x[SIZE] = { 2,4,6 };
int main() {
vector m;
vector v2 = x;
cout << "Enter the elements of vector m:" << "\n";
cin >> m;
cout << "\n";
vector m1, m2;
m1 = m * 2;
m2 = 2 * v2;
cout << "m= "<<m<<"\n";
cout << "\n";
cout << "m1= " << m1 << "\n";
cout << "m2= " << m2 << "\n";
cin.get();
return 0;
}
Probably your linker settings are incorrect. Go to menu item Project/Properties. Then in the dialog find Configuration Properties/Linker/System/Subsystem and make sure it says Console (/SUBSYSTEM:CONSOLE).
Evgeny is correct cin.get() is not guaranteed to halt your program because there are still characters waiting to be read from cin that are left over from previous reads.
Your code assumes you must enter 3 number. If you enter less numbers you see no output.
Some comments:
Your cin.get() doesn't stop execution.
Using std (like using namespace std) and definition own vector class - it's very bad idea.

C++ Operator Overload >>

I hadn't found answer even if exist anywhere.
I have class and I want overload >> operator
That code compile but it don't work how I want.
I want put value in all cells inside array, but it only work for 1st cell. Looks like my loop don't work.
Edited:
Full code below. Btw sorry for language but this is my homework and teacher want that names.
#include <cstdlib>
#include <iostream>
#include <string>
#include <cmath>
template <class T>
class Wielomian {
private:
int stopien;
T *wspolczynniki;
public:
friend std::ostream & operator << (std::ostream &output, Wielomian &w)
{
output << "Wielomian: ";
for (int i = w.stopien-1; i >= 0; i--)
{
output << w.wspolczynniki[i] << "x^" << i << " ";
if (i)
output << "+ ";
}
return output;
}
friend std::istream & operator >> (std::istream &input, Wielomian &w)
{
int i = 0;
do {
input >> w.wspolczynniki[i++];
} while (w.stopien < i);
return input;
}
T operator () (T x)
{
T wynik = 0;
for (int i = 0; i < this->stopien; i++)
{
wynik += this->wspolczynniki[i] * pow(x,i);
}
return wynik;
}
T& operator[](const int index)
{
return wspolczynniki[index];
}
Wielomian operator + (const Wielomian &w)
{
const Wielomian *wiekszy;
const Wielomian *mniejszy;
if (w.stopien > this->stopien)
{
wiekszy = &w;
mniejszy = this;
}
else
{
wiekszy = this;
mniejszy = &w;
}
for (int i = 0; i < mniejszy->stopien; i++)
wiekszy->wspolczynniki[i] += mniejszy->wspolczynniki[i];
return *wiekszy;
}
Wielomian operator - (const Wielomian &w)
{
const Wielomian *wiekszy;
const Wielomian *mniejszy;
if (w.stopien > this->stopien)
{
wiekszy = &w;
mniejszy = this;
}
else
{
wiekszy = this;
mniejszy = &w;
}
for (int i = 0; i < mniejszy->stopien; i++)
wiekszy->wspolczynniki[i] -= mniejszy->wspolczynniki[i];
return *wiekszy;
}
Wielomian operator = (const Wielomian &w)
{
this->stopien = w.stopien;
this->wspolczynniki = new float[this->stopien];
memcpy(this->wspolczynniki, w.wspolczynniki, w.stopien * sizeof(double));
}
Wielomian(const Wielomian &w)
{
this->stopien = w.stopien;
this->wspolczynniki = new float[this->stopien];
memcpy(this->wspolczynniki, w.wspolczynniki, w.stopien * sizeof(double));
}
Wielomian(int stopien = 0, T wspolczynik[] = { 3 })
{
this->stopien = stopien;
wspolczynniki = new T[this->stopien];
for (int i = 0; i < stopien; i++)
{
this->wspolczynniki[i] = wspolczynik[i];
}
}
~Wielomian()
{
free(this->wspolczynniki);
}
};
int main()
{
double tab[4] = {3,4,5,6};
Wielomian<double> w1(4,tab);
std::cin >> w1;
std::cout << w1;
std::cin.get();
std::cin.get();
return 0;
}
Your while condition in operator >> is wrong. In your code you have:
int i = 0;
do {
input >> w.wspolczynniki[i++];
} while (w.stopien < i);
i is 0 at the beginning, and then after input >> w.wspolczynniki[i++] it is 1. The while condition is (w.stopien < i) so if w.stopien (which is 4 in your example) is smaler then i which is 1 in the first iteration, you will continue the loop. But 4 < 1 is false you will always only read one value.
So get your do-while to work you would need to change it to (w.stopien > i). But as you test if your index i is in the correct range you shouldn't use a do-while at all, but a while loop.
int i = 0;
while (i < w.stopien) {
input >> w.wspolczynniki[i++];
}
Or even a for loop, which would make clearer what you are doing:
for(int i=0; i< w.stopien; i++) {
input >> w.wspolczynniki[i];
}
In addition to that - and what is already mentioned in the comments - never combine the memory allocations and deallocation that don't belong together. If you use new[] then you have to use delete[] to free the memory and not free.
And don't use signed numbers (int) for indices, so stopien and i should be unsigned (e.g. size_t). And for stopien you should ensure on construction that it is 1 or larger.
And if you are allowed to you should switch form T* wspolczynniki to std::vector<T> wspolczynniki that would allow you to get rid of the copy constructor, the assignment operator, the destructor, you would not need int stopien, and you could simplify other parts of the code using [algorithm](https://en.cppreference.com/w/cpp/algorithm), or at least keep that you normally would use astd::vector` (or other containers) then doing the allocation and the copying yourself.

Error while overloading insertion operator [duplicate]

This question already has answers here:
My attempt at value initialization is interpreted as a function declaration, and why doesn't A a(()); solve it?
(5 answers)
Understanding 'most vexing parse' - why allow ambiguous syntax?
(2 answers)
Closed 5 years ago.
I have following piece of code
#include <iostream>
using namespace std;
class TestMatrix {
int row, col;
int **arr = NULL;
public:
friend istream& operator>> (istream &in, TestMatrix &mat);
friend ostream& operator<< (ostream &out, TestMatrix &mat);
TestMatrix(int row=1, int col=1):row(row), col(col){
arr = new int*[row];
for (int i = 0; i<row; i++) {
arr[i] = new int[col];
}
}
};
TestMatrix() {
/*cout << "Enter number of rows of your matrix";
cin >> this->row;
cout << "Enter number of columns of matrix";
cin >> this->col;*/
this->row = 3;
this->col = 3;
arr = new int*[this->row];
for (int i = 0; i<this->row; i++) {
arr[i] = new int[this->col];
}
}
istream & operator>> (istream & in, TestMatrix &mat)
{
cout << "Enter " << mat.row * mat.col << " numbers row wise \n";
for (int i = 0; i < mat.row; i++) {
for (int j = 0; j < mat.col; j++) {
in >> mat.arr[i][j];
}
}
return in;
}
ostream & operator<< (ostream & out, TestMatrix &mat) {
for (int i = 0; i < mat.row; i++) {
for (int j = 0; j < mat.col; j++) {
cout << mat.arr[i][j] << " ";
}
cout << "\n";
}
return out;
}
int main() {
TestMatrix mMatrix1(3, 3);
TestMatrix mMatrix2();
//**This works fine
cin >> mMatrix1;
//**This gives error
cin >> mMatrix2;
return 0;
}
I am trying to overload insertion and extraction operator.
I have instantiated class TestMatrix using overloaded constructors.
While trying to access overloaded operator with instance which was constructed using constructor without argument, I get error stating
binary '>>': no operator found which takes a right-hand operand of type 'overloaded-function' (or there is no acceptable conversion)
Can someone please explain reason for same.

Overloading operator[] changing value

I'm trying to overload an int array, so basically if I have this in my main func
IntArray arr(10);
for(int i = 0; 0 < 10; i++)
a[i] = i * 10;
I was able to get
a[0] = 0, a[1] =10, a[2]=20.... so on
I was able to make this one work.
If I then do
IntArray arr(-3, 10)
with same for loop, I was able to get the appropriate answer as well.
BUT...
If I do
IntArray arr(6, 8)`
using same for loop I get c[6] = 1, c[7]=1, c[8] =0
I been trying to figure this out since yesterday, here's my code:
//---------------------Header file
#ifndef INTARRAY_H_
#define INTARRAY_H_
#include <iostream>
using namespace std;
class IntArray
{
private:
int first;
int last;
int size;
string arrName;
int* arrPtr;
public:
IntArray();
int& operator[](int i);
IntArray(int num);
IntArray(int num1, int num2);
int low();
int high();
void setName(string str);
//streams
friend istream& operator>>(istream& is, IntArray& d);
friend ostream& operator<<(ostream& os, IntArray& d);
};
#endif /* INTARRAY_H_ */
//---------------------
My int array class:
#include "IntArray.h"
IntArray::IntArray(){
size = 10;
first = 0; last = 9;
arrPtr = new int[size];
}
IntArray::IntArray(int num){
size = num;
first = 0; last = size-1;
arrPtr = new int[size];
//cout<<"\n the size "<<size<<endl;
//arrPtr[3] = 123;
//ex = 3;
}
IntArray::IntArray(int num1, int num2){
first = num1; last = num2;
size = last - first + 1;
//cout<<"\n the size "<<size<<endl;
arrPtr = new int[size];
}
int& IntArray::operator[](int i) {
if (i >= (last+1)){
cout<<"Error: Index out of range"<<endl;
exit(1);
}
return arrPtr[i];
}
int IntArray::getInt(int i){
return arrPtr[i];
}
//======================
int IntArray::low(){
return first;
}
int IntArray::high(){
return last;
}
//======================
//==========OUT stream==========
// for cout << justName<< endl;
ostream& operator<<(ostream& os, IntArray& aPtr) {
for(int i = aPtr.low(); i <= aPtr.high(); i++){
os << aPtr.arrName <<"[" << i << "] = " << aPtr[i] << " ";
}
return os;
}
void IntArray::setName(string str){
arrName = str;
}
For some apparent reason, after using my setName function on this test function, it changes the value to c[6] = 1, c[7]=1, c[8] =0.
void test3() {
IntArray c(6, 8);
for(int i = c.low(); i <= c.high(); i++)
c[i] = i * 10;
c.setName("c");
cout << c << endl;
}
Let me make this one clear. Like I said, I did narrowed down my problem.
IntArray a(10) //THIS ONE WORKS!
IntArray a(-3, 6) //THIS ONE WORKS!
IntArray a(6,8) //NOT working.
For the last one, the array outputs the right value, until I use the setName function.
This may not be your only problem but it looks like you want to allow users of your class to use the old Perl $[
To support this you'll need to modify it in your operator[]:
int& IntArray::operator[](int i) {
if (i > last || i < first ){
cout<<"Error: Index out of range"<<endl;
exit(1);
}
return arrPtr[i - first];
}
In the subscript operator you also should check that i is not less than first.
Tale into account that relative to the pointer you have to use indices starting from zero. So instead of
return arrPtr[i];
you have to write
return arrPtr[i - first];
Also it would be better if constructor
IntArray(int num);
would be declared like
IntArray( size_t num);
and correspondingly data member size would have type size_t