参考:http://www.weixueyuan.net/view/6384.html

总结:

  下标操作符是必须要以类的成员函数的形式进行重载的。其在类中的声明格式如下:
      返回类型 & operator[] (参数)
  或
      const 返回类型 & operator[] (参数) const    ,  后面的 const可使两函数是不同的函数,编译器可以分辨出来。

  如果使用第一种声明方式,操作符重载函数不仅可以访问对象,同时还可以修改对象。如果使用第二种声明方式,则操作符重载函数只能访问而不能修改对象。如语句“arr[5] = 7;”语句是无效的,

  非const成员函数不能处理const对象,这也是第二种的应用场景之一。

---------------------------

在前面已经提到下标操作符是必须要以类的成员函数的形式进行重载的。其在类中的声明格式如下:
    返回类型 & operator[] (参数)
或
    const 返回类型 & operator[] (参数)

如果使用第一种声明方式,操作符重载函数不仅可以访问对象,同时还可以修改对象。如果使用第二种声明方式,则操作符重载函数只能访问而不能修改对象。

在我们访问数组时,通过下标去访问数组中的元素并不具有检查边界溢出功能,我们可以重载下标操作符使之具有相应的功能。

例1:

#include<iostream>
#include<string>
using namespace std; class Array
{
public:
Array(){length = ; num = NULL;};
Array(int n);
int & operator[]( int );
const int & operator[]( int )const;
int getlength() const {return length;}
private:
int length;
int * num;
}; Array::Array(int n)
{
try
{
num = new int[n];
}
catch(bad_alloc)
{
cerr<<"allocate storage failure!"<<endl;
throw;
}
length = n;
} int& Array::operator[](int i)
{
if(i < || i >= length)
throw string("out of bounds");
return num[i];
} const int & Array::operator[](int i) const
{
if(i < || i >= length)
throw string("out of bounds");
return num[i];
} int main()
{
Array A();
int i;
try
{
for(i = ; i < A.getlength(); i++)
A[i] = i;
for(i = ;i < ; i++ )
cout<< A[i] <<endl;
}
catch(string s)
{
cerr<< s <<", i = "<< i <<endl;
} return ;
}

本例中定义了一个Array类,表示的是一个整形数组,在类中我们重载了下标操作符,使之具备检测下标溢出的功能。在类中为了方便我们使用了string类,这个类将在后面会进行详细介绍,在这里可以将其对象理解为一个字符串。在本例中重载下标操作符,我们提供了两个版本的重载下标操作符函数:
    int & operator[]( int );
    const int & operator[]( int )const;

需要注意的是第一个下标操作符重载函数最后面不带有const,加上const意味着该成员函数是常成员函数,如果第一个函数后面也加上了const,则两个函数仅有返回值不相同,这个不足以用于区分函数,编译器会提示语法错误。这两种版本的下标操作符重载函数其实很好理解,一个是可以修改类对象,下面一个则只可以访问对象而不能修改对象。对于上面一种下标操作符重载函数的声明,以下两个语句都是有效的:
    arr[5] = 7;
    int var = arr[3];

换言之,我们既可以访问类对象,同时又能修改类对象。“arr[5]”其实可以理解为:
    arr.operator[]( 5 )

而对于下面一种下标操作符重载函数,我们不能修改对象,也就是说语句“arr[5] = 7;”语句是无效的,但是它依然可以用于访问对象,因此“int var = arr[3];”语句仍然有效。

我们再来看一下下标操作符重载函数的定义,在函数体内部,先进行下标越界检测,如果出现越界则抛出异常,否则就返回下标 i 所对应的数据。这两种版本的下标操作符重载函数的函数定义都是如此。

我们来看一下程序输出结果:
    0
    1
    2
    3
    4
    out of bounds, i = 5

在例1中即使我们没有定义const版本的,上面的例子也是可以正确运行的,但是非const成员函数不能处理const对象,因此通常我们在设计程序时,会同时提供两种版本的操作符重载函数。在例1中如果我们增添下面一个display顶层函数,用于打印对象数组中的所有元素。

void display(const Array & A)
{
for(int i=; i < A.getlength(); i++)
cout<< A[i] <<endl;
}

此时如果我们在例1中没有定义const版本的下标操作符重载函数,则例1将会出现语法错误而无法编译通过的。

