
C++基础
文章平均质量分 65
把大学没学完的学完
用代码淋漓尽致的展现自己的思路
展开
-
为什么C++空类还有内存呢?
一个空的class 如://sizeof X==1class X{};事实上并不是空的,它有一个隐晦的1byte,那是被编译器安插进去的一个char。这使得这个class的两个object得以在内存中配置独一无二的地址。原创 2014-03-12 23:40:17 · 414 阅读 · 0 评论 -
浅谈泛型编程
泛型编程最初诞生于C++中,目的是为了实现C++的STL(标准模板库)。其语言支持机制就是模板(Templates)。模板的精神其实很简单:参数化类型。换句话说,把一个原本特定于某个类型的算法或类当中的类型信息抽掉,抽出来做成模板参数T。比如qsort泛化之后就变成了: templatevoid sort(RandomAccessIterator first, RandomAccess原创 2014-03-31 01:04:12 · 476 阅读 · 0 评论 -
C++ 底层做的事情
C++在背后为我们做了太多的事情。 数组索引元素机制C++对象模型成员函数调用的实现C++虚函数机制的实现C++虚基类的实现 详情请阅读《深入探索C++对象模型》 很多底层的东西要用汇编指令,有空真要好好学下汇编原创 2014-03-31 15:40:23 · 420 阅读 · 0 评论 -
面向对象图解
现实中的实体可以抽象出类别的概念。对应于计算机世界中的一个类(class)。类是由属性和功能构成的,或者说是由数据成员,成员函数,类型成员构成原创 2014-03-31 13:01:30 · 533 阅读 · 0 评论 -
探索虚函数表的位置
引言:近日一个问题引起了我的注意:"请问虚函数表放在哪里?"。我也曾经思考过这个问题,零零散散也有一定的收获,这次正好趁这个机会把我对这一部分的理解整理一下。首先值得声明的是,本文的编译环境是VS2002+WinXP。C++标准并没有对虚函数的实现作出任何的说明,甚至都没有提到虚函数的实现需要用虚表来实现,只不过主流的C++编译器的虚函数机制都是通过虚表来实现的,所以用虚表来实现虚函数就成了"不是原创 2014-03-31 14:08:54 · 830 阅读 · 1 评论 -
virtual 语法规则
面向对象编程(Visual)在C++中,基类必须指出希望派生类重写哪些函数,定义为virtual的函数是基类期待派生类重新定义的,基类希望派生类继承的函数不能定义为虚函数。在C++中,通过基类的引用(或指针)调用虚函数时,发生动态绑定。引用(或指针)既可以指向基类对象也可以指向派生类对象,这一事实是动态绑定的关键。用引用(或指针)调用的虚函数在运行时确定,被调用的函数是引用(或指针转载 2014-04-04 13:57:09 · 640 阅读 · 0 评论 -
派生类到基类转换到可访问性
要确定到基类的转换是否可访问,可以考虑基类的public成员是否可访问,如果可以,转换是可以访问的,否则,转换是不可访问的。如果是public继承,则用户代码和后代类都可以使用派生类到基类的转换。如果类是使用private或protected继承派生的,则用户代码不能将派生类型对象转换为基类对象。如果是private继承,则从private继承类派生的类不能转换为基类。如果原创 2014-04-05 00:48:09 · 507 阅读 · 0 评论 -
变量和数据
1.什么是变量?电脑具有存储的功能。我们可以通过word打开一个保存的文章,也可以通过FPE(整人专家,一款游戏修改软件)来查看或锁定内存中保存的游戏人物的生命值。那么,一个程序是如何把数据存到电脑里,又是如何把电脑里的数据取出来的呢?在程序设计的时候,我们要把存储的数据放在一个叫变量(Variable)的东西里。它就好像是一个箱子,而数据就是箱子里的物品。当然在我们放东西和取东西之前必须原创 2014-03-22 16:15:43 · 813 阅读 · 0 评论 -
C++会生成默认构造函数的四种情况
C++标准是这样写的默认构造函数是由编译器在需要的时候将其合成出来,这里#include #include using namespace std; class A { public: char *ptr; //string str; }; int main() { A b; b.ptr=NULL; return 0; }强调的是需要,而原创 2014-03-27 23:24:00 · 647 阅读 · 0 评论 -
最好使用未命名的命名空间取代文件中的静态声明
在标准C++中引入命名空间之前,程序必须将名字声明为static ,使它们局部于一个文件。文件中静态声明的使用从C语言继承而来,在C语言中,声明为static的局部实体在声明它的文件之外不可见。 C++不赞成文件静态声明。不赞成的特征是在未来版本中可能不支持的特征。应该避免文件静态而使用未命名的命名空间代替。原创 2014-03-16 17:21:37 · 444 阅读 · 0 评论 -
++i和i++的区别
大家都应该知道i++和++i的区别,前者是先使用i的值,然后再增加1,而后者是先增加1然后再使用i的值。但是i++和++i那个更好呢? 我们实现角度来看:前者是将i值加1后赋给i,然后返回i本身;而后者是先用个临时变量存储i值,然后将i值加1赋给赋给i,然后返回临时变量的值。内置数据类型他们的效率差不多,看他们的汇编代码就知道,我看的汇编代码是VC的,其他编译器不知道,还是得要看编译器优化原创 2014-03-30 22:31:54 · 670 阅读 · 0 评论 -
引入虚函数的目的
引入虚函数的目的就是为了让指向派生类对象的基类指针可以调用覆盖了基类虚方法的那个虚方法。把不同的子类对象都当作父类来看,可以屏蔽不同子类对象之间的差异,写出通用的代码,做出通用的编程,以适应需求的不断变化。赋值之后,父类指针就可以根据当前赋值给它的子对象的特性以不同的方式运作。 多态性可以简单地概括为“一个接口,多种方法”。继承是实现代码的可重用性,可以直接调用父类的函数。多态原创 2014-03-30 01:04:21 · 2318 阅读 · 0 评论 -
函数查找规则
函数查找的顺序如下:1)查找函数的名字2)从中找出最佳匹配。3)检查是否具有该函数的访问权限4)实参相依之查找原则:根据实参的类型,自动进入相应的类内部、命名空间进行查找。原创 2014-03-29 18:40:49 · 473 阅读 · 0 评论 -
C/C++位操作技巧
检测一个无符号数是不为2^n-1(^为幂): x&(x+1)将最右侧0位改为1位: x | (x+1) 使用位运算的无分支代码:计算绝对值 int abs( int x ) { int y ; y = x >> 31 ; return (x^y)-y ; //or: (x+y)^y }符号函数:sign(x) = -1, x 0int si原创 2014-03-13 12:32:32 · 896 阅读 · 0 评论 -
C/C++中的日期和时间
#include UTC(世界标准时间);Calendar Time(日历时间);epoch(时间点);clock tick(时钟计时单元) 函数用途 函数名 得到处理器时间 clock 得到时间差原创 2014-03-14 00:45:54 · 466 阅读 · 0 评论 -
在构造和析构期间不要调用virtual函数
在构造和析构期间不要调用virtual函数,因为这类调用从不下降至derived class (比起当前执行构造函数和析构函数那层).#include using namespace std; class Base {public:Base(); virtual ~Base(); virtual void print(); }; Base:原创 2014-03-27 23:42:07 · 522 阅读 · 0 评论 -
重载,覆盖,隐藏的分析
成员函数的重载、覆盖(override)与隐藏很容易混淆,C++程序员必须要搞清楚概念,否则错误将防不胜防。1 重载与覆盖成员函数被重载的特征:(1)相同的范围(在同一个类中);(2)函数名字相同;(3)参数不同;(4)virtual 关键字可有可无。覆盖是指派生类函数覆盖基类函数,特征是:(1)不同的范围(分别位于派生类与基类);(2)函数名字相同;原创 2014-03-28 01:09:29 · 357 阅读 · 0 评论 -
RAII手法
如何确保资源一定会被释放(即便发生异常),这在D里面对应的是scope(exit),在Java里面对应的是finally,在C# 里面对应的是scoped using。简而言之就是,不管当前作用域以何种方式退出,某某操作(通常是资源释放)都一定要被执行。这个问题的答案其实C++程序员们应该耳熟能详了:RAII。RAII是C++最为强大的特性之一。在C++里面,局部变量的析构函数刚好满足原创 2014-03-30 17:10:09 · 1496 阅读 · 0 评论 -
避免using 指示
using 指示注入来自一个命名空间的所有名字,它的使用是靠不住的:只用一个语句,命名空间的所有成员名就突然可见了。虽然这个方法看似简单,但也有它自身的问题。如果应用程序使用很多库,并且用using 指示使得这些库中的名字可见,那么,全局命名空间污染问题就重新出现。 而且,当引入库的新版本的时候,正在工作的程序可能会编译失败。如果新版本引入一个与应用程序正在使用的名字冲突的名字,就会原创 2014-03-29 18:58:12 · 429 阅读 · 0 评论 -
异常exception与error-code
异常与错误代码的本质区别之一——异常会自动往上层栈传播:一旦异常被抛出,执行流就立即中止,取而代之的是自动的stack-unwinding操作,直到找到一个适当的catch子句。 相较之下,使用error-code的话,要将下层调用发生的错误传播到上层去,就必须手动检查每个调用边界,任何错误,都必须手动转发(返回)给上层,稍有遗漏,就会带着错误的状态继续往下执行,从而在下游不知道原创 2014-03-30 18:16:07 · 6287 阅读 · 0 评论 -
对指针的初步理解
指针变量的概念:存放地址的变量称为指针变量。指针变量是一种特殊的变量,它不同于一般的变量,一般变量存放的是数据本身,而指针变量存放的是数据的地址。假设在程序中声明了1个int型的变量a,其值为68。系统为变量a分配的首地址为0X65FDF4H,pa是存放变量a地址的指针变量,即pa中存放的值为0x065FDF4H。对变量a的访问有两种方式:一是直接按地址0x065FDF4H找到a的存储原创 2014-03-12 22:10:37 · 559 阅读 · 0 评论 -
C++内存处理的问题小结
1、内存泄露对堆上的内存进行申请的时候,一定要提高警觉程度。 动态内存的申请与释放必须配对,程序中malloc 与free 、new与delete的一定要成对。千万防止光申请不释放的代码出现。如果发生这种错误,函数每被调用一次就丢失一块内存。我们来看一下如何防止:我们将指针放进对象的内部并且让对象管理指针是最简单的防止内存泄露的方法。应把new返回的指针存储在对象的成员变量里,原创 2014-03-12 23:00:08 · 554 阅读 · 0 评论 -
c++中 如何前置声明一个名称空间中的类
//file A.hnamespace A{ class ClassA { };};//file B.hnamespace A{ class ClassA;};namspace B{ class ClassB { public: Class B(); private: A::Class原创 2014-04-13 13:19:23 · 1077 阅读 · 0 评论