设为首页 加入收藏

TOP

C++哪些运算符重载可以重载?(二)
2015-07-20 17:35:28 来源: 作者: 【 】 浏览:5
Tags:哪些 运算 重载 可以
); TRACE_INTEGER(i); TRACE_INTEGER(--i); TRACE_INTEGER(i); TRACE_INTEGER(i++); TRACE_INTEGER(i); TRACE_INTEGER(i--); TRACE_INTEGER(i); TRACE_BOOL(i>j); TRACE_BOOL(i =j); TRACE_BOOL(i<=j); TRACE_HEX(i); TRACE_HEX(~i); TRACE_HEX(i<<4); TRACE_HEX(i>>4); TRACE_HEX(i<<24); TRACE_HEX(i & ~0xF); // i & ~0xF <<== same as ==>> i & Integer(~0xF), because C++ implicit conversion. TRACE_HEX(i | 0xF0); TRACE_HEX(i ^ 0xF0); TRACE_INTEGER(i); TRACE_INTEGER(j); TRACE_INTEGER(i=j); TRACE_INTEGER(i+=j); TRACE_INTEGER(i-=j); TRACE_INTEGER(i*=j); TRACE_INTEGER(i/=j); j = 3; TRACE_INTEGER(i%=j); } 该测试的输出如下:

i:	123
+i:	123
-i:	-123
i+j:	128
i-j:	118
i*j:	615
i/j:	24
i % :	3
++i:	124
i:	124
--i:	123
i:	123
i++:	123
i:	124
i--:	124
i:	123
i>j:	true
i
  
   =j:	true
i<=j:	false
i:	0000007B
~i:	FFFFFF84
i<<4:	000007B0
i>>4:	00000007
i<<24:	7B000000
i & ~0xF:	00000070
i | 0xF0:	000000FB
i ^ 0xF0:	0000008B
i:	123
j:	5
i=j:	5
i+=j:	10
i-=j:	5
i*=j:	25
i/=j:	5
i%=j:	2

  


模拟指针Pointer

再回想一下原生的指针支持那些运算?

具体有:

*,解引用,从T*得到T

[],下标运算

++,自增

--,自减

+,加法

-,减法

有一点值得注意的是:

每种类型都对应一种指针,如int对应int*;解引用和下标运算的返回结果可以做“左值”(赋值运算符左边的值,即可以赋值);指针的加减,-是以指针当前类型的大小为单位的,即:若有指针p,则 (size_t)(p + 1) == (size_t)p + sizeof(*p)

要实现1,Pointer类型必须实现为类模板;

Pointer实现为类模板,它的数据成员(data member)就可以是原生指针,可以很自然的支持原生指针的加减运算。

据此实现的Pointer类如下:

template 
  
   
class Pointer 
{
public:
	Pointer() : ptr_(0) {}
	Pointer(T* ptr) : ptr_(ptr) {}
	
	// operator T*() { return ptr_; } // implicit conversion.
	T* get() const { return ptr_; }	
	
	T& operator*() const { return *ptr_; }
	T* operator->() const { return ptr_; printf("operator->()\n"); }
	T& operator[](int offset) const { return ptr_[offset]; }
	
	Pointer
   
     operator++() { return Pointer(++ptr_); } // prefix Pointer
    
      operator--() { return Pointer(--ptr_); } // prefix Pointer
     
       operator++(int) { return Pointer(ptr_++); } // suffix Pointer
      
        operator--(int) { return Pointer(ptr_--); } // suffix Pointer
       
         operator+=(int off) { return Pointer(ptr_ += off); } Pointer
        
          operator-=(int off) { return Pointer(ptr_ -= off); } Pointer
         
           operator+(int off) const { return Pointer(ptr_ + off); } Pointer
          
            operator-(int off) const { return Pointer(ptr_ - off); } // private: T* ptr_; };
          
         
        
       
      
     
    
   
  

Pointer类仅模拟指针的一般运算,并没有考虑“通过指针进行资源管理”这一主题,所有也没有保证delete ptr的实际行为。


以下是该类的测试程序:

template
  
   
ostream& operator<<(ostream& out, const Pointer
   
    & ptr) { out << ptr.ptr_; return out; } //#define TRACE(fmt, exp) printf(#exp ":\t" fmt, (exp)) #define TRACE(exp) cout << #exp << ":\t" << (exp) << endl #define ARRAY_SIZE(a) sizeof(a)/sizeof(a[0]) int ia[] = { 123, 456, 789, 111, 222, 333 }; void testPointer() { for(int i=0; i
    
      ptr = &ia[0]; TRACE(ptr); TRACE(ia); TRACE(*ptr); TRACE(ptr[1]); TRACE(++ptr); TRACE(*ptr); TRACE(--ptr); TRACE(*ptr); TRACE(ptr++); TRACE(*ptr); TRACE(ptr--); TRACE(*ptr); TRACE(ptr+=2); TRACE(*ptr); TRACE(ptr-=2); TRACE(*ptr); ptr = &ia[3]; TRACE(ptr+2); TRACE(*(ptr+2)); TRACE(ptr-2); TRACE(*(ptr-2)); ptr[0] = 555; TRACE(ptr[0]); *ptr = 666; TRACE(*ptr); }
    
   
  

测试程序的输出如下:

0x603090: 123
0x603094: 456
0x603098: 789
0x60309c: 111
0x6030a0: 222
0x6030a4: 333
ptr:	0x603090
ia:	0x603090
*ptr:	123
ptr[1]:	456
++ptr:	0x603094
*ptr:	456
--ptr:	0x603090
*ptr:	123
ptr++:	0x603090
*ptr:	456
ptr--:	0x603094
*ptr:	123
ptr+=2:	0x603098
*ptr:	789
ptr-=2:	0x603090
*ptr:	123
ptr+2:	0x6030a4
*(ptr+2):	333
ptr-2:	0x603094
*(ptr-2):	456
ptr[0]:	555
*ptr:	666


上面的测试testPointer并没有用到operator->,下面单独测试operator->:

struct Foo 
{
	int id;
	static int count;
	
	Foo() : id(++count) { printf("Foo::Foo(%p)\n", this); }
	~Foo() { printf("Foo::~Foo(%p)\n", this); }
	
	void show() { printf("Foo.show(%p): %d\n", this, id); }
};

int Foo::count = 0;

void testAccess()
{
	printf("\n%s():\n", __FUNCTION__);
	Pointer
  
    fptr = new Foo();
	
	// test operator->
	fptr->show();     // access member function.
	TRACE(fptr->id);  //
首页 上一页 1 2 3 下一页 尾页 2/3/3
】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
分享到: 
上一篇c++ 对象的内存布局 下一篇POJ2386 Lake Counting(DFS)

评论

帐  号: 密码: (新用户注册)
验 证 码:
表  情:
内  容:

·PostgreSQL 索引 - (2025-12-25 22:20:43)
·MySQL Node.js 连接 (2025-12-25 22:20:41)
·SQL 撤销索引、表以 (2025-12-25 22:20:38)
·Linux系统简介 (2025-12-25 21:55:25)
·Linux安装MySQL过程 (2025-12-25 21:55:22)