飘云阁

 找回密码
 加入我们

QQ登录

只需一步,快速开始

查看: 1942|回复: 4

[C/C++] 关于那个传说中的虚表(浅析构造顺序)

[复制链接]

该用户从未签到

发表于 2010-1-19 01:06:13 | 显示全部楼层 |阅读模式
1.
this 指针是通过寄存器传参过去的

2. 类的 构造 和 析构 时都会对虚表进行赋值 (虚表在编译的时候就已经写入代码段了)
即对
mov [ebp-4],ecx
mov ecx,[ebp-4]
mov [ecx],offset class::`vftable' (虚表的地址)

所以通过 构造和析构函数 都是可以找到该类的虚表的

3. 关于大忽悠虚表

class People
{
virtual ~People()
}

class Student: public People
{}

int main(int argc, char* argv[])
{
        Student stu(1,2,3);
        Student * pstu = new Student(1,2,3);
        delete pstu;
        return 0;
}

Student 的虚表中成员 仅仅为 父类的虚表集,子类的虚函数要进去想都别想 ~ 这个大家都知道哈
也就是说子类单独定义的虚表想进入多态 想都别想哈 ~~

虚表的顺序 就是 父类中虚表定义的书序哈 跟子类如何定义无关~~

而对象的虚表中 虚函数 自身在虚表吗? 答案是 No 而是另一个间接调用虚函数的函数填充了所谓的虚函数
(就是这个东西啦哈 scalar deleting destructor)

上边代码即可测试 这里点到为止好了 ~~
PYG19周年生日快乐!

该用户从未签到

 楼主| 发表于 2010-1-19 10:37:35 | 显示全部楼层
拷贝构造中初始化类表的顺序

1. 先看一下Copy构造

public:
        char * m_pName;
        int m_nAge;
        int m_nHeight;

34:
35:   People::People(const People &obj):m_nAge(obj.m_nAge),
36:       m_pName(obj.m_pName),m_nHeight(obj.m_nHeight)
37:   {
00411850   push        ebp
00411851   mov         ebp,esp
00411853   sub         esp,44h
00411856   push        ebx
00411857   push        esi
00411858   push        edi
00411859   push        ecx
0041185A   lea         edi,[ebp-44h]
0041185D   mov         ecx,11h
00411862   mov         eax,0CCCCCCCCh
00411867   rep stos    dword ptr [edi]
00411869   pop         ecx
// 从这里开始 配对COPY ~
0041186A   mov         dword ptr [ebp-4],ecx
0041186D   mov         eax,dword ptr [ebp-4]
00411870   mov         ecx,dword ptr [ebp+8]
00411873   mov         edx,dword ptr [ecx+4]
00411876   mov         dword ptr [eax+4],edx
00411879   mov         eax,dword ptr [ebp-4]
0041187C   mov         ecx,dword ptr [ebp+8]
0041187F   mov         edx,dword ptr [ecx+8]
00411882   mov         dword ptr [eax+8],edx
00411885   mov         eax,dword ptr [ebp-4]
00411888   mov         ecx,dword ptr [ebp+8]
0041188B   mov         edx,dword ptr [ecx+0Ch]
0041188E   mov         dword ptr [eax+0Ch],edx
00411891   mov         eax,dword ptr [ebp-4]
00411894   mov         dword ptr [eax],offset People::`vftable' (00428038)
38:       // 拷贝构造中只默认添加一个虚表的写入操作
39:       // 先写虚表 再复制
40:   //  m_nAge = obj.m_nAge;
41:   //  m_nHeight = obj.m_nAge;
42:   //  m_pName = obj.m_pName;
43:   }
0041189A   mov         eax,dword ptr [ebp-4]
0041189D   pop         edi
0041189E   pop         esi
0041189F   pop         ebx
004118A0   mov         esp,ebp
004118A2   pop         ebp
004118A3   ret         4

2.拷贝构造确实是按老师说的 不管初始化类表如何 都按照类的定义顺序来赋值

People::People(int age,int heigth,char * pName):m_nAge(age),
        m_nHeight(heigth),m_pName(pName)

004013D9   pop         ecx
004013DA   mov         dword ptr [ebp-4],ecx
004013DD   mov         eax,dword ptr [ebp-4]
004013E0   mov         ecx,dword ptr [ebp+10h]
004013E3   mov         dword ptr [eax+4],ecx
004013E6   mov         edx,dword ptr [ebp-4]
004013E9   mov         eax,dword ptr [ebp+8]
004013EC   mov         dword ptr [edx+8],eax
004013EF   mov         ecx,dword ptr [ebp-4]
004013F2   mov         edx,dword ptr [ebp+0Ch]
004013F5   mov         dword ptr [ecx+0Ch],edx
PYG19周年生日快乐!
  • TA的每日心情
    无聊
    2017-4-18 16:56
  • 签到天数: 1 天

    [LV.1]初来乍到

    发表于 2010-1-19 21:18:33 | 显示全部楼层
    原帖由 Nisy 于 2010-1-19 01:06 发表
    2. 类的 构造 和 析构 时都会对虚表进行赋值 (虚表在编译的时候就已经写入代码段了)
    即对
    mov [ebp-4],ecx
    mov ecx,[ebp-4]
    mov [ecx],offset class::`vftable' (虚表的地址)

    所以通过 构造和析构函数 都是可以找到该类的虚表的


    构造就是让this指针指向虚表,所以,知道this指针了,就知道虚表位置了,没有必要再去看构造或者析构……

    3. 关于大忽悠虚表

    这个没有看懂,等老方讲过多态以后再来看~

    2.拷贝构造确实是按老师说的 不管初始化类表如何 都按照类的定义顺序来赋值

    这个是为什么不按照初始化类表的顺序来定义来着?
    老师讲这个的时候,我睡着了~/:012

    [ 本帖最后由 besterChen 于 2010-1-19 21:22 编辑 ]
    PYG19周年生日快乐!

    该用户从未签到

     楼主| 发表于 2010-1-20 11:38:44 | 显示全部楼层
    原帖由 besterChen 于 2010-1-19 21:18 发表


    构造就是让this指针指向虚表,所以,知道this指针了,就知道虚表位置了,没有必要再去看构造或者析构……


    这个没有看懂,等老方讲过多态以后再来看~

    这个是为什么不按照初始化类表的顺序来定义来着?
    ...


    构造就是让this指针指向虚表
        ==>是填虚表指针 虚表是编译时就弄好的 在数据段 不是指向虚表


    为什么不按照初始化类表的顺序来定义来着
        ==>一会告诉你哈
    PYG19周年生日快乐!
  • TA的每日心情
    开心
    2023-8-23 14:44
  • 签到天数: 1 天

    [LV.1]初来乍到

    发表于 2010-1-26 22:26:47 | 显示全部楼层
    打酱油的来抄笔记了。。。。。。  看不懂啊 看不懂。/:002
    PYG19周年生日快乐!
    您需要登录后才可以回帖 登录 | 加入我们

    本版积分规则

    快速回复 返回顶部 返回列表