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产品主页,最权威的资料都在这里,参考手 ...
随机推荐
- Python学习笔记之selenium 定制启动 chrome 的选项
在自动化中,默认情况下我们打开的就是一个普通的纯净的chrome浏览器,而我们平时在使用浏览器时,经常就添加一些插件,扩展,代理之类的应用.所以使用 selenium 时,我们可能需要对 chrome ...
- Eclipse 中 No java virtual machine was found... 解决方法
这个链接说的不错,http://www.mafutian.net/123.html,,但是还有一种可能是64位和32位的问题,也就是eclipse32位只能用32位的jdk,eclipse64位的只能 ...
- AIX rcp跨主机远程
rcp用途:在本地主机和远程主机之间或者两个远程主机之间传输文件.详细用法可man rcp查看. 现在要把主机10.200.5.200的/tmp/work.sh(属主为root用户)拷贝到远程主机18 ...
- 数据科学:numpy.where() 的用法
原文出处:numpy.where() 用法讲解 原创作者:massquantity numpy.where() 有两种用法: 1. np.where(condition, x, y) 满足条件(con ...
- 关于Python导入其他目录中的类
在需要导入的某个类的目录中,添加一个__init__.py的文件,
- Maven的安装及配置、Maven在Eclipse中的配置
一.需要准备的东西 1. JDK 2. Eclipse 3. Maven程序包 二.检查JAVA安装 三.安装Maven 下载apache-maven-3.5.3-bin.zip解压即可. 四.配置M ...
- 分布式爬虫搭建系列 之三---scrapy框架初用
第一,scrapy框架的安装 通过命令提示符进行安装(如果没有安装的话) pip install Scrapy 如果需要卸载的话使用命令为: pip uninstall Scrapy 第二,scrap ...
- Windows + Ubuntu 双系统安装
前言:本篇文章是对之前文章的更新,更新的主内容是把原来用手机拍摄的图片换成了虚拟机的截图,以及对磁盘划分的新的见解和一些使用感受,原本是打算删除之前的那篇Win + Ubuntu双系统的文章的,后来想 ...
- C#读写EXCEL(二) ZedGraph在Asp.net中的应用
C#读写EXCEL(二) 2010-08-25 14:50:42| 分类: 默认分类 | 标签: |举报 |字号大中小 订阅 用微信 “扫一扫” 将文章分享到朋友圈. 用易信 “扫一扫” ...
- java core 正则 "\\PL+"的意义
java core第十版中的第一章中出现了一个正则"\\PL+",根据注释(Split into words:noletters are delimiters)提示,这个正则的意思 ...