
C++
文章平均质量分 87
衡雪
这个作者很懒,什么都没留下…
展开
-
C++运算符重载三种形式(成员函数,友元函数,普通函数)详解
首先,介绍三种重载方式: 1 //作为成员函数重载(常见) 2 class Person{ 3 Private: 4 string name; 5 int age; 6 public: 7 Person(const char* name, int age):name(name),age(age){} 8 bool operator<(c...转载 2018-07-07 15:29:56 · 13103 阅读 · 2 评论 -
揭秘 typedef四用途与两陷阱
typedef用来声明一个别名,typedef后面的语法,是一个声明。本来笔者以为这里不会产生什么误解的,但结果却出乎意料,产生误解的人不在少数。罪魁祸首又是那些害人的教材。在这些教材中介绍typedef的时候通常会写出如下形式: typedef int PARA; 这种形式跟#define int PARA几乎一样,如前面几章所述,这些教材的宗旨是由浅入深,但实际做出来的行为却是以偏盖全。的确,...转载 2018-06-10 22:22:15 · 113 阅读 · 0 评论 -
类和结构体的递归定义
1.类的递归定义有两个类这样定义: Subject.h 头文件如下:#ifndef SUBJECT_H#define SUBJECT_H#include <iostream>#include "Observer.h" class Subject{public: void Info(){ std::cout <<" Subject !/n"; }protected...转载 2018-06-10 21:56:48 · 3676 阅读 · 0 评论 -
头文件重复包含
如果某个头文件被多次包含,则在VC编译器中编译,会抛出“重复定义”错误。为了避免同一个文件被重复包含多次,C++提出了2种解决方案。1、#ifndef _SOME_FILE_H #define _SOME_FILE_H …… …… #endif //在文件末端2、#pragma one …… ……#ifndef、#define...转载 2018-06-10 15:19:27 · 231 阅读 · 0 评论 -
掌握变量定义的位置与时机
变量的定义建议离使用位置越近越好,尽量避免变量作用域的膨胀。如下代码:string GetSubStr(const string& str,size_t iPos){string strSubstr;if (str.size()<iPos){throw logic_error("iPos is too larger!");}strSubstr=str.substr(iPos);re...转载 2018-06-10 15:18:00 · 212 阅读 · 0 评论 -
局部变量和全局变量的差别
变量一般包括4种如下:1、全局变量,在整个工程文件都有效2、静态全局变量,指定定义它的文件内有效3、静态局部变量,只在定义它的函数内有效,只是程序仅分配一次内存,函数返回后,该变量不会消失4、局部变量,定义它的函数内有效,函数返回后失效...原创 2018-06-10 15:11:47 · 893 阅读 · 0 评论 -
计算机是如何存储变量的
C++可执行程序的数据存储区域可分为如下:1、只读数据区,如:char *pTest = "Hello World"2、全局/静态存储区 如:static int nNum = 10或者定义在main函数外的全局变量3、自由存储区、堆区 如:char *pTest = new char[100],申请的内存块编译器不负责释放,由代码自行代用delete pTest[]释放内存。具有节省空间、使用方...原创 2018-06-09 22:55:29 · 1162 阅读 · 0 评论 -
C++比C加了什么
1.C++对C的扩展主要表现在面向对象和泛型编程两个部分。当然除了这两部分的重要功能外,C++对C语言的基础方面如函数、变量类型等也进行了完善和添加2.C语言在C99标准之前没有bool变量;引用是C++语言区别C语言的一个新引入的重要扩充。3.C++的多态包括两种:一种是运行时的多态,另一种是编译时的多态C++通过函数重载和运算符重载实现编译时多态,通过继承和虚函数来实现运行时多态。面向过程的多...原创 2018-06-09 22:36:10 · 4741 阅读 · 0 评论 -
如何在C++中调用C程序
C++和C是两种完全不同的编译链接处理方式,如果直接在C++里面调用C函数,会找不到函数体,报链接错误。要解决这个问题,就要在 C++文件里面显示声明一下哪些函数是C写的,要用C的方式来处理。1.引用头文件前需要加上 extern “C”,如果引用多个,那么就如下所示extern “C”{#include “ s.h”#include “t.h”#include “g.h” #include “j...转载 2018-06-09 22:11:29 · 467 阅读 · 0 评论 -
如何降低函数的圈复杂度
圈复杂度就是统计一个函数有多少个分支(if,while,for等)每增加一个分支,复杂度加1。简单来说,就是相当于需要多少个测试用例才能对这个函数做到全路径覆盖。计算方法:(1)由1计算,一直往下通过程序。(2)一旦遇到以下关键字或同类的词,如if ,while,repeat,for,and ,or,CC加1。(3)switch-case语句的每一种情况加1。降低函数复杂度的方法:提炼函数、替换算...转载 2018-06-16 23:05:35 · 6206 阅读 · 0 评论 -
优化结构体中元素的布局
下面的代码片段定义了结构体A和B:struct A // 结构体A{int a;char b;short c;};struct B // 结构体B{char b;int a;short c;};在32位机器上,char、short、int三种类型的大小分别是1、2、4。那么上面两个结构体的大小如何呢?结构体A中包含了一个4字节的int,一个1字节的char和一个2字节的short,B也一样,所以A...转载 2018-06-10 22:43:25 · 440 阅读 · 0 评论 -
关于#和##的讨论
一、一般用法 我们使用#把宏参数变为一个字符串,用##把两个宏参数贴合在一起. 用法: #i nclude #i nclude using namespace std; #define STR(s) #s #define CONS(a,b) int(a##e##b) int main() { printf(STR(vck)); // 输出字符串"vck...转载 2018-07-03 21:38:11 · 133 阅读 · 0 评论 -
若不想使用编译器自动生成函数,就该明确拒绝
编译器会自动为我们生成构造函数,拷贝构造函数,赋值操作符和析构函数。如果想要拒绝他们自动生成,那么就自行声明他们,并且令这些函数为private,从而阻止人们调用他。方式一:很明显直接的方法,正如前面所说的,将函数声明为private,但是这样并不绝对安全,因为member函数和friend函数还是可以访问到private成员。方式二:在方式一的基础上,只将函数声明不给出定义,这样编译不出错,但是...转载 2018-07-03 22:11:42 · 218 阅读 · 0 评论 -
陷阱重重的C++赋值重载函数operator=
曾经有C++高手说过:看一个C++程序员功底是否够硬,让他写个赋值重载函数就能看出来了!在我看来,这种说法并不夸张。因为能将operator=函数写好确实需要扎实的基础,其中的陷阱真不少。陷阱一:不懂规避自我拷贝先看代码string& string::operator=(const string& rhs){ if (m_pStr != NULL) delete...转载 2018-07-07 15:18:54 · 266 阅读 · 0 评论 -
重载operator[]的注意事项
【C++语法】关于operator[]重载的注意点今天在书上注意到这样一段代码:#include <iostream>#include <cassert>#include <string>using namespace std; template <class type, int dim>class Point{public: Point(); Po...转载 2018-07-07 15:01:14 · 1686 阅读 · 0 评论 -
区别++/--操作符前置和后置的差异
这篇文章不是讨论(i++)+(i++)+(i++)的计算结果,更不是讨论(i++)+(++i)+(i++)。 在C++教程中,我们都会学到:i++和++i是两个表达式,他们都会对i进行自增,但是呢,作为表达式,i++的值是自增之前的值,++i的值是自增之后的值。 本文在此基础上,进行一些稍微深入的讨论。 从操作符重载的角度,看i++和++i的区别,是一个比较好的切入点。 操作符重载假设有一个类Ag...转载 2018-07-07 14:46:57 · 508 阅读 · 0 评论 -
理解常量成员函数
常量成员函数 (const member function), 可读取类中的数据成员,但不能修改。1 声明1.1 const 关键字 参数列表后,加 const 关键字,声明为常量成员函数,表明其不被允许修改类的数据成员 下面的类,以年、月、日的形式来表示日期 (注意:年月日的声明顺序)class Date {public: int GetYear() const { ret...转载 2018-07-04 21:49:49 · 3416 阅读 · 1 评论 -
C++为类中提供类成员的初始化列表(★firecat推荐★)
在使用C++编程的过程当中,常常需要对类成员进行初始化,通常的方法有两种:第一种方法:CMYClass::CSomeClass(){ x=0; y=1;}第二种方法:CSomeClass::CSomeClass() : x(0), y(1){}本文将要探讨这两种方法的异同以及如何使用这两种方法。 从技术上说,第二种方法比较好,但是在大多数情况下,两者实际上没有什么区别...转载 2018-07-04 21:26:13 · 7520 阅读 · 0 评论 -
C++类中引用成员和常量成员的初始化(初始化列表)
如果一个类是这样定义的:Class A{ public: A(int pram1, int pram2, int pram3); privite: int a; int &b; const int c; }假如在构造函数中对三个私有变量进行赋值则通常会这样写:A::A(int pram1...转载 2018-07-04 21:24:23 · 2741 阅读 · 0 评论 -
将成员变量声明为private
切记声明数据成员为private。它为客户提供了访问数据的一致,细微划分的访问控制,允许约束条件获得保证,而且为类的作者提供了实现上的弹性。 protec并不比public更具有封装性。不应该将数据成员声明为public的三个理由:一、语法一致性 如果数据成员不是public的,客户访问一个对象的唯一方法就是通过成员函数。如果在public接口中的每件东西都是函数,客户就不必...转载 2018-07-04 21:04:10 · 2241 阅读 · 0 评论 -
class对象大小与什么有关系
之前看了很多关于类对象大小问题的计算,今天闲着没事就来整理整理,写写自己的看法。首先,来看看一个只有构造函数和析构函数的空类:[cpp] view plain copy#include <iostream> using namespace std; class Base { public: Base(); ~Base(); }; int main(int...转载 2018-07-04 20:56:13 · 530 阅读 · 0 评论 -
struct和class的关系
一、 C++中的struct对C中的struct进行了扩充,它已经不再只是一个包含不同数据类型的数据结构了,它已经获取了太多的功能。 struct能包含成员函数吗? 能! struct能继承吗? 能!! struct能实现多态吗? 能!!! 原文:http://blog.youkuaiyun.com/xdrt81y/article/details/17143...转载 2018-07-03 22:28:06 · 995 阅读 · 0 评论 -
尽量不要使用可变参数
在某些情况下我们希望函数参数的个数可以根据实际需要来确定,所以C语言中就提供了一种长度不确定的参数,形如:“...”,C++语言也继承了这一语言特性。在采用ANSI标准形式时,参数个数可变的函数的原型是:typefuncname(typepara1,typepara2,...);这种形式至少需要一个普通的形式参数,后面的省略号(...)不能省去,它是函数原型必不可少的一部分。典型的例子有大家熟悉的...转载 2018-06-16 22:54:17 · 1748 阅读 · 0 评论 -
不要让main函数返回void
同C程序一样,每个C++程序都包含一个或多个函数,而且必须有一个函数命名为main,并且每个函数都由具有一定功能的语句序列组成。操作系统将main作为程序入口,调用main函数来执行程序;main函数执行其语句序列,并返回一个值给操作系统。在大多数系统中,main函数的返回值用于说明程序的退出状态。如果返回0,则代表main函数成功执行完毕,程序正常退出,否则代表程序异常退出。然而在编写C++程序...转载 2018-06-16 22:32:35 · 4089 阅读 · 0 评论 -
C++的函数重载
函数重载的重要性不言而明,但是你知道C++中函数重载是如何实现的呢(虽然本文谈的是C++中函数重载的实现,但我想其它语言也是类似的)?这个可以分解为下面两个问题1、声明/定义重载函数时,是如何解决命名冲突的?(抛开函数重载不谈,using就是一种解决命名冲突的方法,解决命名冲突还有很多其它的方法,这里就不论述了)2、当我们调用一个重载的函数时,又是如何去解析的?(即怎么知道调用的是哪个函数呢)这两...转载 2018-06-16 22:21:45 · 142 阅读 · 0 评论 -
关于空指针
臭名昭著的空指针到底是什么? 语言定义中说明, 每一种指针类型都有一个特殊值 --- "空指针" --- 它与同类型的其它所有指针值都不相同, 它 "与任何对象或函数的指针值都不相等"。也就是说, 取地址操作符 & 永远也不能得到空指针, 同样对 malloc() 的成功调用也不会返回空指针, 如果失败, malloc() 的确返回空指针, 这是空指针的典型用法: 表示 "未分配" 或者...转载 2018-06-14 22:34:30 · 3695 阅读 · 0 评论 -
禁止以多态的形式处理数组
#include<iostream>using namespace std;class BasedClass{ //基类private: int num;public: BasedClass() { this->num = 1; }; BasedClass(int num) { this->num = num; }; int getNu...转载 2018-06-14 23:07:49 · 158 阅读 · 0 评论 -
数组指针和指针数组的区别
数组指针(也称行指针)定义 int (*p)[n];()优先级高,首先说明p是一个指针,指向一个整型的一维数组,这个一维数组的长度是n,也可以说是p的步长。也就是说执行p+1时,p要跨过n个整型数据的长度。如要将二维数组赋给一指针,应这样赋值:int a[3][4];int (*p)[4]; //该语句是定义一个数组指针,指向含4个元素的一维数组。 p=a; //将该二维数组的首地址...转载 2018-06-13 22:30:21 · 116 阅读 · 0 评论 -
进程间通信方式
转自:http://blog.youkuaiyun.com/shiqz/article/details/5862936摘 要 随着人们对应用程序的要求越来越高,单进程应用在许多场合已不能满足人们的要求。编写多进程/多线程程序成为现代程序设计的一个重要特点,在多进程程序设计中,进程间的通信是不可避免的。Microsoft Win32 API提供了多种进程间通信的方法,全面地阐述了这些方法的特点,并加以比较和分析...转载 2018-06-13 21:12:47 · 2009 阅读 · 0 评论 -
线程间通信的三种方法
多线程通信的方法主要有以下三种: 1.全局变量进程中的线程间内存共享,这是比较常用的通信方式和交互方式。注:定义全局变量时最好使用volatile来定义,以防编译器对此变量进行优化。 2.Message消息机制常用的Message通信的接口主要有两个:PostMessage和PostThreadMessage,PostMessage为线程向主窗口发送消息。而PostThreadMessage是任意...转载 2018-06-14 23:08:03 · 11314 阅读 · 0 评论 -
static用法小结
static用法小结static关键字是C, C++中都存在的关键字, 它主要有三种使用方式, 其中前两种只指在C语言中使用, 第三种在C++中使用(C,C++中具体细微操作不尽相同, 本文以C++为准).(1)局部静态变量(2)外部静态变量/函数(3)静态数据成员/成员函数下面就这三种使用方式及注意事项分别说明一、局部静态变量在C/C++中, 局部变量按照存储形式可分为三种auto, stati...转载 2018-06-12 21:57:18 · 123 阅读 · 0 评论 -
sizeof计算空间大小的总结
sizeof,看起来还真不简单,总结起来还是一大堆的东西,不过这是笔试面试中出现比较频繁的,我也是考过才觉得很重要,有些规则如果不注意,还真是拿到一道题目摸不着头脑,所有总结一下,方面忘记的时候瞄一瞄,其中重点是struct的空间大小部分。关于sizeof的总结 1、sizeof的使用形式:sizeof(var_name)或者sizeof var_name 2、变量名可以不用括号括住:size...转载 2018-06-12 21:44:36 · 309 阅读 · 0 评论 -
使用new/delete时要采用相同的形式
当使用new动态生成一个对象时,有两件事回发生:(1)对象内存的分配(这一过程名为operator new的函数实现)。(2)针对此内存会有一个(或更多)构造函数被调用。当使用delete释放对象内存时,同样会有两件事发生:(1)真毒此内存会有一个(或更多)析构函数被调用。(2)内存被释放(通过名为operator delete的函数)。总结:如果调用new时使用[],则必须在对应调用delete...原创 2018-06-12 21:29:32 · 129 阅读 · 0 评论 -
改善C++ 程序的150个建议学习之建议21:尽量用new/delete代替malloc/free
建议21:尽量用new/delete代替malloc/free在C语言中,我们已经熟悉利用malloc/free来管理动态内存,而在C++中,我们又有了新的工具:new/delete。你不禁会产生疑问—有了malloc/free为什么还要new/delete 呢?使用malloc/free和使用new/delete又有什么区别呢?首先来分析一下下面的代码片段:class Object{public...转载 2018-06-12 21:18:14 · 199 阅读 · 0 评论 -
C++中引用与指针的区别
请说出C++中引用和指针的区别。(华为、腾讯、阿里等) 参考答案: (1)当引用被创建时,它必须被初始化。而指针则可以在任何时候被初始化。 (2)一旦一个引用被初始化为指向一个对象,它就不能被改变为对另一个对象的引用。而指针则可以在任何时候指向另一个对象。 (3)不可能有NULL引用。必须确保引用是和一块合法的存储单元关联。 进一步解析: 指针和引用都是 C++ 中的基本语法成份,它们既有联系,也...转载 2018-06-14 23:07:09 · 123 阅读 · 0 评论 -
避免那些由运算符引发的混乱
一般,C++被认为是C的超集。C++确实从它的前辈C那里继承了很多东西,比如一套含义相当混乱模糊的运算符。由于C/C++语法规则的灵活性,以致那些粗心的程序员常会使用错误的运算符,进而引发不必要的麻烦。下面的代码就是一个典型的例子: if(nValue = 0) { // do something if nValue is not zero. }显然,程序员的本意是要写if(nValue==0)。...转载 2018-06-14 23:16:35 · 164 阅读 · 0 评论 -
尽量使用C++风格的类型转换
仔细想想地位卑贱的类型转换功能(cast),其在程序设计中的地位就象goto语句一样令人鄙视。但是它还不是无法令人忍受,因为当在某些紧要的关头,类型转换还是必需的,这时它是一个必需品。 不过C风格的类型转换并不代表所有的类型转换功能。一来它们过于粗鲁,能允许你在任何类型之间进行转换。不过如果要进行更精确的类型转换,这会是一个优点。在这些类型转换中存在着巨大的不同,例如把一个指向const对象的指...转载 2018-06-15 22:37:49 · 229 阅读 · 0 评论 -
内联函数和宏定义的区别
用内联函数取代宏:1.内联函数在运行时可调试,而宏定义不可以;2.编译器会对内联函数的参数类型做安全检查或自动类型转换(同普通函数),而宏定义则不会; 3.内联函数可以访问类的成员变量,宏定义则不能; 4.在类中声明同时定义的成员函数,自动转化为内联函数。12345内联函数和普通函数相比可以加快程序运行的速度,因为不需要中断调用,在编译的时候内联函数可以直接被镶嵌到目标代码中。内联函数要做...转载 2018-06-16 15:20:14 · 260 阅读 · 0 评论 -
内联函数inline
inline int max( int , int ,int ); //声明inline int max( int a, int b, int c) //定义{if( b > a) a = b;if( c > a) a = c;return a;}!!!注意:可以在声明函数和定义函数的同时写inline,也可以只在函数声明时加inline,而定义函数时不加inline。只要在调用该函数...转载 2018-06-16 15:05:26 · 135 阅读 · 0 评论 -
宏定义中使用do{}while(0)的好处
#define MACRO_NAME(para) do{macro content}while(0)的格式,总结了以下几个原因:1,空的宏定义避免warning:#define foo() do{}while(0)2,存在一个独立的block,可以用来进行变量定义,进行比较复杂的实现。3,如果出现在判断语句过后的宏,这样可以保证作为一个整体来是实现:#define foo(x) / action1...转载 2018-06-16 14:23:17 · 181 阅读 · 0 评论