派生类的this指针能不能直接指向基类的指针指向派生类私有数据,因为我重载+运算符的时候想让基类的指针指向派生类数据也相加,

C++编程指向成员的指针以及this指针的基本使用指南
指向成员的指针
指向成员的指针的声明是指针声明的特例。使用以下序列来声明它们:
[storage-class-specifiers] [cv-qualifiers] type-specifiers [ms-modifier]
qualified-name ::* [cv-qualifiers] identifier
[= & qualified-name :: member-name];
声明说明符:
可选存储类说明符。
可选 const 和/或 volatile 说明符。
类型说明符:类型的名称。这是要指向的成员的类型,而不是类。
可选的 Microsoft 专用修饰符。
包含要指向的成员的类的限定名。
:: 运算符。
* 运算符。
可选 const 和/或 volatile 说明符。
命名指向成员的指针的标识符。
可选的初始值设定项:
= 运算符。
& 运算符。
类的限定名。
:: 运算符。
适当类型的类的非静态成员的名称。
像往常一样,允许在单个声明中使用多个声明符(以及任何关联的初始值设定项)。
指向类的成员的指针与普通指针不同,因为它有该成员的类型的类型信息和该成员所属的类的类型信息。常规指针只标识内存中的一个对象或只具有其地址。指向类的某个成员的指针标识类的所有实例中的该成员。以下示例声明类、Window 和一些指向成员数据的指针。
// pointers_to_members1.cpp
class Window
// Default constructor.
Window( int x1, int y1,
// Constructor specifying
int x2, int y2 );
// window size.
bool SetCaption( const char *szTitle ); // Set window caption.
const char *GetCaption();
// Get window caption.
char *szWinC
// Window caption.
// Declare a pointer to the data member szWinCaption.
char * Window::* pwCaption = &Window::szWinC
int main()
在前面的示例中,pwCaption 是一个指针,它指向具有 Windowchar* 类型的类 的任何成员。类型 pwCaption 不是 char * Window::*。下一个代码片段将指针声明为 SetCaption 和 GetCaption 成员函数。
const char * (Window::*pfnwGC)() = &Window::GetC
bool (Window::*pfnwSC)( const char * ) = &Window::SetC
指针 pfnwGC 和 pfnwSC 分别指向 GetCaption 类的 SetCaption 和 Window。以下代码直接使用指向成员 pwCaption 的指针将信息复制到窗口标题:
Window wMainW
Window *pwChildWindow = new W
char *szUntitled = "Untitled - ";
int cUntitledLen = strlen( szUntitled );
strcpy_s( wMainWindow.*pwCaption, cUntitledLen, szUntitled );
(wMainWindow.*pwCaption)[cUntitledLen - 1] = '1';
//wMainWindow.SzWinCaption [cUntitledLen - 1] = '1';
strcpy_s( pwChildWindow-&*pwCaption, cUntitledLen, szUntitled );
(pwChildWindow-&*pwCaption)[cUntitledLen - 1] = '2'; //same as //pwChildWindow-&szWinCaption[cUntitledLen - 1] = '2';
.* 和 C&* 运算符(指向成员的指针运算符)的区别在于 .* 运算符选择成员给定的对象或对象引用,而 C&* 运算符通过指针选择成员。(有关这些运算符的更多信息,请参阅使用指向成员的指针运算符的表达式。)
指向成员的指针运算符的结果是成员的类型 - 本例中为 char *。
以下代码片段使用指向成员的指针调用成员函数 GetCaption 和 SetCaption:
// Allocate a buffer.
sizeOfBuffer = 100
char szCaptionBase[sizeOfBuffer];
// Copy the main window caption into the buffer
// and append " [View 1]".
strcpy_s( szCaptionBase, sizeOfBuffer, (wMainWindow.*pfnwGC)() );
strcat_s( szCaptionBase, sizeOfBuffer, " [View 1]" );
// Set the child window's caption.
(pwChildWindow-&*pfnwSC)( szCaptionBase );
针对指向成员的指针的限制
静态成员的地址不是指向成员的指针。它是指向静态成员的一个实例的常规指针。由于给定类的所有对象只存在一个静态成员实例,因此可以使用普通的 address-of (&) 和取消引用 (*) 运算符。
指向成员和虚函数的指针
通过指向成员函数的指针调用虚函数就如同直接调用函数一样;将在 v 表中查找并调用正确的函数。
一直以来,虚函数工作的关键是通过指向基类的指针来调用它们。(有关虚函数的详细信息,请参阅虚函数。)
以下代码演示如何通过指向成员函数的指针调用虚函数:
// virtual_functions.cpp
// compile with: /EHsc
#include &iostream&
class Base
virtual void Print();
void (Base ::* bfnPrint)() = &Base :: P
void Base :: Print()
cout && "Print function for class Base\n";
class Derived : public Base
void Print(); // Print is still a virtual function.
void Derived :: Print()
cout && "Print function for class Derived\n";
int main()
Derived dO
bPtr = &bO // Set pointer to address of bObject.
(bPtr-&*bfnPrint)();
bPtr = &dO // Set pointer to address of dObject.
(bPtr-&*bfnPrint)();
//Output: Print function for class Base
Print function for class Derived
this 指针是只能在 class、struct或 union 类型的非静态成员函数中访问的指针。它指向为其调用成员函数的对象。静态成员函数没有 this 指针。
this-&member-identifier
对象的 this 指针不是对象的一部分;它没有在对象上的 sizeof 语句的结果中反映。相反,当对某个对象调用非静态成员函数时,该对象的地址将由编译器作为隐藏的参数传递给函数。例如,以下函数调用:
myDate.setMonth( 3 );
可以按以下方式解释:
setMonth( &myDate, 3 );
对象的地址可从成员函数的内部作为 this 指针提供。 this 的大多数使用都是隐式的。在引用类的成员时显式使用 this 是合法的,但没有必要。例如:
void Date::setMonth( int mn )
// These three statements
this-&month =
// are equivalent
(*this).month =
表达式 *this 通常用于从成员函数返回当前对象:
this 指针还用于防止自引用:
if (&Object != this) {
// do not execute in cases of self-reference
由于 this 指针无法更改,因此不允许对 this 赋值。C++ 的早期实现允许对 this 赋值。
this 指针有时可直接使用 - 例如,当操作自引用数据结构,而其中需要当前对象的地址时。
// this_pointer.cpp
// compile with: /EHsc
#include &iostream&
#include &string.h&
Buf( char* szBuffer, size_t sizeOfBuffer );
Buf& operator=( const Buf & );
void Display() { cout && buffer && }
size_t sizeOfB
Buf::Buf( char* szBuffer, size_t sizeOfBuffer )
sizeOfBuffer++; // account for a NULL terminator
buffer = new char[ sizeOfBuffer ];
if (buffer)
strcpy_s( buffer, sizeOfBuffer, szBuffer );
sizeOfBuffer = sizeOfB
Buf& Buf::operator=( const Buf &otherbuf )
if( &otherbuf != this )
if (buffer)
sizeOfBuffer = strlen( otherbuf.buffer ) + 1;
buffer = new char[sizeOfBuffer];
strcpy_s( buffer, sizeOfBuffer, otherbuf.buffer );
int main()
Buf myBuf( "my buffer", 10 );
Buf yourBuf( "your buffer", 12 );
// Display 'my buffer'
myBuf.Display();
// assignment opperator
myBuf = yourB
// Display 'your buffer'
myBuf.Display();
your buffer
this 指针的类型
通过 const 和 关键字,可以在函数声明中修改 volatilethis 指针的类型。若要将函数声明为具有一个或多个关键字的特性,请将关键字添加到函数参数列表的后面。
请看以下示例:
// type_of_this_pointer1.cpp
class Point
unsigned X()
int main()
上面的代码声明一个成员函数 X,其中,this 指针被视为指向 const 对象的 const 指针。可以使用 cv-mod-list 选项的组合,但它们始终通过 this 修改指向的对象,而不是 this 指针本身。因此,以下声明将声明函数 X;this 指针是指向 const 对象的 const 指针:
// type_of_this_pointer2.cpp
class Point
unsigned X()
int main()
成员函数中 this 指针的类型由以下语法描述,其中,cv-qualifier-list 是从成员函数声明符中确定的,可以是 const 和/或 volatile,而 class-type 是类的名称:
[cv-qualifier-list] class-type * const this
换言之,this 始终是 const 指针;无法重新指派它。成员函数声明中使用的 const 或 volatile 限定符适用于由该函数范围中的 this 指向的类实例。
下表介绍了有关这些修饰符的工作方式的更多信息。
this 修饰符的语义
不能更改数据成员;无法调用不是 const 的成员函数。
每次访问成员数据时,都会从内存中加载该数据;禁用某些优化。
将 const 对象传递给不是 const 的成员函数是错误的。同样,将 volatile 对象传递给不是 volatile 的成员函数也是错误的。
声明为 const 的成员函数不能更改数据成员 - 在此类函数中,this 指针是指向 const 对象的指针。
构造函数和析构函数不能声明为 const 或 volatile。但是,可以在 const 或 volatile 对象上调用它们。
相关报道:
本站地址:
责任编辑:
已有位网友参与评论
本类周最热
分类导航: |
软件名称软件类别好评率
本站所有资源均来自互联网,本站只做收集,如本站侵犯到您的版权请发送邮件给我们,我们收到邮件后会在第一时间删除!商务QQ:1674653
Copyright (C)C++类中的this指针(转)
先要理解class的意思。class应该理解为一种类型,象int,char一样,是用户自定义的类型。(虽然比int
char这样build-in类型复杂的多,但首先要理解它们一样是类型)。用这个类型可以来声明一个变量,比如int x, myclass
my等等。这样就像变量x具有int类型一样,变量my具有myclass类型。
理解了这个,就好解释this了,my里的this
就是指向my的指针。如果还有一个变量myclass mz,mz的this就是指向mz的指针。 这样就很容易理解this
的类型应该是myclass
*,而对其的解引用*this就应该是一个myclass类型的变量。通常在class定义时要用到类型变量自身时,因为这时候还不知道变量名(为了通用也不可能固定实际的变量名),就用this这样的指针来使用变量自身。&
1. this指针的用处:
一个对象的this指针并不是对象本身的一部分,不会影响sizeof(对象)的结果。this作用域是在类内部,当在类的非静态成员函数中访问类的非静态成员的时候,编译器会自动将对象本身的地址作为一个隐含参数传递给函数。也就是说,即使你没有写上this指针,编译器在编译的时候也是加上this的,它作为非静态成员函数的隐含形参,对各成员的访问均通过this进行。例如,调用date.SetMonth(9)
&===& SetMonth(&date,
9),this帮助完成了这一转换。
this指针的使用:
一种情况就是,在类的非静态成员函数中返回类对象本身的时候,直接使用
return *this;另外一种情况是当参数与成员变量名相同时,如this-&n = n (不能写成n
3.this指针程序示例:&
this指针是存在与类的成员函数中,指向被调用函数所在的类实例的地址。&
根据以下程序来说明this指针
#include&iostream.h&
class Point
& Point(int a, int b) { x=a; y=b;}
& Void MovePoint( int a, int b){ x+=a;
& Void print(){
cout&&"x="&&x&&"y="&&y&&}
void main( )
&& Point point1( 10,10);
&& point1.MovePoint(2,2);
&& point1.print( );
当对象point1调用MovePoint(2,2)函数时,即将point1对象的地址传递给了this指针。
MovePoint函数的原型应该是 void MovePoint( Point *this, int a, int
b);第一个参数是指向该类对象的一个指针,我们在定义成员函数时没看见是因为这个参数在类中是隐含的。这样point1的地址传递给了this,所以在MovePoint函数中便显式的写成:
void MovePoint(int a, int b) { this-&x +=a;
this-& y+=}
即可以知道,point1调用该函数后,也就是point1的数据成员被调用并更新了值。
即该函数过程可写成 point1.x+= point1. y + =
关于this指针的一个精典回答:
当你进入一个房子后,
你可以看见桌子、椅子、地板等,
但是房子你是看不到全貌了。
对于一个类的实例来说,
你可以看到它的成员函数、成员变量,
但是实例本身呢?
this是一个指针,它时时刻刻指向你这个实例本身。
--------------------------------------------------------------------------------------
this 可以直接访问一个隐藏的指针,这个指针就称为 this
指针。它实际上是类定义中一个缺省的预定义的指针。当调用一个成员函数时,系统保证this
指针始终指向产生这个调用的对象,并将该指针作为一个变元自动传递给该函数。同时,只有对象和成员函数之间才存在 this
【示例】下面一段程序创建一个叫做power的类来计算一个数的幂:
&&& double b,
&&& power(double
base, int exp);
&&& double
get_power() {}
&power::power(double base int exp)
&& val = 1;
&& if(exp == 0)
&& for(; exp & 0;
val = val *}
&void main()
&& power x(4.0, 2), y(2.5, 1),
z(5.7, 0);
cout && x.get_power()
&& y.get_power()
cout && z.get_power()
&在一个类的成员函数内部(如power()),可以直接引用一个类的数据成员,而无需用任何对象或类的限制性说明。所以在
power 类的构造函数 power() 里语句b = 意味着参数 base 的值将被赋予产生这个调用的对象中的数据成员
b。在程序中分别定义了 power 的三个对象 x、y
和z,编译器将对象的成员函数与同一对象的数据成员在调用时联系在一起,为此编译器实际上给成员函数传递了一个隐藏的指向函数调用所要引用的对象的指针,即
this 指针。相同的语句可以改写如下:
这表明,当发生函数调用时(例如当新建一个 power 类的对象x时),编译器传给构造函数 power() 一个指向对象 x 的
this 指针,并隐式地使用这个指针访问属于对象x的b的拷贝。其实上述 power() 函数中的 b=base
等语句只是简写形式,下面是用 this 指针改写的完整的 power()函数:
&power::power(double base , int
& this-&e =
this-&val = 1;
& if(exp == 0)
& for(; exp&0; exp--)
this-&val =
this-&val*this-&b;
在这个例子中,数据成员的名字前缀表达式 this-& 是合法的但没有什么效果,因为this
指针的使用本来就是隐式的。友元函数不是类的成员,而且没有this指针,静态成员函数也没有 this 指针。但在另一些情况下,必须用
this 指针明确当前调用的对象,如在重载运算符时,可以看到 this
指针是非常重要的,它在某些类型的链表管理中往往也是必要的
--------------------------------------------------------------------------------------
this在成员函数的开始前构造,在成员的结束后清除。
这个生命周期同任何一个函数的参数是一样的,没有任何区别。
因为,成员函数默认第一个参数就是this。
class & A{
func(int & p){}
func的原型在编译器看来,应该是
int & func(A* & const
& this, & int &
即开始执行成员函数之前,构造。
成员函数执行结束,清除。
如果class或者struct里没有成员函数,this是没有构造函数的。只能当作C的STRUCT使用
Primer》,找“this指针”章节
C++,this指针问题~
this指针的使用:
一种情况就是,在类的非静态成员函数中返回类对象本身的时候,直接使用 return
*this;另外一种情况是当参数与成员变量名相同时,如this-&n = n (不能写成n =
这个:this-&n =
在这样的形式下,哪个n是成员变量? 哪个n是参数?
我看了几篇文章,说法都不一致哟~
彻底整得头大了。
class figure{
vitual double getArea()=0;
class rectangle:public figure{
protected:
rectangle(){};
rectangle(double height,double width){
this-&height=
this-&width=
double getArea()
{return height*}
class square:public rectangle{
square(double width){
height=this-&width=
如现在figure *figures[2]={new rectange(5,6),new square(5)};
for (int i=1;i&3;i++)
cout&&(figures[i])-&getArea()&&
到底是如何传参的哟?简单说说就行,不胜感激~或直接说明前面问题就行了~谢谢啦~
问题补充:到底哪个叫成员变量哟?
protected:
还是double width?
这样说来是square(double width)那儿的width叫做成员变量喽?如果这样讲就通了。
最佳答案:
其实很简单啊。先回答你前面的问题吧,this-&n = n
;显然是第一个n是成员变量阿。难到你不知道-〉是数据访问符么。
在说一说,你列举的具体实例吧。figure *figures[2]={new rectange(5,6),new
square(5)};
这一句,似乎很复杂,其实不然。我们知道类的赋值原则中有这样的一条,就是派生类指针可以赋值给基类指针。而这条语句中,*figures[2]是一个指针数组,就是含有两个基类指针的数组。在花括号里是对他们赋值。new
rectange(5,6),new square(5)}; 第一个是调用
rectangle构造函数.建立了一个height=5,width=6的长方形(rectangle);第二个是调用了square的构造函数。
square(double width){
height=this-&width=
其实你前面说的话已经对这个问题给予了解决,即当菲静态成员函数的参数与成员变量名相同时要用this指针(显示调用)。显然不相同的时候是隐式调用的。height=this-&width=width就是说对象的成员变量height,width.均被形参赋予相同的值。
square是从rectangle那里派生出来的,因而它的成员变量为height和width,那一句只是叫长和宽都等于参数值。我想height不用this-&height是因为没有与它同名的参数吧。height=this-&width=width为什么不是
thie-&height=this-&width=width 因为它不是
height=height这种形式了。
已投稿到:
以上网友发言只代表其个人观点,不代表新浪网的观点或立场。C++必知必会 - 指向类的数据成员的指针并非指针
C++必知必会 - 指向类的数据成员的指针并非指针
普通指针使用*来标示,而指向类的成员函数的指针使用ClassName::*标示。需要注意的是,指向类的数据成员的指针并非指针,因为它既不包含地址,行为也不像指针 。与常规指针不同,一个指向成员的指针并不指向一个具体的内存位置,它指向的是一个类的特定成员,而不是指向一个特定对象里的特定成员。通常最清晰的做法是将指向数据成员的指针看作 为一个偏移量 。 C++标准并没有说该如何实现指向成员的指针,大多数编译器都将指向数据成员的指针实现为一个整数,其中包含被指向成员的偏移量。另外加上1(加1是为了让0值可以表示一个空的数据成员指针)。 这个偏移量告诉你,一个特定成员的位置距离对象的起点有多少个字节。一个类成员的偏移量在任何对象中都是相同的。给定一个成员在类内的偏移量,为了访问位于那个偏移量的数据成员,我们需要该类的一个对象的地址。这时候就需要.*和-&*这两个看上去非同寻常的操作符闪亮登场了。//------& & class C { && & & public: && & & & //...& & & & int a_; && & }; && & int C::*pimC; // 一个指针,指向C的一个int成员 && & C aC; && & C * pC = &aC; && & pimC = &C::a_; && & aC.* pimC = 0 ; && & int b = pC - & *pimC;//------当写下pC-&*pimC时,其实是请求将pC内的地址加上pimC内的偏移量,为的是访问pC所指向的C对象中适当的数据成员。当写aC.*pimC时,是在请求aC的地址加上pimC中的偏离量,也是为了访问pC所指向的C对象中适当的数据成员.&另外,存在从指向基类成员的指针到指向公有派生类成员的指针的隐式转换,但不存在从指向派生类成员的指针到指向其任何一个基类成员的指针的转换。这个可以从c++对象的内存布局来理解,因为基类成员一般在子类对象的前部分,所以这些成员在基类或者子类中的偏移是一样的;解析的时候,就是对象的首地址加上这个偏移量来获得真正的数据成员:理解了这一点,你就知道有虚继承的类中,与虚基类的相关转化是非法的。同样,指向类的非静态 成员函数的指针也不是指针,不是一个地址,而是一个指向成员函数的指针 。为了访问该成员,需要将对象的地址(this指针)和成员的偏移量(包含于指向数据成员的指针中)相加。对于指向成员函数的指针的情形,需要将对象的地址用作(或用于计算)this指针的值,进行函数调用,以及作为其他用途。指向成员函数的指针也表现出一种逆变性,即存在从指向基类成员函数的指针到指向派生类成员函数指针的预定义转化,反之不然。这很好理解,如果考虑到基类成员函数会试图通过其this指针访问基类成员,然而派生类函数可能会试图反问基类中不存在的成员的话。
发表评论:
馆藏&34466
TA的推荐TA的最新馆藏[转]&基类指针可以指向派生类对象,基类指针不能转换为派生类指针?
[问题点数:30分,结帖人maomao85]
基类指针可以指向派生类对象,基类指针不能转换为派生类指针?
[问题点数:30分,结帖人maomao85]
不显示删除回复
显示所有回复
显示星级回复
显示得分回复
只显示楼主
匿名用户不能发表回复!|
每天回帖即可获得10分可用分!小技巧:
你还可以输入10000个字符
(Ctrl+Enter)
请遵守CSDN,不得违反国家法律法规。
转载文章请注明出自“CSDN(www.csdn.net)”。如是商业用途请联系原作者。C++实训07_图文_百度文库
两大类热门资源免费畅读
续费一年阅读会员,立省24元!
评价文档:
上传于||暂无简介
大小:515.00KB
登录百度文库,专享文档复制特权,财富值每天免费拿!
你可能喜欢}

我要回帖

更多关于 基类的指针指向派生类 的文章

更多推荐

版权声明:文章内容来源于网络,版权归原作者所有,如有侵权请点击这里与我们联系,我们将及时删除。

点击添加站长微信