C++类对象作为函数参数传递详解
我们知道了如何使用变量作为函数的实参,类对象也可以作为实参传递给函数。 例如,以下函数具有一个接收 Rectangle 对象的形参:
void displayRectangle(Rectangle r)
Rectangle box(15,10);
Length = 15 下面的程序说明了这一点: #include <iostream> #include <iomanip> #include <string> using namespace std; class InventoryItem { private: int partNum; // Part number string description; // Item description int onHand; // Units on hand double price; // Unit price public: void storeInfo(int p,string d,int oH,double cost); // Prototype int getPartNum() { return partNum; } string getDescription() { return description; } int getOnHand() { return onHand; } double getPrice() { return price; } }; void InventoryItem::storeInfo(int p,double cost) { partNum = p; description = d; onHand = oH; price = cost; } //Function prototypes for client program void storeValues (InventoryItem&);// Receives an object by reference void showValues (InventoryItem); // Receives an object by value int main() { InventoryItem part; // part is an Inventoryltem object storeValues(part); showValues(part); return 0; } void storeValues(InventoryItem &item) { int partNum; // Local variables to hold user input string description; int qty; double price; // Get the data from the user cout << "Enter data for the new part number n"; cout << "Part number: "; cin >> partNum; cout << "Description: "; cin.get(); getline (cin,description); cout << "Quantity on hand: "; cin >> qty; cout << "Unit price: "; cin >> price; item.storeInfo(partNum,description,qty,price); } void showValues(InventoryItem item) { cout << fixed << showpoint << setprecision(2) << endl; cout << "Part Number : " << item.getPartNum() << endl; cout << "Description : " << item.getDescription () << endl; cout << "Units On Hand: " << item.getOnHand () << endl; cout << "Price : $" << item.getPrice() << endl; }程序输出结果:
Enter data for the new part number 程序中还可以看到,Inventoryltem 类声明出现在 storeValues 和 showValues 函数的原型之前,这一点很重要,因为这两个函数都有一个 Inventoryltem 对象作为形参,所以编译器在遇到任何引用它的语句之前,必须知道 Inventoryltem 是什么,否则就会发生错误。 常量引用形参在上面的程序中,InventoryItem 对象按值传递给 showValues 函数。但是,按值传递对象需要复制所有对象成员的副本,这可能会减慢程序的执行时间,如果对象有很多成员,则更是如此。另一方面,当按引用传递对象时,由于该函数可以访问原始对象,而不必进行任何复制,所以它比通过值传递更快,正因为如此,一般更愿意按引用传递对象。但是,按引用传递对象有一个缺点,因为该函数可以访问原始对象,所以它可以调用其设置器函数更改对象成员数据。这就是为什么当程序员想要保护对象的内容时,通常不会按引用传递变量。 幸运的是这个问题有解决办法。为了保护对象让它作为实参传递,而又不必复制副本,可以将它作为常量引用进行传递,这意味着原始对象作为引用被传递给了函数,但是它不能调用任何设置器函数或更改对象的成员数据,它只能调用自己被指定为常量函数的访问器函数。 要将形参声明为常量引用形参,必须将关键字 const 放在函数原型和函数头的形参列表中。对照上面程序中的 showValues 函数的函数原型和函数头,如果将它改为使用常量引用形参,则语句如下:
void showValues (const InventoryItem&) //函数原型 double getPrice() const 如果 showValues 尝试调用任何其他 InventoryItem 函数,则会发生编译器错误。请注意,当 showValues 被修改为具有常量引用形参时,只有函数原型和函数头被更改为包含关键字 const。showValues 函数的主体和对 showValues 的调用不会改变。从函数返回一个对象正如函数可以编写为返回一个 int、double 或其他数据类型一样,它们也可以设计为返回一个对象。事实上,当以前从函数返回一个字符串时,就已经是在这样做了,因为字符串就是一个对象。当函数返回一个对象时,它通常会创建该类的局部实例,设置其数据成员,然后返回它。 以下仍以上面程序为例,说明如何在 storeValues 函数中创建 InventoryItem 对象,然后返回到调用函数。请注意,这个新版本的 storeValues 函数不接收任何实参,它的返回类型现在是 InventoryItem 而不是 void。 InventoryItem storeValues() { InventoryItem templtem; // Inventoryltem 局部对象 int partNum; //存储用户输入的局部变量 string description; int qty; double price; //在此编写获取用户输入的代码. //将数据保存到InventoryItem对象并返回它 tempItem.storeInfo(partNum,price); return tempItem; }main 函数随后应创建 part 语句,如下所示: InventoryItem part = storeValues(); 下面的程序修改了之前的程序,以纳入刚才讨论的技术。以前名为 storeValues 的函数被重命名为 createItem,因为它现在会创建一个名为 InventoryItem 的对象并将其返回给 main。showValues 函数现在接收 part 作为常量引用,而不是像以前一样按值传递它。#include <iostream> #include <iomanip> #include <string> using namespace std; class InventoryItem { private: int partNum; // Part number string description; // Item description int onHand; // Units on hand double price; // Unit price public: void storeInfo (int p,double cost);// Prototype int getPartNum () const { return partNum; } string getDescription() const { return description; } int getOnHand() const { return onHand; } double getPrice() const { return price; } }; void InventoryItem::storeInfo(int p,double cost) { partNum = p; description = d; onHand = oH; price = cost; } InventoryItem createItem(); // Returns an Inventoryltem object void showValues (const InventoryItem&); int main() { InventoryItem part = createItem (); showValues(part); return 0; } InventoryItem createItem() { InventoryItem tempItem;// Local Inventoryltem object int partNum; // Local variables to hold user input string description; int qty; double price; //Get the data from the user cout << "Enter data for the new part number n"; cout << "Part number: "; cin >> partNum; cout << "Description:"; cin.get(); getline(cin,description); cout << "Quantity on hand: "; cin >> qty; cout << "Unit price: "; cin >> price; tempItem.storeInfo(partNum,price); return tempItem; } void showValues(const InventoryItem &item) { cout << fixed << showpoint << setprecision(2) << endl; cout << "Part Number : " << item.getPartNum() << endl; cout << "Description : " << item.getDescription () << endl; cout << "Units On Hand: " << item.getOnHand () << endl; cout << "Price : $"<< item.getPrice () << endl; }程序输出结果:
Enter data for the new part number (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |