c++中的引用的使用原理和实例(二)

操作方法

  • 01

    使用引用的时机。流操作符<<和>>、赋值操作符=的返回值、拷贝构造函数的参数、赋值操作符=的参数、其它情况都推荐使用引用。 这个程序里面到处都是&,也就是引用,引用当然可以不用了,老师会一一改变程序来说明这一点,但是使用引用就可以带来很多方便,或者说可以解决很多意想不到的问题。 程序最初给出的含错程序就是这样的,很长了: 头文件strngbad.h: // strngbad.h -- flawed string class definition #include <iostream> #ifndef STRNGBAD_H_ #define STRNGBAD_H_ class StringBad { private: char * str;                // pointer to string int len;                   // length of string static int num_strings;    // number of objects public: StringBad(const char * s); // constructor StringBad();               // default constructor ~StringBad();              // destructor // friend function friend std::ostream & operator<<(std::ostream & os, const StringBad & st); }; #endif 源文件strngbad.cpp : // strngbad.cpp -- StringBad class methods #include <cstring>                    // string.h for some #include \"strngbad.h\" using std::cout; // initializing static class member int StringBad::num_strings = 0; // class methods // construct StringBad from C string StringBad::StringBad(const char * s) { len = std::strlen(s);                  // set size str = new char[len + 1];          // allot storage std::strcpy(str, s);                   // initialize pointer[Page] num_strings++;                    // set object count cout << num_strings << \": \\\"\" << str << \"\\\" object created\\n\";    // For Your Information } StringBad::StringBad()                // default constructor { len = 4; str = new char[4]; std::strcpy(str, \"C++\");               // default string num_strings++; cout << num_strings << \": \\\"\" << str << \"\\\" default object created\\n\";  // FYI } StringBad::~StringBad()               // necessary destructor { cout << \"\\\"\" << str << \"\\\" object deleted, \"; // FYI --num_strings;                    // required cout << num_strings << \" left\\n\"; // FYI delete [] str;                    // required } std::ostream & operator<<(std::ostream & os, const StringBad & st) { os << st.str; return os; } 这个函数在调用的时候不会再调用别的函数,因为他在调用的时候,进行的是地址的传递,main中的调用语句是:callme1(headline1);其实就是把headline1的地址传递给rsb这个变量,使用的是引用,这样就使得,两者的地址和值都是一样的,就是c/c++中的很简单的一个引用级别的地址传递,不调用其他函数。 再看函数里面的cout这个东西,这个东西在其他的地方也看到过,但是这个地方跟其他的地方的变量有点区别的,他在这里是用的是类StringBad里面的一个友员函数,而不是简单的标准的io流,具体的看StringBad里面的定义。 下面的这个调用就有点问题了,这个就有一个传值和赋值的问题了。如果是一个简单的内置变量类型的传值和赋值就是可以直接的进行也不要调用其他的函数,或者说即使调用也不会出现我们无法控制的问题,这里就不同了,他会再调用一个隐式复制函数,如果作者没有给定显式复制函数的话 void callme2(StringBad sb);    // pass by value 这个函数在程序里面使用过一次,问题在这里就开始产生headline2传递给sb之后进行赋值,就是StringBad sb=headline2,注意了,StringBad  sb=headline2和StringBad  sb;sb =headline2;这样的写法是不一样的,后面讲。 上面已经说过了,如果没有显式的复制函数就会自动调用或者说系统会帮你构造一个隐式复制函数,呵呵系统对我们真的好,有的时候这个好就出了问题了,这个好也就是程序的运行结果里面为什么会出现乱码,以及出现析构时的-1,-2 的缘故。 看看构造函数: 每次构造一个类对象的时候就会把num_strings++执行,增加计数。 在新建一个对象并将其用另一个同类类对象初始化的时候都会调用复制构造函数StringBad::StringBad(const StringBad &st),就是看时隐式还是显式的了。 隐式的没有显示的那么符合人的意思了,他就是复制而且给值,我们要求num_strings++但是他能做的就是最基本的给值,不会帮我们++这么一下。这个时一个方面,另一个方面才是最恐怖的,就是系统自己给我们的隐式复制函数是临时的!临时的是什么意思?就是说,当一个变量活到头了就要消失了: StringBad  sb=headline2 这个语句会执行,把headline2的成员的量都给sb以后,就要执行析构函数,把sb给析构了,但是headline和sb的str字符串指针都是指向的一个位置,那么当把sb给析构的同时,headline也被析构了,再要用std::ostream & operator<<(std::ostream & os, const StringBad & st)这个函数来显示str量就不对了,因为要对一个已经不存在的地址进行读或者写都是会导致异常的。这个就是后来的乱码的来由! [NextPage] 怎么办? 给出显示的复制构造函数:可以用指针的也可以用引用的: 由于StringBad  sb=headline2相当于:StringBad sb=StringBad::StringBad(headline2),那么这么构造: 这个是引用的,指针的就后来再看。 错误已经解决的差不多了,下面还有一个问题,    StringBad knot;    knot = headline1;这两条语句就跟上面的StringBad sb=headline2不一样了,起码过程不一样,分为两步,第一步就是初始化knot,这个由默认构造函数执行,第二步就是knot = headline1赋值,这个也没有给出函数原型,系统又来帮忙了,帮我们构造隐式的一些构造函数,这个也是我们看不见的,所以我们要自己来给出一个成员函数或者友员函数。 成员函数: StringBad & StringBad::operator=(const StringBad  &st) { if (this == &st) return *this; delete [] str; len = st.len; str = new char[len + 1]; strcpy(str, st.str); return *this; } 也是用了引用的形式,使用的是重载赋值符号。到这里差不多可以给出完整的正确的程序了: 为大家分享源文件strngbad.cpp :#endif