5.6 C++重载下标操作符的更多相关文章

  1. 【c++习题】【17/5/22】重载数组下标操作符

    一.写出程序运行结果 1#include <iostream > using namespace std; int a[10]={1,2, 3, 4, 5, 6, 7, 8, 9, 10} ...

  2. C++ 之 重载赋值操作符

    Widget 类中,定义了一个 Bitmap 类型的私有数据成员 -- pb 指针 class Bitmap { ... }; class Widget { private: Bitmap *pb; ...

  3. C++中复制构造函数与重载赋值操作符总结

    前言 这篇文章将对C++中复制构造函数和重载赋值操作符进行总结,包括以下内容: 1.复制构造函数和重载赋值操作符的定义: 2.复制构造函数和重载赋值操作符的调用时机: 3.复制构造函数和重载赋值操作符 ...

  4. C++中复制构造函数与重载赋值操作符

    我们都知道,在C++中建立一个类,这个类中肯定会包括构造函数.析构函数.复制构造函数和重载赋值操作:即使在你没有明确定义的情况下,编译器也会给你生成这样的四个函数.例如以下类:   class CTe ...

  5. 5.9 C++重载转型操作符

    参考:http://www.weixueyuan.net/view/6387.html 注意: 转型构造函数可以将其它类型的参数转换为类类型,如果我们要进行相反的转换过程,将类类型转换为其它数据类型, ...

  6. 5.5 C++重载赋值操作符

    参考:http://www.weixueyuan.net/view/6383.html 总结: 重载赋值操作符同重载类的是拷贝构造函数的原因是一样,将一个对象拷贝给另一个对象,同时当类中存在指针类型的 ...

  7. 【c++】c++中重载输出操作符,为什么要返回引用

    针对:ostream & operator <<(ostream & os, const ClassType &object) 说明几点: 1.第一个形参为对ost ...

  8. Effective C++(10) 重载赋值操作符时,返回该对象的引用(retrun *this)

    问题聚焦: 这个准则比较简短,但是往往就是这种细节的地方,可以提高你的代码质量. 细节决定成败,让我们一起学习这条重载赋值操作符时需要遵守的准则吧. 还是以一个例子开始: Demo // 连锁赋值 x ...

  9. C++ 重载操作符- 02 重载输入输出操作符

    重载输入输出操作符 本篇博客主要介绍两个操作符重载.一个是 <<(输出操作符).一个是 >> (输入操作符) 现在就使用实例来学习:如何重载输入和输出操作符. #include ...

随机推荐

  1. stm32复位引脚NRST

    STM32F的NRST是异步复位脚. 当NRST输入低电平的时候,MCU处于复位状态,重设所有的内部寄存器,及片内几十KB的SRAM. 当NRST从低电平变高时,PC指针从0开始. 但是复位的时候不会 ...

  2. 用C#实现多种方式播放Wav声音

    using System; using System.Collections.Generic; using System.ComponentModel; using System.Data; usin ...

  3. Lab 1-1

    LABS The purpose of the labs is to give you an opportunity to practice the skills taught in the chap ...

  4. p1218 Superprime Rib

    深搜,添加数字后如果仍为质数,继续递归. #include <iostream> #include <cstdio> #include <cmath> #inclu ...

  5. android -------- ConstraintLayout 宽高比和偏移量比(三)

    前面的文章 ConstraintLayout 介绍 (一) ConstraintLayout约束属性 (二) 此博文主要讲解: app:layout_constraintHorizontal_bias ...

  6. use . adb . get wifi

    adb shell 连接手机获取root权限,如果返回的字符串中不包含root字样,再输入su命令回车 继续输入cat /data/misc/wifi/*.conf命令,将会把文件打印出来 ssid表 ...

  7. 【IDEA】【4】遇到的问题

    前言: 1,jar包未导入到项目中 2,报错 cannot resolve symbol 3,左边栏只能看到文件看不到项目结构 4,报错 No valid Maven installation fou ...

  8. 时间选择控件YearPicker(基于React,antd)

    不知道为什么蚂蚁金服团队没有在ant design的DatePicker中单独给出选择年份的组件,这给我们这种懒人造成了很大的痛苦,自己手造轮子是很麻烦的.毕竟只是一个伸手党,emmmmm..... ...

  9. canvas移动端兼容性问题总结

    项目简介:在网页利用canvas在图片中动态绘制文字,合成一张图片,并导出 遇到的问题: 1.在移动端canvas drawImage()方法图片无法绘制出来,只显示文字 原因:图片未加载就进行绘制, ...

  10. python-day72--django实现的cookie/session

    COOKIE 与 SESSION 一.概念cookie不属于http协议范围,由于http协议无法保持状态,但实际情况,我们却又需要“保持状态”,因此cookie就是在这样一个场景下诞生.cookie ...