这是2013年写的一篇旧文,放在gegahost.net上面 http://raison.gegahost.net/?p=15

February 15, 2013

How `new’ operator works ?

Filed under: c++ — Tags: C++ internal, c++ memory layout, c++ new, POD, virtual class — Raison @ 12:38 am

(original works by Peixu Zhu)

For single inherited classes

1.  in case of single instance of a class without virtual method (inherited or not).

  • suppose the class is `theClass‘.
  • at first, it calls function `malloc‘ to allocate sizeof(theClass) memory, the size is always the same to POD structures.
  • if the `malloc‘ function fails, throw exception if `nothrow‘ is not specified.
  • if the `malloc‘ function success, call class initializer and internal initializer to set default values of members( to be zeros)
  • call the constructor on the instance as a chain, the most rooted constructor is called at first, and then the derived constructors, the latest is theClass‘s constructor.
  • set return value to be the address of `malloc‘ returned.

2.  in case of single instance of a class with virtual method (inherited or not).

  • at first, it calls functon `malloc‘ to allocate sizeof(theClass) sized memory, for single inherited class, sizeof(theClass) =  (sizeof(void*) )  +  sizeof(POD structure). the additional (sizeof(void*) ) sized memory is for purpose of storing virtual pointer table for the class and it’s parent classes.
  • if the `malloc‘ function fails, throw exception if `nothrow‘ is not specified.
  • if the `malloc‘ function success, at first, set the first (sizeof(void*)  to be the class’s virtual pointer table, and then call class initializer and  internal initializer to set default values of members( to be zeros) on subsequent memory.
  • call the constructor on the instance as a chain, the most rooted constructor is called at first, and then derived classes’ constructors, the latest is the class’s constructor.
  • set return value to be the address of `malloc‘ returned.