(0)

相关推荐

  • 在Word文档中添加引用内容

    随着电脑的普及,办公软件也是越来越收到人们的青睐.下面是一些在Word文档中添加引用内容的步骤,希望可以帮到经常用办公软件的朋友们. 操作方法 01 选中并且打开所需要的word文档,并且将光标移动到 ...

  • excel中绝对引用,相对引用,与快捷键相对引用图文教程

    我们在用excel处理数据的过程中,经常要用到拖拽单元格以进行公式复制,引用的数据是已有单元格中的数据,我们可能需要: 1)绝对引用,就是指引用某一单元格的数值,不随着拖拽而变成引用了其他数值 2)也 ...

  • word毕业论文中的引用怎么插入?

    word毕业论文中的引用怎么插入?

  • Excel中循环引用的用法

    Excel中循环引用的用法 提到循环引用,恐怕很多同学都不会陌生,而且会敬而远之.在Excel中输入公式时,经常会遇到下面的提示框,这就是因为公式中有循环引用的问题导致的. 通常情况下,如果公式中包含 ...

  • word文档中毕业论文中的引用怎么插入?

    word文档中毕业论文中的引用怎么插入? 1.首先打开word文档 2.找到你需要进行注释或者你引用的话语,选中他们. 3.然后找到左上角的如下图中 的引用,点开 4.点开引用之后,你会发现有插入尾注 ...

  • excel中indirect引用工作表返回ref错误值该怎么办?

    excel中indirect引用工作表错误的解决方法 1.打开一个工作样表作为例子.如图所示: 2.输入indirect函数公式跨工作表引用.可以直接使用鼠标点击.如图所示: 3.返回了一个ref错误 ...

  • 一招教你在Word中自动引用参考文献

    相信很多小伙伴在日常办公中都会用到Word,那么在其中我们怎么自动引用参考文献呢?方法很简单,下面小编就来为大家介绍.具体如下:1. 首先,打开Word,在其中打开要进行操作的文档,下面小编就会在下图 ...

  • 怎么在Word文档中添加引用文献

    Word是现在十分常用的文件类型之一,有些新用户不知道怎么在Word文档中添加引用文献,接下来小编就给大家介绍一下具体的操作步骤.具体如下:1. 首先第一步打开电脑浏览器,根据下图箭头所指,搜索并进入 ...

  • 表格中绝对引用和相对引用的区别(excel表格绝对引用相对引用)

    最基础的教程来了!!!在日常excel教学中,大家常会听到各位大佬文案中出现"$"以及"F4"键的运用,然后留下一脸懵逼的自己独自百度,出现什么"绝对 ...