The below is the code, but I dont know how to debuy it. Can someone help me?
enter image description here
#include <iostream>
using namespace std;
class CSample
{
int *x;
int N;
public:
//dafualt constructor
CSample(): x(NULL)
{}
void AllocateX(int N)
{
this->N = N;
x = new int[this->N];
}
int GetX()
{
return x;
}
~CSample()
{
delete []x;
}
};
int main()
{
CSample ob1; //Default constructor is called.
ob1.AllocateX(10);
//problem with this line
CSample ob2 = ob1; //default copy constructor called.
CSample ob3; //Default constructor called.
//problem with this line
ob3 = ob1; //default overloaded = operator function called.
}
This method has the wrong signature
int GetX()
{
return x;
}
it should be
int* GetX()
{
return x;
}
As far as your assignment, you'd need a copy assignment operator to say ob3 = ob1 which would look like
CSample& operator=(CSample& other)
{
N = other.N;
x = new int[N];
std::copy(other.x, other.x + other.N, x);
return *this;
}
Related
I have question on the below code. In the main function what will happen when the line: obj = 20; is executed. I am not able to understand why it calls the constructor? Could anyone of you please explain?
#include <iostream>
#include <string>
using namespace std;
class Int {
int x;
public:
Int(int x_in = 0)
: x{ x_in }
{
cout << "Conversion Ctor called" << endl;
}
operator string()
{
cout << "Conversion Operator" << endl;
return to_string(x);
}
};
int main()
{
Int obj(3);
string str = obj;
obj = 20;
string str2 = static_cast<string>(obj);
obj = static_cast<Int>(30);
return 0;
}
Within the class there is not defined the assignment operator operator =( int ). But the class has the conversion constructor
Int(int x_in = 0)
So in this statement
obj = 20;
there is called the constructor like Int( 20 ) to convert the integer value to an object of the type Int that can be assigned to the object obj due to the implicit move assignment operator generated by the compiler.
Lacking a assignment operator taking int, your compiler uses the next best assignment operator it can get it's hands on, which is the implicitly declared move assignment operator (Int::operator=(Int&&)). To use this operator, a rvalue reference to a Int object is required, which the compiler creates using the constructor Int::Int(int), i.e. the compiler treats obj = 20; as
obj.operator=(Int(20));
To see what's happening here, you could implement the move assignment operator yourself to print something to the console when the assignment operator is executed:
class Int
{
...
public:
...
Int& operator=(Int&& other)
{
std::cout << "move assignment of Int, new value: " << other.x << '\n';
x = other.x;
return *this;
}
// the following members are only declared to make sure the available
// constructors/operators are the same as in the original version of the code
Int(Int&&) = default;
Int& operator=(Int const&) = default;
Int(Int const&) = default;
};
After I run the program I get an error saying projectname has triggered a breakpoint. I still do not know what the error is. I think there's a member function missing but someone help me out?
#include "AClass.h"
#include <iostream>
using namespace std;
int main()
{
AClass* x = new AClass(10, -1.0);
AClass y = *x;
delete x;
return 0;
}
Code from my cpp file is as follows:
#include "AClass.h"
#include <iostream>
using namespace std;
// Constructor
AClass::AClass(int len, double val)
: length(len)
{
if (len < 0) {
cout << "Invalid data length = " << len << endl;
data = NULL;
}
else {
data = new double[length];
for (int i = 0; i < length; i++)
data[i] = val;
}
}
// Destructor
AClass::~AClass()
{
// delete data if it is not NULL
if (data) delete[] data;
}
Your AClass member double* data; will be copied here:
AClass y = *x;
Since you haven't provided copy/move constructors/assignment operators, the raw pointer will be copied as-is in these situations and delete[] data will be done by both x and y in the destructor.
Mandatory read when dealing with raw pointers:
https://en.cppreference.com/w/cpp/language/rule_of_three
And these:
What is The Rule of Three?
Rule-of-Three becomes Rule-of-Five with C++11?
Here's an example implementation of the member functions mentioned in the above articles. It's a little much - and error prone, which is why it's almost always better to use a standard container.
#include <algorithm>
#include <iostream>
#include <utility>
class AClass {
public:
AClass(size_t len, double val);
// rule of five:
AClass(const AClass& rhs); // copy constructor
AClass(AClass&& rhs); // move constructor
AClass& operator=(const AClass& rhs); // copy assignment
AClass& operator=(AClass&& rhs); // move assignment
~AClass();
private:
size_t length; // use an unsigned type since you only accept unsigned values
double* data;
};
// destructor
AClass::~AClass() {
delete[] data;
}
AClass::AClass(size_t len, double val) :
length(len),
data(new double[length])
{
std::fill_n(data, length, val);
}
// copy constructor
AClass::AClass(const AClass& rhs) :
length(rhs.length),
data(new double[length])
{
std::copy_n(rhs.data, length, data);
}
// move constructor
AClass::AClass(AClass&& rhs) :
length(std::exchange(rhs.length, 0)),
data(std::exchange(rhs.data, nullptr))
{}
// copy assignment
AClass& AClass::operator=(const AClass& rhs) {
double* tmpdata = new double[rhs.length];
delete[] data;
length = rhs.length;
data = tmpdata;
std::copy_n(rhs.data, length, data);
return *this;
}
// move assignment
AClass& AClass::operator=(AClass&& rhs) {
// leave the destruction up to the moved-from object
std::swap(length, rhs.length);
std::swap(data, rhs.data);
return *this;
}
int main() {
AClass* x = new AClass(10, -1.0);
AClass y = *x;
delete x;
}
I have a problem with assignment int to object like this:
int main() {
Wurzel a;
Wurzel b=3; // error: conversion from 'int' to non-scalar type 'Wurzel' requested
return 0;
}
My class with assignment operator:
class Wurzel{
private:
int wurzelexponent;
int wert;
public:
Wurzel(){
wurzelexponent=1;
wert=1;
}
Wurzel& operator =(const Wurzel &w) {
wurzelexponent = w.wurzelexponent;
}
};
I must do this with = operator
Where is the problem?
I must do this with = operator
No, you can't. Because Wurzel b=3; is not assignment, it's initialization, copy initialization. As the error message said, you need a converting constructor to accomplish it.
class Wurzel{
...
public:
...
Wurzel(int x) : wurzelexponent(x), wert(1) {}
Wurzel(int x, int y) : wurzelexponent(x), wert(y) {}
...
};
then
Wurzel b = 3; // Wurzel::Wurzel(int) will be called
Wurzel b = {3, 2}; // Wurzel::Wurzel(int, int) will be called [1]
Note that operator= is only used for assignment, such as:
Wurzel b; // default initialized
b = something; // this is assignment, operator=() will be used
[1] Converting constructor with multiple parameters was introduced from C++11.
The problem is that functions needed are not defined.
One solution is overloading = operator to accept int.
Try this:
class Wurzel{
private:
int wurzelexponent;
int wert;
public:
Wurzel(){
wurzelexponent=1;
wert=1;
}
// this is constructor, not = operator
/*
Wurzel(int a) {
wurzelexponent = a;
wert = a;
}
*/
Wurzel& operator =(const Wurzel &w) {
wurzelexponent = w.wurzelexponent;
return *this; // you should return something
}
Wurzel& operator=(int a) {
// implement as you like
wurzelexponent = a;
return *this;
}
};
int main() {
Wurzel a;
// this is not = operator but initializing
//Wurzel b=3;
Wurzel b;
b = 3; // this is = opetator, which you say you must use
return 0;
}
You are trying to assing an int: Wurzel b=3;, but your operator= is only overloaded for const Wurzel &w. Its parameter is Wurzel, not an int and int is not implicitly convertible to Wurzel. To fix, you can add another operator:
Wurzel& operator =(int i)
{}
#include < iostream >
using namespace std;
class A
{
public:
int x;
A(int i)
{
x= i;
cout<<"Constructor is Called "<<x<<endl;
}
~A()
{
cout<<"destructor is Called "<<x<<endl;
}
A(const A &a)
{
cout<<"in copy constructor a.x = "<<a.x<<endl;
cout<<" x = "<<x<<endl;
}
};
const A &fun(int i)
{
cout<<"in Fun"<<endl;
A t(i+1);
return(t);
}
main()
{
A *gg = new A(5);
A t = fun(2);
}
output of this is :
Constructor is Called 5
in Fun
Constructor is Called 3
destructor is Called 3
in copy constructor a.x = 0
x = 4067272
Why it is a.x=0 and x= 4067272?
Add code to initialize x in the copy constructor.
A(const A &a) : x(a.x)
//^^^^^^^^^^^^^^^ Missing code
{
cout<<"in copy constructor a.x = "<<a.x<<endl;
cout<<" x = "<<x<<endl;
}
Also,
fun returns a reference to a local variable. The reference is invalid after you return from fun. When you use A t = fun(2);, you are entering UB territory. You can't assume anything reasonable from it.
You can fix this by returning an object from fun instead of a const&.
A fun(int i)
{
cout<<"in Fun"<<endl;
A t(i+1);
return(t);
}
I found this code on the internet. I am a bit confused about the calling of the copy constructor and I just wanted to know why the copy constructor is called when the display function is called?
#include<iostream>
using namespace std;
class myclass
{
int val;
int copynumber;
public:
//normal constructor
myclass(int i)
{
val = i;
copynumber = 0;
cout<<"inside normal constructor"<<endl;
}
//copy constructor
myclass (const myclass &o)
{
val = o.val;
copynumber = o.copynumber + 1;
cout<<"Inside copy constructor"<<endl;
}
~myclass()
{
if(copynumber == 0)
cout<<"Destructing original"<<endl;
else
cout<<"Destructing copy number"<<endl;
}
int getval()
{
return val;
}
};
void display (myclass ob)
{
cout<<ob.getval()<<endl;
}
int main()
{
myclass a(10);
display (a);
return 0;
}
In the display method you are passing the parameter by value, so obviously there will be a copy made and sent to the function. Learn the difference of pass by value and reference. this and this tutorials may be useful.
It is being invoked because you are passing the object value rather than by const reference. If you passed a const myclass& ob, instead, then the copy constructor wouldn't get called. However, as is, your function is set up to create a copy of the parameter (that is, your function operates on a copy, not the original object).