#include "StoreItem.h"
using namespace System;
namespace ElectronicsStore
{
CStoreItem::CStoreItem(void)
: nbr(0),
cat(L'U'),
mk(L"Unknown"),
mdl(L"Unspecified"),
nm(L"N/A"),
discount(0.00),
price(0.00)
{
}
CStoreItem::CStoreItem(long itmNbr, String ^ make,
String ^ model, double unitPrice)
: nbr(itmNbr),
cat(L'U'),
mk(make),
mdl(model),
nm(L"N/A"),
discount(0.00),
price(unitPrice)
{
}
CStoreItem::CStoreItem(long itmNbr, String ^ name,
double unitPrice)
: nbr(itmNbr),
cat(L'U'),
mk(L"Unknown"),
mdl(L"Unspecified"),
nm(name),
discount(0.00),
price(unitPrice)
{
}
CStoreItem::CStoreItem(long itmNbr, __wchar_t category,
String ^ make, String ^ model,
double discountRate, double unitPrice)
: nbr(itmNbr),
cat(category),
mk(make),
mdl(model),
discount(discountRate),
price(unitPrice)
{
}
CStoreItem::~CStoreItem()
{
}
}
To create one more source file, on the main menu, click Project -> Add New Item...
In the Templates list, make sure C++ File (.cpp) is selected.
Set the Name to Exercise and click Add
Complete the file as follows:
#include "StoreItem.h"
using namespace System;
using namespace ElectronicsStore;
static void DescribeStoreItem(CStoreItem ^ %);
int main()
{
String ^ strTitle = L"=-= Nearson Electonics =-=\n"
L"******* Store Items ******";
Console::WriteLine();
return 0;
}
Execute the application to make sure it can compile
Close the DOS window
Because it cannot perform an assignment,
a member variable of a class can only receive a value from the outside world. It
can also be vulnerable to outside objects and functions. You can prevent this vulnerability by "hiding" the
member variable in a private section. Because you may still want outside objects and
functions to interact with the value held by a member variable, you can create
an accessory method that corresponds to that variable. One way you can implement
such a method is to make it return a reference.
Like a regular function, a method of a
class can be created to return a reference or a tracking reference. When
creating the method, make sure you type the & or % operator on the left of
its name. When implementing the method, in most cases, you can simply return a
member variable of the class that is declared with the same data type as the one
that the method would return. Here is an example:
Header File: Rectangle.h |
#pragma once
public ref class CRectangle
{
private:
double len;
public:
double %Length();
};
|
Source File: Rectangle.cpp |
#include "Rectangle.h"
double %CRectangle::Length()
{
return len;
}
|
You may remember that a function can only be assigned to a
variable. It cannot be assigned a value. In the same way, no value can be
assigned to the name of a method. For example, the following code will not
compile:
public ref class Circle
{
private:
double Radius;
public:
Circle(double rad) { Radius = rad; }
double Area() { return Radius * Radius * 3.14159; }
};
int main()
{
Circle circ(24.55);
double a = 0.00;
circ.Area() = a;
return 0;
}
The exception to this rule is with
reference methods. If a method returns a reference, it can be assigned a value.
Here is an example:
int main()
{
CRectangle ^ rect = gcnew CRectangle;
rect->Length() = 24.58;
ShowCharacteristics(rect);
Console::WriteLine();
return 0;
}
In the same way, a method that returns a
reference can also have its value retrieved. Here is an example:
Source File: Exercise.cpp |
#include "Rectangle.h"
using namespace System;
void ShowCharacteristics(CRectangle ^ %recto)
{
Console::WriteLine(L"Rectangle Characteristics");
Console::WriteLine(L"Length: {0}", recto->Length());
}
int main()
{
CRectangle ^ rect = gcnew CRectangle;
rect->Length() = 24.58;
ShowCharacteristics(rect);
Console::WriteLine();
return 0;
}
|
This would produce:
Rectangle Characteristics
Length: 24.58
Press any key to continue . . .
Notice that a reference method is
assigned a value or a value is assigned to it. In the C++ jargon, this means
that a reference method can be either an L-value (left value) or an R-value
(right value) in an expression. As mentioned earlier, a regular member variable
cannot validate or reject value because it cannot perform an assignment. Like
the properties that we will see next, the ability for a reference method to be a
left or right operand of an assignment makes it a valuable candidate to validate
or reject a value that is meant for a member variable.
A method is an action that is performed to complement a
class. It requires the mechanism of a function: some parentheses and optional
arguments. If you declare a private member variable that must interact with the
outside world, you must also implement different methods to accomplish different
roles. One of the obstacles of a normal method is that it cannot be assigned a
value, unless you create it as returning a reference. A property provides a
solution to both problems in one object. To be able to play this role, a
property must combine the functionalities of a member variable and that of a
method. For this reason, there are strict rules you must follow to create a
method.
The primary syntax used to create a property is:
modifier property type property_name;
The modifier can be static (or virtual, which we will
introduce in the next lessons). The property keyword is required. The
property keyword is followed by a data type, which can be one of those we
reviewed in Lesson 2. It can also be an enumeration. The data type is followed
by the name of the property.
A property is primarily a member variable of a class. To create one, you can simply precede the data type of a member variable
with the property keyword. Here is an example:
#pragma once
public ref class CRectangle
{
private:
double len;
double hgt;
public:
CRectangle(double l, double h);
public:
property String ^ Name;
};
After creating a property, you can access it outside of its
class like you
would any member variable. You can first declare a variable of the class and
then use the period operator to access the property. Here is an example:
#include "Rectangle.h"
using namespace System;
void ShowCharacteristics(CRectangle %recto)
{
Console::WriteLine(L"Shape Characteristics");
Console::WriteLine(L"Name: {0}", recto.Name);
}
int main()
{
CRectangle rect(24.58, -22.16);
rect.Name = L"Rectangle";
ShowCharacteristics(rect);
Console::WriteLine();
return 0;
}
Or you can create a handle to the class and use the arrow
operator to access the property. Here is an example:
#include "Rectangle.h"
using namespace System;
void ShowCharacteristics(CRectangle ^ %recto)
{
Console::WriteLine(L"Shape Characteristics");
Console::WriteLine(L"Name: {0}", recto->Name);
}
int main()
{
CRectangle ^ rect = gcnew CRectangle(24.58, -22.16);
rect->Name = L"Rectangle";
ShowCharacteristics(rect);
Console::WriteLine();
return 0;
}
This would produce:
Shape Characteristics
Name: Rectangle
Press any key to continue . . .
Practical
Learning: Creating Simple Properties |
|
- Access the StoreItem.h file
- To create simple properties, declare the following variables:
#pragma once
using namespace System;
namespace ElectronicsStore
{
public ref class CStoreItem
{
public:
// An item whose characteristics are not (yet) known
CStoreItem(void);
// An item that is known by its make, model, and unit price
CStoreItem(long itmNbr, String ^ make,
String ^ model, double unitPrice);
// An item that is known by its name and unit price
CStoreItem(long itmNbr, String ^ name, double unitPrice);
~CStoreItem();
private:
long nbr;
__wchar_t ^ cat;
String ^ mk;
String ^ mdl;
String ^ nm;
double discount;
double price;
public:
property long ItemNumber;
property __wchar_t ^ Category;
property String ^ Make;
property String ^ Model;
property String ^ Name;
property double DiscountRate;
property double UnitPrice;
};
}
- Access the Exercise.cpp file
- To test the simple properties, change it as follows:
#include "StoreItem.h"
using namespace System;
using namespace ElectronicsStore;
static void DescribeStoreItem(CStoreItem ^ %);
static void DescribeStoreItem(CStoreItem ^ %, const int);
int main()
{
String ^ strTitle = L"=-= Nearson Electonics =-=\n"
L"******* Store Items ******";
CStoreItem ^ saleItem = gcnew CStoreItem();
Console::WriteLine(L"==/==A store item with default values==/==");
DescribeStoreItem(saleItem, 0);
Console::WriteLine();
Console::WriteLine(L"==/==A store item completely defined==/==");
saleItem = gcnew CStoreItem();
saleItem->ItemNumber = 513497;
saleItem->Category = L'T';
saleItem->Make = L"Uniden";
saleItem->Model = L"8x8 Packet8 Broadband Internet Phone System";
saleItem->DiscountRate = -10;
saleItem->UnitPrice = -145.95;
DescribeStoreItem(saleItem, 0);
Console::WriteLine();
return 0;
}
// This function is used when an item is specified by its make and model
void DescribeStoreItem(CStoreItem ^ %item)
{
Console::WriteLine(L"Store Item Description");
Console::WriteLine(L"Item Number: {0}", item->ItemNumber);
Console::WriteLine(L"Category: {0}", item->Category);
Console::WriteLine(L"Make {0}", item->Make);
Console::WriteLine(L"Model: {0}", item->Model);
Console::WriteLine(L"Name: {0}", item->Name);
Console::WriteLine(L"Discount Rate: {0:P}", item->DiscountRate);
Console::WriteLine(L"Unit Price: {0:C}", item->UnitPrice);
}
// This function is used when an item is specified by its name
void DescribeStoreItem(CStoreItem ^ %item, const int)
{
Console::WriteLine(L"Store Item Description");
Console::WriteLine(L"Item Number: {0}", item->ItemNumber);
Console::WriteLine(L"Category: {0}", item->Category);
Console::WriteLine(L"Make {0}", item->Make);
Console::WriteLine(L"Model: {0}", item->Model);
Console::WriteLine(L"Discount Rate: {0:P}", item->DiscountRate);
Console::WriteLine(L"Unit Price: {0:C}", item->UnitPrice);
}
- Execute the application to test it. This would produce:
==/==A store item with default values==/==
Store Item Description
Item Number: 0
Category:
Make
Model:
Discount Rate: 0.00 %
Unit Price: $0.00
==/==A store item completely defined==/==
Store Item Description
Item Number: 513497
Category: T
Make Uniden
Model: 8x8 Packet8 Broadband Internet Phone System
Discount Rate: -1,000.00 %
Unit Price: ($145.95)
Press any key to continue . . .
- Close the DOS window
One of the roles of a property is to allow the other members of
the class or the other class and functions of an application to find
out what value the property is holding. Such a property is referred to as
"getter". The formula to create a property that provides the value of
its member variable is:
modifier property type property_name
{
modifier type get();
}
Notice that the property is created like a namespace: it has
a body and curly brackets but no parentheses like a function. In the body of the
property, there is a type of method named get. This name is required.
Because the property is meant to return a value, the get() method returns
a data type. Because get() is a method, it must have a body
delimited with curly brackets. Here is an example from our CRectangle class:
public ref class CRectangle
{
private:
double len;
double hgt;
public:
property double Length
{
double get() {}
}
};
Use the body of the get method to implement the
necessary behavior of the property getter. The simplest way consists of
returning its corresponding private member variable. Here is an example:
public ref class CRectangle
{
private:
double len;
public:
property double Length
{
double get() { return len; }
}
};
When a property includes only a get() method, such a
property is referred to as a read-only because the outside classes and functions
can only retrieve the value of the property but they cannot change it. A classic
example is the area of a rectangle. There is no need or reason for outside
classes or functions to modify this value. They can only retrieve it if they
need it. For this reason, you can create such a method as read-only. Here is an
example:
public ref class CRectangle
{
private:
double len;
double hgt;
public:
CRectangle(double l, double h);
public:
property double Length
{
double get() { return len; }
}
property double Area
{
double get()
{
return len * hgt;
}
}
};
After creating a property, you can access it like you
would any member variable. You can first declare a variable of the class, a
pointer to the class, or its handle, and use either the period or the arrow
operator. Here is an example:
using namespace System;
public ref class CRectangle
{
private:
double len;
double hgt;
public:
CRectangle();
CRectangle(double l, double h);
public:
property double Length
{
double get() { return len; }
}
property double Perimeter
{
double get()
{
return 2 * (len + hgt);
}
}
property double Area
{
double get()
{
return len * hgt;
}
}
};
CRectangle::CRectangle()
: len(0.00), hgt(0.00)
{
}
CRectangle::CRectangle(double l, double h)
: len(l), hgt(h)
{
}
void ShowCharacteristics(CRectangle ^ %recto)
{
Console::WriteLine(L"Rectangle Characteristics");
Console::WriteLine(L"Length: {0}", recto->Length);
Console::WriteLine(L"Perimeter: {0}", recto->Perimeter);
Console::WriteLine(L"Area: {0}", recto->Area);
}
int main()
{
CRectangle ^ rect = gcnew CRectangle(24.58, -22.16);
ShowCharacteristics(rect);
Console::WriteLine();
return 0;
}
This would produce:
Rectangle Characteristics
Length: 24.58
Perimeter: 4.84
Area: -544.6928
Press any key to continue . . .
In the same way, you can create as many read-only properties
as you want.
Notice that the perimeter of our rectangle appears to be
less than the length. Furthermore, the area is negative. Both values don't make
sense. A getter property doesn't have to directly produce the value of the
member variable. It can use a mechanism to validate a value that its
corresponding member variable is holding. If the value is admissible, you can
use it. If the value is not acceptable, you can either reject it or provide an
appropriate alternative.
Practical
Learning: Using Read-Only Properties of a Class |
|
- Display the StoreItem.h header file
- To transform the simple properties into read-only, change the file as
follows:
#pragma once
using namespace System;
namespace ElectronicsStore
{
public ref class CStoreItem
{
public:
// An item whose characteristics are not (yet) known
CStoreItem(void);
// An item that is known by its make, model, and unit price
CStoreItem(long itmNbr, String ^ make,
String ^ model, double unitPrice);
// An item that is known by its name and unit price
CStoreItem(long itmNbr, String ^ name, double unitPrice);
// An item completely defined
CStoreItem(long itmNbr, __wchar_t category,
String ^ make, String ^ model,
double discountRate, double unitPrice);
~CStoreItem();
private:
long nbr;
__wchar_t ^ cat;
String ^ mk;
String ^ mdl;
String ^ nm;
double discount;
double price;
public:
property long ItemNumber
{
long get() { return nbr; }
}
property __wchar_t ^ Category
{
__wchar_t ^ get() { return cat; }
}
property String ^ Make
{
String ^ get() { return mk; }
}
property String ^ Model
{
String ^ get() { return mdl; }
}
property String ^ Name
{
String ^ get() { return nm; }
}
property double DiscountRate
{
double get() { return discount; }
}
property double UnitPrice
{
double get() { return price; }
}
};
}
- Execute the application to test it
- Notice that you receive many errors because of the assignments in the
Exercise.cpp file
- Access the Exercise.cpp file and change it as follows:
#include "StoreItem.h"
using namespace System;
using namespace ElectronicsStore;
static void DescribeStoreItem(CStoreItem ^ %);
static void DescribeStoreItem(CStoreItem ^ %, const int);
int main()
{
String ^ strTitle = L"=-= Nearson Electonics =-=\n"
L"******* Store Items ******";
CStoreItem ^ saleItem = gcnew CStoreItem();
Console::WriteLine(L"==/==A store item with default values==/==");
DescribeStoreItem(saleItem, 0);
Console::WriteLine();
Console::WriteLine(L"==/==A store item completely defined==/==");
saleItem = gcnew CStoreItem(513497, L'T', L"Uniden",
L"8x8 Packet8 Broadband Internet Phone System",
-10, -145.95);
DescribeStoreItem(saleItem, 0);
Console::WriteLine();
return 0;
}
// This function is used when an item is specified by its make and model
void DescribeStoreItem(CStoreItem ^ %item)
{
Console::WriteLine(L"Store Item Description");
Console::WriteLine(L"Item Number: {0}", item->ItemNumber);
Console::WriteLine(L"Category: {0}", item->Category);
Console::WriteLine(L"Make {0}", item->Make);
Console::WriteLine(L"Model: {0}", item->Model);
Console::WriteLine(L"Name: {0}", item->Name);
Console::WriteLine(L"Discount Rate: {0:P}", item->DiscountRate);
Console::WriteLine(L"Unit Price: {0:C}", item->UnitPrice);
}
// This function is used when an item is specified by its name
void DescribeStoreItem(CStoreItem ^ %item, const int)
{
Console::WriteLine(L"Store Item Description");
Console::WriteLine(L"Item Number: {0}", item->ItemNumber);
Console::WriteLine(L"Category: {0}", item->Category);
Console::WriteLine(L"Make {0}", item->Make);
Console::WriteLine(L"Model: {0}", item->Model);
Console::WriteLine(L"Discount Rate: {0:P}", item->DiscountRate);
Console::WriteLine(L"Unit Price: {0:C}", item->UnitPrice);
}
- Execute the application again
- Close the DOS window
As mentioned previously, if you create a private member
variable, the outside classes and functions cannot access it to influence its
value. If you still want these other classes and functions to modify the value
of the member variable, you can create a property to stand in the middle. The
outside classes and functions can then submit a value to the property, and the
property would be in charge of assigning it to the corresponding member
variable. The formula to create such a property is:
modifier property type property_name
{
modifier void set(type);
}
This type of property is used to receive values for a member
variable. Because it doesn't return a value, it is created as void. The
method that actually handles the "transaction" is named set.
The value that is submitted to the property is passed as an argument to the set()
method. Because set is a method, it must have a body. Here is an example:
public ref class CRectangle
{
private:
double hgt;
public:
property double Height
{
void set(double h) { }
}
};
In the body of the set() method, define the necessary
behavior of the property. At a minimum, you can assign the argument to the
corresponding member variable. Here is an example:
public ref class CRectangle
{
private:
double hgt;
public:
property double Height
{
void set(double h) { hgt = h; }
}
};
Once again, to access the property from an external object
or function, you can use the appropriate operator (. or ->) as if it were a
member variable. Here is an example:
using namespace System;
public ref class CRectangle
{
private:
double len;
double hgt;
public:
CRectangle();
CRectangle(double l, double h);
public:
property double Length
{
double get() { return len; }
}
property double Height
{
void set(double h) { hgt = h; }
}
property double Perimeter
{
double get()
{
return 2 * (len + hgt);
}
}
property double Area
{
double get()
{
return len * hgt;
}
}
};
CRectangle::CRectangle()
: len(0.00), hgt(0.00)
{
}
CRectangle::CRectangle(double l, double h)
: len(l), hgt(h)
{
}
void ShowCharacteristics(CRectangle ^ %recto)
{
Console::WriteLine(L"Rectangle Characteristics");
Console::WriteLine(L"Length: {0}", recto->Length);
Console::WriteLine(L"Perimeter: {0}", recto->Perimeter);
Console::WriteLine(L"Area: {0}", recto->Area);
}
int main()
{
CRectangle ^ rect = gcnew CRectangle(24.58, 22.16);
rect->Height = 35.64;
ShowCharacteristics(rect);
Console::WriteLine();
return 0;
}
This would produce:
Rectangle Characteristics
Length: 24.58
Perimeter: 22.12
Area: 876.0312
Press any key to continue . . .
We have seen that a property provides a valuable
relationship between a private member variable of a class and the outside world.
As such, it can both receive values for the member variable and provide values
to the outside world. This means that a property can be meant to both read from
and write to its corresponding member variable. Such a proeprty is referred to
as read/write.
To create a read/write property, you must implement both the
get() and the set() methods of the property. When a property is
read/write, its set() method can be used to validate the values that are
submitted to the property. The get() method can then be used to present the
current value of the property to the external classes and functions. It is
important to note that the other members of the class can also access the
property. Here are examples of read/write properties:
Header File: Rectangle.h |
#pragma once
using namespace System;
public ref class CRectangle
{
private:
double len;
double hgt;
public:
property String ^ Name;
property double Length
{
double get() { return len; }
void set(double L)
{
len = L;
}
}
property double Height
{
double get() { return hgt; }
void set(double h)
{
hgt = h;
}
}
property double Perimeter
{
double get()
{
return 2 * (Length + Height);
}
}
property double Area
{
double get()
{
return Length * Height;
}
}
};
|
Source File: Rectangle.cpp |
#include "Rectangle.h"
|
Source File: Exercise.cpp |
#include "Rectangle.h"
using namespace System;
CRectangle ^ CreateShape()
{
CRectangle ^ R = gcnew CRectangle;
R->Name = L"Rectangle";
R->Length = 42.06;
R->Height = 27.92;
return R;
}
void ShowCharacteristics(CRectangle ^ %recto)
{
Console::WriteLine(L"Shape Characteristics");
Console::WriteLine(L"Name: {0}", recto->Name);
Console::WriteLine(L"Length: {0}", recto->Length);
Console::WriteLine(L"Perimeter: {0}", recto->Perimeter);
Console::WriteLine(L"Area: {0}", recto->Area);
}
int main()
{
CRectangle ^ rect = CreateShape();
ShowCharacteristics(rect);
Console::WriteLine();
return 0;
}
|
This would produce:
Shape Characteristics
Name: Rectangle
Length: 42.06
Perimeter: 139.96
Area: 1174.3152
Press any key to continue . . .
Practical
Learning: Using Read/Write Properties of a Class |
|
- Access the StoreItem.h header file
- To complete the properties of the class, change the file as follows:
#pragma once
using namespace System;
namespace ElectronicsStore
{
public ref class CStoreItem
{
public:
// An item whose characteristics are not (yet) known
CStoreItem(void);
// An item that is known by its make, model, and unit price
CStoreItem(long itmNbr, String ^ make,
String ^ model, double unitPrice);
// An item that is known by its name and unit price
CStoreItem(long itmNbr, String ^ name, double unitPrice);
// An item completely defined
CStoreItem(long itmNbr, __wchar_t category,
String ^ make, String ^ model,
double discountRate, double unitPrice);
~CStoreItem();
private:
long nbr;
__wchar_t ^ cat;
String ^ mk;
String ^ mdl;
String ^ nm;
double discount;
double price;
public:
property long ItemNumber
{
long get() { return nbr; }
void set(long n) { this->nbr = n; }
}
property __wchar_t ^ Category
{
__wchar_t ^ get() { return cat; }
void set(__wchar_t ^ n) { this->cat = n; }
}
property String ^ Make
{
String ^ get() { return mk; }
void set(String ^ m) { this->mk = m; }
}
property String ^ Model
{
String ^ get() { return mdl; }
void set(String ^ m) { this->mdl = m; }
}
property String ^ Name
{
String ^ get() { return nm; }
void set(String ^ n) { this->nm = n; }
}
property double DiscountRate
{
double get() { return discount; }
void set(double d) { this->discount = d; }
}
property double UnitPrice
{
double get() { return price; }
void set(double p) { this->price = p; }
}
};
}
- Access the Exercise.cpp file and change it as follows:
#include "StoreItem.h"
using namespace System;
using namespace ElectronicsStore;
CStoreItem ^ CreateStoreItem();
static void DescribeStoreItem(CStoreItem ^ %);
static void DescribeStoreItem(CStoreItem ^ %, const int);
int main()
{
String ^ strTitle = L"=-= Nearson Electonics =-=\n"
L"******* Store Items ******";
CStoreItem ^ saleItem = CreateStoreItem();
Console::WriteLine(L"");
DescribeStoreItem(saleItem, 0);
Console::WriteLine();
return 0;
}
CStoreItem ^ CreateStoreItem()
{
long number;
__wchar_t ^ category;
String ^ make;
String ^ model;
double discount;
double price;
Console::WriteLine(L"To create a store item, enter its information");
Console::Write(L"Item Number: ");
number = long::Parse(Console::ReadLine());
Console::WriteLine(L"Category");
Console::WriteLine(L"A - Audio Cables");
Console::WriteLine(L"B - Instructional and Tutorials (Books)");
Console::WriteLine(L"C - Cell Phones and Accessories");
Console::WriteLine(L"D - Bags and Cases");
Console::WriteLine(L"H - Headphones");
Console::WriteLine(L"I - Instructional and Tutorials (VHS & DVD)");
Console::WriteLine(L"M - Digital Cameras");
Console::WriteLine(L"O - Cables and Connectors");
Console::WriteLine(L"P - PDAs and Accessories");
Console::WriteLine(L"T - Telephones and Accessories");
Console::WriteLine(L"S - Surge Protector");
Console::WriteLine(L"V - TVs and Videos");
Console::Write(L"Your Choice? ");
category = __wchar_t::Parse(Console::ReadLine());
Console::Write(L"Make ");
make = Console::ReadLine();
Console::Write(L"Model: ");
model = Console::ReadLine();
Console::Write(L"Discount Applied (Enter 0 to 100, 0 if no discount): ");
discount = double::Parse(Console::ReadLine());
Console::Write(L"Unit Price: ");
price = double::Parse(Console::ReadLine());
CStoreItem ^ sItem = gcnew CStoreItem;
sItem->ItemNumber = number;
sItem->Category = category;
sItem->Make = make;
sItem->Model = model;
sItem->DiscountRate = discount;
sItem->UnitPrice = price;
return sItem;
}
// This function is used when an item is specified by its make and model
void DescribeStoreItem(CStoreItem ^ %item)
{
Console::WriteLine(L"Store Item Description");
Console::WriteLine(L"Item Number: {0}", item->ItemNumber);
Console::WriteLine(L"Category: {0}", item->Category);
Console::WriteLine(L"Make {0}", item->Make);
Console::WriteLine(L"Model: {0}", item->Model);
Console::WriteLine(L"Name: {0}", item->Name);
Console::WriteLine(L"Discount Rate: {0:P}", item->DiscountRate);
Console::WriteLine(L"Unit Price: {0:C}", item->UnitPrice);
}
// This function is used when an item is specified by its name
void DescribeStoreItem(CStoreItem ^ %item, const int)
{
Console::WriteLine(L"Store Item Description");
Console::WriteLine(L"Item Number: {0}", item->ItemNumber);
Console::WriteLine(L"Category: {0}", item->Category);
Console::WriteLine(L"Make {0}", item->Make);
Console::WriteLine(L"Model: {0}", item->Model);
Console::WriteLine(L"Discount Rate: {0:P}", item->DiscountRate);
Console::WriteLine(L"Unit Price: {0:C}", item->UnitPrice);
}
- Execute the application to test it. Here is an example:
To create a store item, enter its information
Item Number: 666802
Category
A - Audio Cables
B - Instructional and Tutorials (Books)
C - Cell Phones and Accessories
D - Bags and Cases
H - Headphones
I - Instructional and Tutorials (VHS & DVD)
M - Digital Cameras
O - Cables and Connectors
P - PDAs and Accessories
T - Telephones and Accessories
S - Surge Protector
V - TVs and Videos
Your Choice? V
Make Maxent
Model: MX-42VM11
Discount Applied (Enter 0 to 100, 0 if no discount): 5
Unit Price: 1250.50
Store Item Description
Item Number: 666802
Category: V
Make Maxent
Model: MX-42VM11
Discount Rate: 500.00 %
Unit Price: $1,250.50
Press any key to continue . . .
|
|
- Close the DOS window
Other Techniques of Implementing Properties |
|
Like a regular member variable, a property van be created as
static. To do this, precede its name with the static keyword. A static property
can implement only the behavior of a static member variable. Here is an example:
public ref class CComputerInventory
{
private:
static String ^ name;
public:
property static String ^ ComputerName
{
String ^ get() { return name; }
void set(String ^ nm) { name = nm; }
}
};
After creating a static property, you can access it outside
using the . or the -> operators. Because it is static, you can also access it
using the :: operator applied to the name of the class. Here are examples:
using namespace System;
public ref class CComputerInventory
{
private:
static String ^ name;
static String ^ mnUser;
public:
property static String ^ ComputerName
{
String ^ get() { return name; }
void set(String ^ nm) { name = nm; }
}
property static String ^ MainUser
{
String ^ get() { return mnUser; }
void set(String ^ user) { mnUser = user; }
}
};
void ListComputer(CComputerInventory ^ cInv)
{
Console::WriteLine(L"Computer Inventory");
Console::WriteLine(L"Computer Name: {0}", cInv->ComputerName);
Console::WriteLine(L"Main User: {0}", cInv->MainUser);
}
int main()
{
CComputerInventory ^ inv = gcnew CComputerInventory;
CComputerInventory::ComputerName = L"CNTLWKS228";
CComputerInventory::MainUser = L"Gertrude Monay";
ListComputer(inv);
Console::WriteLine();
return 0;
}
This would produce:
Computer Inventory
Computer Name: CNTLWKS228
Main User: Gertrude Monay
Press any key to continue . . .
As done for a primitive type, you can create a property that
is based on a class. If the class is managed, type the ^ operator between the
class's name and its property name. We will see an
example in Lesson 16.
All of the properties we have created so far were of
primitive types in the stack. You can also create a property in the managed
heap. To do this, type the ^ operator between its data type and its name.
When you derive a class from another, the new class inherits
the (public) properties of the parent class. This is one of the most valuable
characteristics of properties.
| |