/*class Sales_data {
public:
Sales_data(const Sales_data&);
private:
string bookNo;
int units_sold = 0;
double revenue = 0.0;
};
Sales_data::Sales_data(const Sales_data&orig):
bookNo(orig.bookNo), units_sold(orig.units_sold), revenue(orig.revenue) { }
int main() {
return 0;
}*/
/*
int main() {
string dots(10, '.');
string s(dots);
string s2 = dots;
string null_book = "9-999-99999-9";
string nines = string(100, '9');
return 0;
}*/
// the vecotr uses a explicit constructor
/*int main() {
vector<int> v1(10);
//vecotr<int> v2 = 10;
void f(vector<int>);
//f(10);
f(vector<int>(10));
return 0;
}*/
//Exercises Section 13.1.1
//Exercise 13.1: What is a copy constructor ? When is it used ?
//A constructor is the copy constructor if its first parameter is
//a reference to the class type and any additional parameters have
//default values
//when copy initialization happens and that copy initialization re
//quires either copy constructor or move constructor
//Define variables using an '=', pass an object as an argument to a
//parameter of nonreference type, return an object from a function
//that has a nonreference return type, Brace initilaize the elements
//in an array or the members of an aggregate class, some class types
//also use copy initialzation for the objects they allocate
//Exercise 13.2: Explain why the following declaration is illegal :
//Sales_data::Sales_data(Sales_data rhs);
//the call would never succeed to call the copy ocnstructor, it's on indefinitely
//Exercise 13.4: Assuming Point is a class type with a public copy
//constructor, identify each use of the copy constructor in this program
//fragment :
/*Point global;
Point foo_bar(Point arg)//this
{
Point local = arg, *heap = new Point(global);//these two
*heap = local;
Point pa[4] = { local, *heap };//these two
return *heap;//this
}*/
//Exercise 13.5: Given the following sketch of a class, write a copy
//constructor that copies all the members.Your constructor should dynamically
//allocate a new string(§ 12.1.2, p. 458) and copy the object to which ps
//points, rather than copying ps itself.
class HasPtr {
public:
HasPtr(const std::string &s = std::string()) :
ps(new std::string(s)), i(0) { }
HasPtr(const HasPtr &hp) : ps(new std::string(*hp.ps), i(hp.i)) { }
private:
std::string *ps;
int i;
};
/*HasPtr::HasPtr(const HasPtr &c) {
string s = *c.ps;
ps = &s;
i = c.i
}*/
13.2. Copy Control and Resource Management
Exercises Section 13.1.2
Exercise 13.6: What is a copy-assignment operator? When is this operator
used? What does the synthesized copy-assignment operator do? When is it
synthesized?
The copy-assignment operator is function named operator= and takes an
argument of the same class.
It is used when assignment occurred.
The synthesized copy-assignment operator assigns each nonstatic member
of the right-hand object to corresponding member of the left-hand object
using the copy-assignment operator for the type of that member.
When the class does not define its own.
Exercise 13.8: Write the assignment operator for the HasPtr class from
exercise 13.5 in § 13.1.1 (p. 499). As with the copy constructor, your
assignment operator should copy the object to which ps points.
class HasPtr {
public:
HasPtr(const std::string &s = std::string()) :
ps(new std::string(s)), i(0) { }
HasPtr(const HasPtr &hp) : ps(new std::string(*hp.ps)), i(hp.i) { }
HasPtr &operator=(const HasPtr &hp) {
if (this != &hp) {
string *tps = new string(*hp.ps);
delete ps;
ps = tps;
i = hp.i;
}
}
private:
std::string *ps;
int i;
};
Exercises Section 13.1.3
Exercise 13.9: What is a destructor? What does the synthesized destructordo? When is a destructor synthesized?
The destructor operates inversely to the constructors: Constructor init
ialize the nonstatic data members and may do other work, destructors do
whatever work is needed to free the resources used by an object and des
tory the nonstatic data members of the object.
when class does not define its own destructor.
Exercise 13.11: Add a destructor to your HasPtr class from the previous
exercises.
class HasPtr {
public:
HasPtr(const std::string &s = std::string()) :
ps(new std::string(s)), i(0) { }
HasPtr(const HasPtr &hp) : ps(new std::string(*hp.ps)), i(hp.i) { }
HasPtr &operator=(const HasPtr &hp) {
if (this != &hp) {
string *tps = new string(*hp.ps);
delete ps;
ps = tps;
i = hp.i;
}
}
~HasPtr() { delete ps; }
private:
std::string *ps;
int i;
};
Exercise 13.12: How many destructor calls occur in the following code
fragment?
bool fcn(const Sales_data *trans, Sales_data accum)
{
Sales_data item1(*trans), item2(accum);
return item1.isbn() != item2.isbn();
} three
Exercise 13.13: A good way to understand copy-control members and
constructors is to define a simple class with these members in which each
member prints its name:
struct X {
X() {std::cout << "X()" << std::endl;}
X(const X&) {std::cout << "X(const X&)" <<
std::endl;}
};
Add the copy-assignment operator and destructor to X and write a program using
X objects in various ways: Pass them as nonreference and reference parameters;
dynamically allocate them; put them in containers; and so forth. Study the output
until you are certain you understand when and why each copy-control member is
used. As you read the output, remember that the compiler can omit calls to the
copy constructor.
struct X {
X() { std::cout << "X()" << std::endl; }
X(const X&) {
std::cout << "X(const X&)" << std::endl;
}
X &operator=(const X &rhs) {
cout << "X &operator=(const X&)" << endl;
return *this;
}
~X() { cout << "~X()" << endl; }
};
void f(const X &rx, X x) {//1
cout << 1 << endl;
vector<X> vec;
vec.reserve(2);
vec.push_back(rx);
cout << 2 << endl;
vec.push_back(x);
cout << 3 << endl;
}//out of the range the three are destructed
int main() {
X *px = new X;
f(*px, *px);
delete px;//the x are destructed
return 0;
}
//Exercises Section 13.1.4
//Exercise 13.14: Assume that numbered is a class with a default constructor
//that generates a unique serial number for each object, which is stored in a
//data member named mysn.Assuming numbered uses the synthesized copycontrol
//members and given the following function :
//Three identical number
class numbered {
public:
numbered() {
mysn = unique++;
}
int mysn;
static int unique;
};
int numbered::unique = 10;
void f(numbered s) {
cout << s.mysn << endl;
}
int main() {
numbered a, b = a, c = b;
f(a);
f(b);
f(c);
return 0;
}
//Exercise 13.15: Assume numbered has a copy constructor that generates a
//new serial number.Does that change the output of the calls in the previous
//exercise ? If so, why ? What output gets generated ?
class numbered {
public:
numbered() {
mysn = unique++;
}
numbered(numbered &n) {
mysn = unique++;
}
int mysn;
static int unique;
};
int numbered::unique = 10;
void f(numbered s) {
cout << s.mysn << endl;
}
int main() {
numbered a, b = a, c = b;
cout << a.mysn << endl;
cout << b.mysn << endl;
cout << c.mysn << endl;
f(a);
f(b);
f(c);
return 0;
}
//Exercise 13.16: What if the parameter in f were const numbered& ?
//Does that change the output ? If so, why ? What output gets generated ?
class numbered {
public:
numbered() {
mysn = unique++;
}
numbered(numbered &n) {
mysn = unique++;
}
int mysn;
static int unique;
};
int numbered::unique = 10;
void f(numbered &s) {
cout << s.mysn << endl;
}
int main() {
numbered a, b = a, c = b;
cout << a.mysn << endl;
cout << b.mysn << endl;
cout << c.mysn << endl;
f(a);
f(b);
f(c);
return 0;
}
//exercises Section 13.1.6
//Exercise 13.18: Define an Employee class that contains an employee name
//and a unique employee identifier.Give the class a default constructor and a
//constructor that takes a string representing the employee’s name.Each
//constructor should generate a unique ID by incrementing a static data
//member.
//Exercise 13.19: Does your Employee class need to define its own versions
//of the copy - control members ? If so, why ? If not, why not? Implement
//whatever copy - control members you think Employee needs.
//No, for the employe copy has no sensible meaning.
class Employee {
public:
Employee();
Employee(const string &);
Employee(const Employee &) = delete;
Employee &operator=(const Employee&) = delete;
const int Id() const { return id; }
private:
static int unique;
string name;
int id;
};
int Employee::unique = 0;
Employee::Employee() {
id = unique++;
}
Employee::Employee(const string &s) {
id = unique++;
name = s;
}
int main() {
return 0;
}