C++语法知识小结(持续更新中)
1)在适用构造函数创建对象时,有时会创建临时对象。如
Stock::Stock(const std::string & co,long n,double pr);
在使用时,下面两条语句有根本区别:
Stock stock2=Stock("Boffo Ojects",2,2.0);
stock1=Stock("Nifty Foods",10,50.0); stock1是类对象
第一条语句是初始化,它创建有指定值的对象,可能会创建临时对象(也可能不会,取决于实现,我的电脑不会创建);第二条语句是赋值。像这样在赋值语句中使用构造函数总会导致在赋值前创建一个临时对象。如果既可以通过初始化,也可以通过赋值来设置对象的值,则应采用初始化方式。通常这种方式的效率更高。
2)作用域为类的常量
有时,类声明可能使用字面值30来指定数组的长度,由于该常量对于所有对象来说都是相同的,因此创建一个由所有对象共享的常量是个不错的主意。但下面这样做不可行:
class Bakery
{
const int Months=12;
double costs[Months];
...
};
这是因为声明类只是描述了对象的形式,并没有创建对象。因此,在创建对象前,将没有用于存储值的空间(C++11提供了成员初始化,但不适用于前述数组声明)。有两种方式可以实现这个目标,并且效果相同
第一种:在类中声明一个枚举。在类声明中声明的枚举的作用域为整个类,因此可以用枚举为整型常量提供作用域为整个类的符号名称。可以这样声明:
class Bakery
{
enum{Months=12};
double costs[Months];
....
}
用这种方式声明枚举并不会创建类数据成员。也就是说,所有对象中都不包含枚举。Months只是一个符号名称,在作用域为整个类的代码中遇到它时,编译器将用12来替换。
第二种:使用关键字static。
class Bakery
{
static const int Months=12;
double costs[Months];
...
}
这将创建一个名为Months的常量,该常量与其它静态变量存储在一起,而不是存储在对象中
3)符号常量和常变量的区别
符号常量不占用内存空间,在预编译时就全部由符号常量的值替换了,由于不占有内存空间,故不可对符号常量寻址,enum声明的就是符号常量,而const int Months=12,声明的为一常变量,因为可对Months寻址。
而常变量首先它是变量,占有内存空间,但其值必须在声明时初始化,且其值不可更改,const声明的是常变量,而不是如C++ Primer Plus的3.2节所说的符号常量
4)C++ Primer Plus中程序11_16的一些思考
在11_16中,有一个符号常量Lbs_per_stn。它的由来可参看书中10.6节,它还可以替换为static const int Lbs_per_stn=14;在看到12.7节中声明了一个类Queue,其中有一个const int qsize成员变量(其实就是常量)。它采用成员初始化列表给常量赋值,即在执行构造函数体之前,创建对象时进行初始化。
Queue::Queue(int qs):qsize(qs)
{
front=rear=null;
items=0;
}
那么在程序11_16中,是否也可以采用这种方式,将Lbs_per_stn声明为const int,在构造函数中采用成员初始化列表呢?
class Stonewt
{
const int Lbs_per_stn;
.....
};
Stonewt::Stonewt(double n):Lbs_per_stn(14)
{
......
}
经试验,在11_16中,不能采用这种方式,因为程序中有语句incognito=275;它的工作方式为先调用Stonewt(double)构造函数创建一个临时对象,再采用编译器自动生成的operator=()函数将临时对象的值逐成员复制到incognito中,而const int incognito属于成员变量,它已在生成对象时初始化为14;const变量是不能再被赋值的;故在编译时会出现operator=()函数在Stonewt中不可用导致错误。
若程序中没有incognito=275;则这种采用成员初始化列表的方式是可用的。
总结:若想采用把一个对象赋值给另一个对象,则成员变量中必不能出现常变量const,因为它只可初始化,不能再次被赋值。而enum{Months=12};则是定义了一个符号常量,在编译时,编译器会自动把Months替换为12;而static const int Lbs_per_stn=14;则是定义了一个名为Months的常量,该常量为静态,与其它静态变量存储在一起,而不是存储在对象中,故此时也可利用=赋值。
5)指针和数组名的区别
char * p="abcdefg";和char str[]="abcdefg";str和指针p都指向字符串的首地址,这一点没有区别。但是,str给字符串"abcdrfg"分配了内存空间,该字符串存储在该内存空间中,但是p指针并没有为字符串分配内存空间,字符串"abcdefg"在内存中的存储由系统分配,指针p在32位机中只占有4个字节,即所有指针类型的占用空间单位。此时,指针p指向的时字符串常量"abcdefg",可以改变指针指向的值,但不能为指针赋值。如
char *ps=p+4;
char *pt=p+2;
*pt='L'; (1)
*pt++=*ps++; (2)
其中(1)和(2)是不可以赋值的,虽然编译时没有错误,因为"abcdefg"对p来讲是一个字符串常量。但是,在这种赋值对数组来说是可以的
char str[]="abcdefg";
char *ps=p+4;
char *pt=p+2;
*pt='L'; (3)
*pt++=*ps++; (4)
(3)和(4)都是可以正常运行的。 一定要注意指针和数组的区别!!!!
(6)函数参数传递问题
在传递函数参数时,若未声明为引用,则是按值传递,即使参数为指针。这里一定要区分参数为指针和参数为数组的区别!!!数组名作为参数时,也是地址,但此时对数组的操作是对原来数组的操作,这并不违反按值传递的原则,传递时,函数生成一个与数组名类型相同的指针,数组名把值传递给该指针,这步就是按值传递,只是该指针也指向原数组的内存空间,所以是对原数组进行操作。指针作为函数参数时,也是按值传递的,在内存中会有两个指针变量,他们指向同一块内存区。!!!
C++语法知识小结(持续更新中)的更多相关文章
- Python 基础知识(持续更新中)
内置数据类型: 整型 浮点型 字符串 布尔值 空值 None 列表 list 元组 tuple 字典 dict 集合 set ...
- Java基础知识(持续更新中...)
1.成员变量:全局变量/字段(Field),不要称之为属性(错误)直接定义在类中,方法外面 1.类成员变量 使用static修饰的变量 2.实例成员变量 没用使用static修饰的变量 局部变量 ...
- MySQL与MSSQL的一些语法差异(持续更新中)
分号不能少:分号不能少:分号不能少:重要的事情说3遍 Insert或者Update的数据包含反斜杠\的时候需要进行转义\\,例:insert into tablename(id,name) value ...
- JPA相关知识点滴--持续更新中.....
Java 持久化(JPA) •Java EE 5 在EJB 3.0 中包含JPA 1.0 •参考实现:TopLink Essentials •Java EE 6 包含JPA 2.0 •参考实现:Ec ...
- CSS相关知识(持续更新中)
1. 弹性布局 一种当页面需要适应不同的屏幕大小以及设备类型时确保元素拥有恰当的行为的布局方式.引入弹性布局模型的目的是提供一种更加有效的方式来对一个容器中的子元素进行排列.对齐和分配空白空间. 2. ...
- Pig基础学习【持续更新中】
*本文参考了Pig官方文档以及已有的一些博客,并加上了自己的一些知识性的理解.目前正在持续更新中.* Pig作为一种处理大规模数据的高级查询语言,底层是转换成MapReduce实现的,可以作为MapR ...
- Pig语言基础-【持续更新中】
***本文参考了Pig官方文档以及已有的一些博客,并加上了自己的一些知识性的理解.目前正在持续更新中.*** Pig作为一种处理大规模数据的高级查询语言,底层是转换成MapReduce实现的, ...
- java视频教程 Java自学视频整理(持续更新中...)
视频教程,马士兵java视频教程,java视频 1.Java基础视频 <张孝祥JAVA视频教程>完整版[RMVB](东西网) 历经5年锤炼(史上最适合初学者入门的Java基础视频)(传智播 ...
- 白话kubernetes的十万个为什么(持续更新中...) - kubernetes
Kubernetes简称? 答:k8s或kube. Kubernetes是什么? 答:由Google开发的一个强大的平台,可以在集群环境中管理容器化应用程序.本质上是一种特殊的数据库,里面存储的是能够 ...
- 痞子衡嵌入式:史上最强i.MX RT学习资源汇总(持续更新中...)
大家好,我是痞子衡,是正经搞技术的痞子.今天痞子衡给大家介绍的是i.MX RT学习资源. 类别 资源 简介 官方汇总 i.MXRT产品主页 恩智浦官方i.MXRT产品主页,最权威的资料都在这里,参考手 ...
随机推荐
- CentOS6安装vsftpd
练习:完成vsftpd配置 (1) 禁锢系统用户于家目录 [root@node3 ~]# yum -y install vsftpd [root@node3 ~]# vim /etc/vsftpd/v ...
- C++的三大特性?C也可以做到
C++的三大特性是什么?封装.继承与多态,那么今天这篇文章小编就来介绍一下,如何用C语言实现C++的这三个特性. 1.封装 何为封装? 在面向对象的思想中,将数据和对数据的操作封装在一起——即类. 类 ...
- ZipArchive扩展的使用和Guzzle依赖的安装使用
在项目开发的过程中,需要去远程下载录音文件 然后保存到自己的项目中,然后再把录音文件压缩打包,最后再下载给用户 1.Guzzle依赖的安装 guzzle官方文档:http://guzzle-cn.re ...
- MVC FileDownLoad
public ActionResult MatDownload() { string ShopId = Session["ShopId"].ToString(); var self ...
- week01—绪论
一.作业题目 仿照三元组或复数的抽象数据类型写出有理数抽象数据类型的描述 (有理数是其分子.分母均为整数且分母不为零的分数). 有理数基本运算: 构造有理数T,元素e1,e2分别被赋以分子.分母值 销 ...
- What’s that ALUA exactly?
What’s that ALUA exactly? 29 September, 20098 Comments Of course by now we have all read the excelle ...
- 普及组2008NOIP 排座椅(贪心+排序)
排座椅 时间限制: 1 Sec 内存限制: 50 MB提交: 4 解决: 3[提交][状态][讨论版][命题人:外部导入] 题目描述 上课的时候总有一些同学和前后左右的人交头接耳,这是令小学班主任 ...
- C# 32位程序访问64位注册表
接上文:http://www.cnblogs.com/TaiYangXiManYouZhe/p/5086974.html 上代码: RegistryKey localKey; if (Environm ...
- Java中计算对象的大小
一.计算对象大小的方法 Java中如何计算对象的大小呢,找到了4种方法: 1.java.lang.instrument.Instrumentation的getObjectSize方法: 2.BTrac ...
- tp5操作mongo
1.通过composer安装 composer require mongodb/mongodb 2.使用 <?php /** * @author: jim * @date: 2017/11/17 ...