3.  in case of arrayed instances of a class without virtual method.

  • suppose n instances are required.
  • calculate the size of required memory:  sizeof(void*) + n * sizeof(theClass)
  • call `malloc‘ to allocate memory of the size required.
  • if `malloc‘ fails, throw exception if `nothrow‘ is not specified.
  • if `malloc‘ success, set the first sizeof(void*) the count of instances in the array (i.e. `n’).
  • for subsequent memory,  each instance is initialized and constructed as above .
  • set return value to be the address of `malloc‘ returned minus sizeof(void*), i.e., the address of first instance.

4.  in case of arrayed instances of a class with virtual method.

  • calculate the size of required memory:

sizeof(void*) + n * sizeof(theClass).
sizeof(theClass) = sizeof(void*) + sizeof(POD)

  • call `malloc‘ to allocate the size required.
  • if `malloc‘ fails, throw exception if `nothrow‘ is not specified.
  • if `malloc‘ success, set the first sizeof(void*) the count of instances in the array (i.e. `n’).
  • for subsequent memory, for each instance, set the first
    sizeof(void*) memory to be the address of virtual pointer table of the
    class, then initialize the members, and call constructor one  by one.
  • set return value to be the address of `malloc‘ returned minus sizeof(void*), i.e., the address of first instance.

5.  about the virtual pointer table.

  • the layout of virtual pointer table:

[vdes1][vdes2](vm1)(vm2)(vm3…)[typeinfo [data of typeinfo]].
square bracketing indicates optional.
each elements are pointer to functions/methods.
vdes1 and vdes2 are virtual destructor.
vm1/vm2 … are virtual methods.
typeinfo    for function `typeid‘ (std::type_info)
data of typeinfo is the data of std::type_info

  • if the class is virtual, then there is typeinfo, and data of typeinfo.
  • if the class has virtual desctructor, there’s vdes1 and vdes2. one is called by `delete‘ operator (free memory in function), and ther other one is called by `delete[]‘ operator (does not free memory in function).
  • in runtime environment, calling virtual methods are converted into
    referencing index in the virtual pointer table, the index value of each
    virtual method is determined at compiling time. In derived classes, the
    child class instance and parent class instance share the same index
    value on same virtual method (with same mangling signature). If the
    child class does not override the parent virtual method, it will set the
    indexed pointer to the parent’s method, rather than of the child,
    however, if the child class override the virtual method, it will be  the
    indexed with pointer to the child’s method.

6.  about the alignment of  address returned by `new/new[]’ operator.
As you know, `new‘ and `new[]‘ operator both call `malloc‘ function to allocate memory required, thus, the alignment of address returned by `new‘ or `new[]‘ is determined by the address returned by `malloc‘. `malloc‘ does not guarantee the returned address is aligned well, thus, the `new‘ and `new[]‘ also do not guarantee the returned address is aligned well, though the size of the class is aligned.
But, there’s alignment version of `malloc‘, like posix_memalign, or valloc, etc., how about alignment version of `new‘ and `new[]‘ ?  The replacement new operator in C++11 may solve the problem.

For classes with multiple parent classes.
1. each parent class has an instance in the derived class instance, sequenced as the class definition.

2. the derived class’s own members are placed at the tail of the allocated memory.

3. sizeof(theClass) = sizeof(parentClass) * (count of parent classes) + sizeof(own)

4. for plain classes without virtual methods, sizeof(own) = sizeof(POD structure),  and for classes with virtual methods, sizeof(own) = sizeof(void*) + sizeof(POD structure).

How `new’ operator works ?的更多相关文章

  1. CLR via C# 3rd - 04 - Type Fundamentals

    1. System.Object        The runtime requires every type to ultimately be derived from the System.Obj ...

  2. Flink - Working with State

    All transformations in Flink may look like functions (in the functional processing terminology), but ...

  3. Think Python - Chapter 11 - Dictionaries

    Dictionaries A dictionary is like a list, but more general. In a list, the indices have to be intege ...

  4. MDX : Non Empty v/s NonEmpty

    MDX : Non Empty v/s NonEmpty User Rating: / 50 PoorBest Written by Jason Thomas    Friday, 07 May 20 ...

  5. NonEmpty和Non Empty的区别[转]

    One of my favourite questions in MDX is the difference between Non Empty and NonEmpty because even t ...

  6. JsonPath详解

    JsonPath is to JSON what XPATH is to XML, a simple way to extract parts of a given document. JsonPat ...

  7. C++11 : variadic templates(可变参数模板)

      Introduction: Before the possibilities of the new C++ language standard, C++11, the use of templat ...

  8. ADF BC New Features

      Examining ADF Business Components New Features Purpose In this tutorial, you create a series of si ...

  9. Dart语言特性必备了解!

    学习Dart语言,必须将以下的概念熟记于心: 在dart语言中,一切皆为对象.所有的对象都是一个类的实例.甚至整数.函数.null也看做是对象.所有的对象都继承于Object类 尽管Dart是强类型语 ...

随机推荐

  1. Unbuntu 终端中使用Tab键不能自动补全

    解决方案 1.利用vi编辑器打开 /etc/bash.bashrc文件(需要root权限) sudo vi /etc/bash.bashrc 2.找到文件中的下列代码 #enable bash com ...

  2. lucene倒排索引瘦身的一些实验——merge的本质是减少cfx文件 变为pos和doc;存储term vector多了tvx和tvd文件有337M

    store NO 压缩后的原始数据 原始数据大小 索引大小 索引时间 单词搜索时间 266 791 594 176 0.2 文件组成见后 运行forceMerge(3)后 merge的本质是减少cfx ...

  3. Apache Maven的下载、安装、测试

    Apache Maven是个软件项目管理工具,基于项目对象模型(Project Object Model,POM)的概念,Maven可用来管理项目的依赖.编译.文档等信息. 使用Maven管理项目时, ...

  4. I.MX6 eMMC分区挂载

    /********************************************************************* * I.MX6 eMMC分区挂载 * 说明: * 如果想要 ...

  5. 【CQ18阶梯赛第二场】题解

    [A-H国的身份证号码I] 用N个for语句可以搞定,但是写起来不方便,所以搜索. dfs(w,num,p)表示搜索完前w位,前面x组成的数位num,最后以为为p. 如果搜索到第N位,则表示num满足 ...

  6. [Selenium] HTML5 中的 Geolocation

    在 HTML5 ,新特性 Geolocation 用于定位用户位置信息. 由于用户位置信息是敏感信息,所以需要得到用户允许后,才能让程序通过 API  获取当前用户信息.WebDriver 程序每次重 ...

  7. 奶牛排序——RMQ

    [问题描述]奶牛在熊大妈的带领下排成了一条直队.显然,不同的奶牛身高不一定相同……现在,奶牛们想知道,如果找出一些连续的奶牛,要求最左边的奶牛 A 是最矮的,最右边的 B 是最高的,且 B 高于 A ...

  8. HBase之一:HBase原理和设计

    一.简介 HBase —— Hadoop Database的简称,Google BigTable的另一种开源实现方式,从问世之初,就为了解决用大量廉价的机器高速存取海量数据.实现数据分布式存储提供可靠 ...

  9. 如何升级xcode 中的cocos2dx 到v2.2.2以上版本

    每次升级cocos2dx版本都觉得不知道怎么弄才行. 这次升级到v2.2.2版本又花了我不少时间.因此在这里分享一下,以后也有地方可以查询. 1. 到http://cocos2d-x.org/ 下载最 ...

  10. 输出文章段落首行空格缩进在IE和chrome显示不一致的问题

    一般的编辑文章时,首行都缩进两格,而执行的操作则是一个tab键或者四个空格键,在html代码中体现的往往都是4个 然而我在输出时却发现了同样的html代码,在IE上显示的是缩进了一个字符,在chrom ...